7

アイテムのリストを処理するデータテンプレートを作成する方法はありますか?DataTemplate.DataType =コレクション<Entity>?

は私がContact.Phones(EntityCollection<Phone>)を持っていると私は、データテンプレートがリストを処理する - など

削除編集を追加する一般的なEntityCollection<Phone>へのDataTemplateのDataTypeプロパティを設定する方法はありますか?

答えて

3

ジェネリックリストを新しいクラスにラップします。新しいクラスは、ジェネリックリストを何も追加せずにサブクラス化します。 これにより、XAMLからリストにバインドすることができます。 これはここに記述されています: Can I specify a generic type in XAML (pre .NET 4 Framework)?

7

私のEmerald Data Foundation(EDF)ツールでは、ジェネリック型も指定できるx:Typeよりも強力なMarkupExtensionを作成してこれを解決しました。私は書くことができ、そのよう:

<DataTemplate TargetType="{edf:Type generic:ICollection{local:Entity}}" /> 

は、ここで私が使用したものだ。それはまた、EDF内の他のコードで使用されているため

[MarkupExtensionReturnType(typeof(Type))] 
    public class TypeExtension : MarkupExtension 
    { 
    public TypeExtension() { } 
    public TypeExtension(string typeName) { TypeName = typeName; } 
    public TypeExtension(Type type) { Type = type; } 

    public string TypeName { get; set; } 
    public Type Type { get; set; } 

    public override object ProvideValue(IServiceProvider serviceProvider) 
    { 
     if(Type==null) 
     { 
     IXamlTypeResolver typeResolver = serviceProvider.GetService(typeof(IXamlTypeResolver)) as IXamlTypeResolver; 
     if(typeResolver==null) throw new InvalidOperationException("EDF Type markup extension used without XAML context"); 
     if(TypeName==null) throw new InvalidOperationException("EDF Type markup extension used without Type or TypeName"); 
     Type = ResolveGenericTypeName(TypeName, (name) => 
     { 
      Type result = typeResolver.Resolve(name); 
      if(result==null) throw new Exception("EDF Type markup extension could not resolve type " + name); 
      return result; 
     }); 
     } 
     return Type; 
    } 

    public static Type ResolveGenericTypeName(string name, Func<string, Type> resolveSimpleName) 
    { 
     if(name.Contains('{')) 
     name = name.Replace('{', '<').Replace('}', '>'); // Note: For convenience working with XAML, we allow {} instead of <> for generic type parameters 

     if(name.Contains('<')) 
     { 
     var match = _genericTypeRegex.Match(name); 
     if(match.Success) 
     { 
      Type[] typeArgs = (
      from arg in match.Groups["typeArgs"].Value.SplitOutsideParenthesis(',') 
      select ResolveGenericTypeName(arg, resolveSimpleName) 
      ).ToArray(); 
      string genericTypeName = match.Groups["genericTypeName"].Value + "`" + typeArgs.Length; 
      Type genericType = resolveSimpleName(genericTypeName); 
      if(genericType!=null && !typeArgs.Contains(null)) 
      return genericType.MakeGenericType(typeArgs); 
     } 
     } 
     return resolveSimpleName(name); 
    } 
    static Regex _genericTypeRegex = new Regex(@"^(?<genericTypeName>\w+)<(?<typeArgs>\w+(,\w+)*)>$"); 

    } 

ジェネリック型名の解析コードは別の方法です。すべてを1つの方法に組み合わせることができます。

関連する問題