2013-11-27 111 views
5

我正在以编程方式创建DataGrid,并且也必须支持ComboBoxColumns将DataGridComboBoxColumn绑定到C#中的DataGrid的ItemsSource

在我创建DataGrid后,我将其设置为ItemSource以收集BindableList<BindableDictionary>类型的集合。 BindableDictionary是一种自定义类型。每个BindableDictionary代表一个元组。关键始终是列的名称,它的值是一个自定义类,它包含一个名为ActualValue的通用属性,一个名为AllowedValuesDictionary<T, string>和一个boolean,用于确定AllowedValues是否将用于构建ComboBoxColumn或“正常”列。该类还实现了INotifyPropertyChangedINotifyPropertyChanging

除了ComboBoxColumn外,这些东西还可以工作。我与ComboBoxColumn问题是,我不知道如何得到它使用AllowedValues对象来填补它的ITEMLIST 使用ActualValue属性选择从AllowedValuesBindableDictionary正确Value填补文本区域。

举个例子,我这​​是怎么绑定一个基于文本的列:

table.Columns.Add(new DataGridTextColumn() { Header = column.GUIName, DisplayIndex = column.Position, Binding = new Binding(column.Name + ".ActualValue") { UpdateSourceTrigger = UpdateSourceTrigger.Default, Mode = BindingMode.TwoWay, NotifyOnTargetUpdated = true, NotifyOnSourceUpdated = true, UpdateSourceExceptionFilter = new UpdateSourceExceptionFilterCallback(BindingExceptionHandler) } }); 

是的,这工作。

我试图DataGridComboBoxColumnItemsSource属性设置为column.AllowedValues,并设置DisplayPath"Value"这也至少显示正确的内容,但我不知道如何绑定到包含在DataGridActualValue财产的ItemsSource。此外,这意味着列内的所有单元共享相同的可选值,这可能会导致未来出现问题。

如果我试图像DataGridTextColumn那样绑定所有东西,则根本不会显示任何东西。也没有可供选择的项目。

如果有人有我可以尝试的暗示,那将会很棒。

编辑

刚看到这一点:https://stackoverflow.com/a/2197004/937093,我想,但后来我得到了我的输出窗口中出现以下消息:

System.Windows.Data Error: 2 : Cannot find governing FrameworkElement or FrameworkContentElement for target element. BindingExpression:Path=AllowedValues; DataItem=null; target element is 'DataGridComboBoxColumn' (HashCode=33493530); target property is 'ItemsSource' (type 'IEnumerable')

我的代码如下所示:

col = new DataGridComboBoxColumn() { Header = column.GUIName, SelectedValueBinding = new Binding(column.Name + ".ActualValue"), SelectedValuePath = "ActualValue" }; 
table.Columns.Add(col); 
BindingOperations.SetBinding(col, DataGridComboBoxColumn.ItemsSourceProperty, new Binding("AllowedValues")); 

编辑2 好的,发现这个网站:http://www.thomaslevesque.com/2011/03/21/wpf-how-to-bind-to-data-when-the-datacontext-is-not-inherited/

我尝试申请代理绑定的东西(虽然我不明白的列是如何在DataGrid ...还有什么地方会是?的可视化树的部分),但它不会工作。我的代码:

BindingProxy proxy = new BindingProxy() { Data = table.ItemsSource }; 
table.Resources.Add("proxy", proxy }); 
col = new DataGridComboBoxColumn() { Header = column.GUIName, SelectedValueBinding = new Binding("Data." + column.Name + ".ActualValue") { Source = proxy }, DisplayMemberPath = "Value", SelectedValuePath = "Key" }; 
table.Columns.Add(col); 
BindingOperations.SetBinding(col, DataGridComboBoxColumn.ItemsSourceProperty, new Binding("Data." + column.Name + ".AllowedValues") }); 

输出在输出窗口:

System.Windows.Data Error: 40 : BindingExpression path error: 'MyColumn' property not found on 'object' ''BindingList`1' (HashCode=55207835)'. BindingExpression:Path=Data.MyColumn.ActualValue; DataItem='BindingProxy' (HashCode=45660050); target element is 'TextBlockComboBox' (Name=''); target property is 'SelectedValue' (type 'Object')

我理解这个问题(它试图发现在的BindingList的“MyColumn”对象),但我不明白这是为什么发生的事情(它应该解析为BindingList [iterator] [“MyColumn”],因为BindingList包含BindableDictionary,这正是我的'普通'列所发生的情况)。

回答

0

我做了类似的事情。我正在使用Winforms,所以我的解决方案可能不适合你。不过,我建议使用类似的东西。

http://tech.pro/tutorial/776/csharp-tutorial-binding-a-datagridview-to-a-collection

再加上这一点。

http://www.codeproject.com/Articles/31418/Implementing-a-Sortable-BindingList-Very-Very-Quic

由于我拥有了一切工作,然后发现我不能排序我的datagridview。

我没有我的源代码方便,但总体思路是我手动创建我的组合框和文本框列,然后将我的列表绑定到它。

当我运行一个遍历每行并基于索引的函数(在我的情况下,我的组合框是最后3列)之后,我会先手动添加组合框的值,然后再那些被添加,我会检查组合框的值并将其设置为。

我还在数据错误事件中包含了这个函数,当我添加一个新列时。如果我添加了一个新行,如果我设置了autosize,它也会随机崩溃。我必须将这些设置为默认值,进行编辑,然后重置它。

希望我有代码提供,但它可能会让你在你的路上。如果不是当我明天上班时,我会张贴一些。 Comboboxes是一个巨大的工作痛苦。

相关问题