C# 简单地用动态成员/属性实现WPF数据绑定源?

C# 简单地用动态成员/属性实现WPF数据绑定源?,c#,.net,wpf,data-binding,C#,.net,Wpf,Data Binding,我正在做一个项目,它允许标记目录。作为界面的一部分,我想显示目录列表。列表中的每个条目都是目录名,加上许多列。一个用于当时应用程序已知的每个标记,带有一个复选框,指示目录是否已使用该标记进行标记。然后,用户可以轻松地标记或取消标记多个目录 我认为使用WPF DataGrid会很好,但是我很难决定如何以一种允许我轻松地将标记目录绑定到DataGrid实例的方式来存储标记目录,因为标记的数量和组成可以随时更改 一种方法是拥有一个目录及其标记的主列表,从中我可以在每次已知标记的数量发生变化时生成一组

我正在做一个项目,它允许标记目录。作为界面的一部分,我想显示目录列表。列表中的每个条目都是目录名,加上许多列。一个用于当时应用程序已知的每个标记,带有一个复选框,指示目录是否已使用该标记进行标记。然后,用户可以轻松地标记或取消标记多个目录

我认为使用WPF DataGrid会很好,但是我很难决定如何以一种允许我轻松地将标记目录绑定到DataGrid实例的方式来存储标记目录,因为标记的数量和组成可以随时更改

  • 一种方法是拥有一个目录及其标记的主列表,从中我可以在每次已知标记的数量发生变化时生成一组补充的Expando对象。每个对象对于每个标记都有一个布尔属性。这些对象的列表可以绑定到DataGrid,自动生成的列将自动显示它们。这样做的好处是,它确实很好地模拟了我正在显示的内容——即使目录没有标记,它仍然具有“nothavethistag”属性,而且实现起来很简单。问题在于它凌乱且效率低下,而且(对此不确定)我认为当属性更改时,我无法调用Expando对象上的方法

  • 另一种方法是在已知标记更改时动态地重新创建DataTemplate。缺点是我必须在代码隐藏中动态创建数据模板

我想知道,考虑第一个选项,是否有一种方法可以覆盖对象似乎必须具有的WPF属性

例如,是否有类似于
IDataBindingSource
的接口

interface IDataBindingSource {
    string[] MyProperties();
    Type[] MyPropertyTypes();
    object[] MyPropertyValues();
}
也就是说,有没有一种简单的方法可以在运行时更改DataGrid中显示的属性(并使用自动生成的列)?

编辑:澄清有关标记的信息。我所说的标签是指小的描述性字符串版本。用户想要的标签数量是有限的,但是有大量的目录。因此,我想为每个目录显示一组复选框,允许我为该目录添加或删除标记,就像您为用户设置权限一样,例如(每个权限都是一个标记,用户在目录中的权限)。但是,在任何给定时间,潜在标记的数量都是可变的,因为用户可以添加更多标记,或者从所有目录中删除标记并有效地删除它


这不是一个困难的问题-一个非常简单的方法是手动绘制一个表,一列用于目录,其他列具有已知的标记列表,然后逻辑将在带有循环的单元格中创建和设置复选框。有很多方法可以做到这一点,但我想使用最好的方法,这使我能够快速编写代码,并保留内置在控件中的功能,如冻结和重新排序等。

我从来都不是
DataGrid
控件的粉丝,尤其是在WPF中。考虑到WPF在控件模板和样式方面的多功能性,我会使用
ListView
作为内容(
ListView.View

然后,您可以放弃整个复杂的
IDataBindingSource
位,直接使用MVVM,这对于标准绑定来说要容易得多

例如,您可以有一个
DirectoryModel
类,该类的内容如下:

public sealed class DirectoryModel : INotifyPropertyChanged
{
  public ObservableCollection<DirectoryModel> Subdirectories { get; set; }

  // Notify when this property changes for proper binding behavior!
  public bool IsTagged { get; set; }
}
公共密封类目录模型:INotifyPropertyChanged
{
公共ObservableCollection子目录{get;set;}
//此属性更改时通知以确保正确的绑定行为!
公共布尔IStaged{get;set;}
}

然后,您的
ListViewItem.IsSelected
属性将绑定到
DirectoryModel.Istaged

不要尝试将其作为列(复数)处理。有一个带有组合框的单列,在其中选中或关闭标记。组合框绑定到集合。@谢谢,这是个好主意。我希望一次显示所有标记复选框,这样我就可以简单地遍历列表并轻松地选中/取消选中,但我确信我可以使ComboBox(或类似的东西)显示如下。我也会调查的。谢谢你的回答!我会使用最好的工具,如果那是ListView,那就是我要使用的工具。但是你能把你的答案再详细一点吗?我不清楚如何实现可以使用自定义模板绑定到ListView的数据模型,但仍然允许在运行时更改标记(请记住每个目录的标记数量是可变的,我已经更新了我的Q以使其更清晰!)啊,我现在更清楚地看到了您的问题。你说标签的数量可以改变。假设我们从目录列表开始,有
蓝色
绿色
红色
的标签。假设每列中都有一个复选框,则每个标记都有一列。现在要添加黄色的
,必须创建另一列,对吗?这在
列表视图
中是可行的,但我承认动态特性会让您在运行时做一些事情(比如创建
绑定
路径)。