DataTemplate.DataType = 集合<实体>?

发布于 2024-08-10 06:42:45 字数 212 浏览 9 评论 0原文

有没有办法创建处理项目列表的数据模板?

我有 Contact.Phones (EntityCollection),我希望数据模板能够处理列表 - 添加删除编辑等。

有没有办法将 DataTemplate 的 DataType 属性设置为通用 EntityCollection<电话>

Is there a way to create a data template that handles a list of items?

I have Contact.Phones (EntityCollection<Phone>) and I want the data template to handle the list - add remove edit etc.

Is there a way to set the DataType property of the DataTemplate to generic EntityCollection<Phone>?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

倒数 2024-08-17 06:42:45

在我的 Emerald Data Foundation (EDF) 工具中,我通过创建一个比 x:Type 更强大的 MarkupExtension 来解决这个问题,它也可以指定泛型类型。这样我可以写:

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

这是我使用的:

  [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+)*)>$");

  }

通用类型名称解析代码位于单独的方法中,因为它也被 EDF 中的其他一些代码使用。您可以将它们全部合并到一种方法中。

In my Emerald Data Foundation (EDF) tool I solved this by creating a more powerful MarkupExtension than x:Type that could specify generic types too. That way I could write:

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

Here's what I used:

  [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+)*)>$");

  }

The generic type name parsing code is in a separate method because it is also used by some other code in EDF. You could combine it all into one method.

寻找一个思念的角度 2024-08-17 06:42:45

将您的通用列表包装在一个新类中,该类对您的通用列表进行子类化,而不添加任何内容。
这使得从 XAML 绑定到列表成为可能。
此处对此进行了描述:
我可以在 XAML(.NET 4 Framework 之前的版本)中指定泛型类型吗?

Wrap your generic list in a new class, which subclasses your generic list without adding anything.
This makes it possible to bind to the list from XAML.
This is described here:
Can I specify a generic type in XAML (pre .NET 4 Framework)?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文