[英]WPF Datagrid binding to list of arrays with Cell Template Column
我有一个绑定到列表的数据网格,其中每个ViewModel都有一个由字符串索引的字段数组,例如RowVM [“ AKey”]。 使用类似的东西这个我可以得到一个TextBlock来显示正确的元素如
textColumn.Binding= new Binding("[" + columnHeaderText + "].Name");
但这只允许我在TextBlock中显示一个值。
我需要显示来自indexed属性的两个字段,所以我想我将使用DataGridTemplateColumn
而不是DataGridTextColumn
,但是还无法获得新的绑定来正确链接到列标题文本。
对于每一列,我的代码当前是
tmpltColumn = new DataGridTemplateColumn();
tmpltColumn.Header = t.FirstName + " " + t.LastName;
tmpltColumn.CellTemplate = TimeTableGrid.FindResource("TimeTableCellTemplate") as DataTemplate;
TimeTableGrid.Columns.Add(tmpltColumn);
其中TimeTableCellTemplate
定义了两个文本块。
如果我将TextBlocks的文本定义为
Text="{Binding Column.Header, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridCell}}}"
然后文本块正确显示列标题。
我不能做的是找到文本块的任何绑定,这些绑定将找到“列标题”文本并将其用作索引。
[编辑:]
原始TextColumn的绑定是在我构建列时创建的,并且具有相关的键值在索引括号中进行了硬编码,例如[columnHeaderText] .Name(请参见上面的textColumn.Binding)。
当我移至TemplateColumns时,Template包含Binding表达式,并且不特定于特定列。
所以我有以下内容(简化):
<DataGrid.Resources>
<DataTemplate x:Key="TimeTableCellTemplate" >
<StackPanel Width="Auto" Height="Auto" Orientation="Vertical" >
<TextBlock Text="{Binding Column.Header, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridCell}}}" />
</StackPanel>
</DataTemplate>
</DataGrid.Resources>
所示的Binding正确显示了TextBlock
的实际Column.Header,但是我需要做的是在RowViewModel的索引中使用该值。 为了满怀希望,我尝试了这一点,即将Column.Header绑定嵌入到CellTemplate绑定中:
<TextBlock Text="{Binding [{Binding Column.Header, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridCell}}}].Name}" />
哪个当然不起作用。
我错过了令人眼花obvious乱的明显东西吗?
[结束]
有解决方案吗? 还是我将不得不例如切换到网格并手动加载每个单元格?
我不需要双向绑定(如果有帮助的话),尽管需要在单元格之间拖放。
按照此链接中描述的模式,我已经找到了一种可行的解决方案。
带有简单TextBlock的原始版本将键(列标题)硬编码到Binding中,例如[key].Name
新版本使用带有相同绑定的嵌套TextBlocks创建模板,再次对其进行硬编码。
为了完整起见,完整的代码调用以下代码:
private DataGridTemplatColumn CreateColumn(string key)
{
DataGridTemplateColumn tmpltColumn = new DataGridTemplateColumn();
tmpltColumn.Header = key;
// Make the parts for the template
FrameworkElementFactory tb = new FrameworkElementFactory(typeof(TextBlock));
Binding b = new Binding($"[{key}].Name");
tb.SetBinding(TextBlock.TextProperty, b);
FrameworkElementFactory tb1 = new FrameworkElementFactory(typeof(TextBlock));
Binding b1 = new Binding();
b1.Path = new PropertyPath($"[{key}].Room");
tb1.SetBinding(TextBlock.TextProperty, b1);
FrameworkElementFactory sb = new FrameworkElementFactory(typeof(StackPanel));
sb.AppendChild(tb);
sb.AppendChild(tb1);
DataTemplate dt = new DataTemplate { VisualTree = sb };
dt.Seal();
tmpltColumn.CellTemplate = dt;
return tmpltColumn;
}
然后将模板列添加到DataGrid,一切顺利。
当我问这个问题时,我想让一个模板(在XAML中定义)适用于所有列,这看起来更加优雅,但这简单易懂,也很好。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.