我的老板喜欢发明非常不寻常的场景来编码,这个让我难过。我正在制作一个必须使用GridView来显示一些非常晚的数据的WPF应用程序。 为了显示数据,他希望能够首先使用一些列标题初始化GridView,这不是问题。然后,他需要将这个GridView,一个DataTable和一些格式信息传递给一个绑定数据的方法。
在设计时,我们不知道我们想要绑定到DataTable中的哪些列。我们不能使用XAML,因为整个网格是动态创建的。在绑定数据时,我们必须指定每列格式化数据。到目前为止,我实现了IValueConverter的实现,它将格式化类作为其构造函数中的参数。 最后的转折是它必须支持多次在数据表中显示相同的列,以不同的方式格式化。显然,您不能在一个DataTable中拥有多个列的副本,因为它们具有名称冲突。
这是我到目前为止所拥有的:
/// <summary>
/// Sets the view of the passed ListView to a new GridView with properly formatted headers.
/// The headers are also the field names (column names) of the data table that you will
/// bind to
/// </summary>
/// <param name="displayPanel"></param>
/// <param name="displayFieldList"></param>
public static void InitializeGrid(ListView displayPanel,IDisplayFieldList displayFieldList)
{
GridView gv = new GridView();
gv.AllowsColumnReorder = true;
for (int i = 0; i < displayFieldList.Count; i++)
{
GridViewColumn col = new GridViewColumn();
col.Header = displayFieldList[i].HeaderText;
gv.Columns.Add(col);
}
displayPanel.View = gv;
}
/// <summary>
/// Binds data to the columns set in the ListView.View. Displays and formats the data.
/// </summary>
/// <param name="displayPanel"></param>
/// <param name="table"></param>
/// <param name="displayFieldList"></param>
public static void BindData(ListView displayPanel, DataTable table, IDisplayFieldList displayFieldList)
{
for(int i=0; i<displayFieldList.Count; i++)
{
GridViewColumn gridCol = ((GridView)displayPanel.View).Columns[i];
DmlDisplayField displayField = displayFieldList[i] as DmlDisplayField;
if(displayField != null)
{
gridCol.DisplayMemberBinding = new Binding()
{
Source = table.Columns[displayField.DataField],
Converter = new MaskConverter(displayField.DataField),
ConverterParameter = displayField
};
}
else
{
gridCol.DisplayMemberBinding = new Binding()
{
Source = table.Columns[displayFieldList[i].Name]
};
}
}
displayPanel.ItemsSource = table.AsDataView();
}
IDisplayFieldList是包含元数据的DisplayField或DmlDisplayField类的集合。 MaskConverter是一个IValueConverter,它以各种方式格式化DmlDisplayField列。
当我运行此代码时,所有行都是空白的,但我可以选择单独的行。
到目前为止,我已经尝试了许多不同的绑定方式,并且大多数从System.Reflection给出了一个“模糊匹配异常”。
如果你需要我发布MaskConverter,我会,但它很乱......
有什么想法吗?万分感谢!
答案 0 :(得分:0)
我只使用winforms DataGridView做了类似的事情,但我认为wpf GridView也应该能够动态地自动创建它的列......
ICustomTypeDescriptor接口允许您向网格提供自己的一组PropertyDescriptors。没有必要将两列绑定到同一属性(描述符),因为您可以为同一属性/列/字段/无论如何提供2个不同的属性描述符...
另一方面,这个概念可能有点矫枉过正,可能有更简单的方法来做到这一点,所以这只是一个建议