代码之家  ›  专栏  ›  技术社区  ›  Cameron MacFarland

如何创建自定义WPF集合?

  •  3
  • Cameron MacFarland  · 技术社区  · 15 年前

    我正在尝试创建一组自定义类,这些类可以通过XAML添加到WPF控件中。

    我遇到的问题是向集合中添加项。这是我到目前为止所拥有的。

    public class MyControl : Control
    {
        static MyControl()
        {
            DefaultStyleKeyProperty.OverrideMetadata(typeof(MyControl), new FrameworkPropertyMetadata(typeof(MyControl)));
        }
    
        public static DependencyProperty MyCollectionProperty = DependencyProperty.Register("MyCollection", typeof(MyCollection), typeof(MyControl));
        public MyCollection MyCollection
        {
            get { return (MyCollection)GetValue(MyCollectionProperty); }
            set { SetValue(MyCollectionProperty, value); }
        }
    }
    
    public class MyCollectionBase : DependencyObject
    {
        // This class is needed for some other things...
    }
    
    [ContentProperty("Items")]
    public class MyCollection : MyCollectionBase
    {
        public ItemCollection Items { get; set; }
    }
    
    public class MyItem : DependencyObject { ... }
    

    和XAML。

    <l:MyControl>
        <l:MyControl.MyCollection>
            <l:MyCollection>
                <l:MyItem />
            </l:MyCollection>
        </l:MyControl.MyCollection>
    </l:MyControl>
    

    例外情况是:
    System.Windows.Markup.XamlParseException occurred Message="'MyItem' object cannot be added to 'MyCollection'. Object of type 'CollectionTest.MyItem' cannot be converted to type 'System.Windows.Controls.ItemCollection'.

    有人知道我怎么修这个吗?谢谢

    2 回复  |  直到 15 年前
        1
  •  3
  •   Cameron MacFarland    15 年前

    在更多的谷歌搜索之后,我发现 this 包含相同错误消息的日志。似乎我也需要实现IList。

    public class MyCollection : MyCollectionBase,  IList
    {
        // IList implementation...
    }
    
        2
  •  1
  •   Pavel Minaev    15 年前

    你可能忘记了创建一个 ItemCollection 在的构造函数中 MyCollection ,并将其分配给 Items 财产?为了让XAML解析器添加项,它需要一个现有的集合实例。它不会为您创建新的(尽管如果集合属性具有setter,它将允许您在XAML中显式创建一个)。所以:

    [ContentProperty("Items")]
    public class MyCollection : MyCollectionBase
    {
        public ObservableCollection<object> Items { get; private set; }
    
        public MyCollection()
        {
             Items = new ObservableCollection<object>();
        }
    }