[英]Dynamically setting DataGrid Columns to ComboBox Columns via data-binding
我有一个DataGrid绑定到我称为“ GridCollection”的DataTable:
<!--DataGrid-->
<DataGrid Name="DataGrid" ItemsSource="{Binding GridCollection}" >
<DataGrid.Columns>
<DataGridTemplateColumn>
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<StackPanel>
<ComboBox ItemsSource="{Binding SelectionOptions}">
<ComboBox.Style>
<Style TargetType="ComboBox">
<Setter Property="Visibility" Value="Collapsed"/>
<Style.Triggers>
<DataTrigger Binding="{Binding Caption, Mode=TwoWay}" Value="ShowComboBox">
<Setter Property="Visibility" Value="Visible"/>
</DataTrigger>
</Style.Triggers>
</Style>
</ComboBox.Style>
</ComboBox>
</StackPanel>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
我希望能够动态更新DataGrid列单元格模板以显示组合框。
我试图通过添加绑定到DataTable列(“标题”)的属性的DataTrigger,然后相应地更新组合框的可见性来实现此目的。
我的理解是,在这种情况下,DataContext是DataTable的Columns。
我尝试设置DataTable的Columns的“ Caption”属性以匹配DataTrigger(“ ShowComboBox”)中指定的值:
ViewModel.GridCollection.Columns[index].Caption = "ShowComboBox";
在确认此代码行正在执行并且Caption属性正在更新之后,这仍然没有对DataGrid进行任何更改。 没有列显示组合框。
我不确定绑定是否存在问题,或者是否还有其他问题。
任何帮助表示赞赏!
由于DataColumn
没有实现INotifyPropertyChanged接口,并且没有向WPF发出属性更改通知,因此无法使用。
但是,如果将一列添加到DataTable
并绑定到此表,它将起作用:
ViewModel.GridCollection.Columns.Add(new DataColumn("Caption"));
不同之处在于DataRowView
类实现了INotifyPropertyChanged
接口。 WPF必须具备此功能,才能侦听对源属性的更改并动态更新视图。
如果更改布局,则需要重置绑定。 从您的数据网格中删除绑定/数据源。 更改标题值,然后将源再次绑定到您的数据网格。
这对我有用的代码:
窗口的XAML
Window x:Class="WpfApplication7.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfApplication7"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525" Loaded="Window_Loaded">
<Grid>
<Grid.RowDefinitions>
<RowDefinition />
<RowDefinition />
</Grid.RowDefinitions>
<DataGrid Name="grd" AutoGenerateColumns="False" ItemsSource="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=Window}, Path=DataContext}">
<DataGrid.Columns>
<DataGridTextColumn Header="01" Binding="{Binding Name}" />
<DataGridTextColumn Header="02" Binding="{Binding LastName}" />
<DataGridTemplateColumn Header="CBX">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<ComboBox>
<ComboBox.Style>
<Style TargetType="ComboBox">
<Style.Triggers>
<DataTrigger Binding="{Binding Path=Caption, Mode=TwoWay}" Value="ShowCombobox">
<Setter Property="Visibility" Value="Collapsed" />
</DataTrigger>
</Style.Triggers>
</Style>
</ComboBox.Style>
</ComboBox>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
<Button Content="Click" Click="Button_Click" Grid.Row="1"/>
</Grid>
</Window>
后面的代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
namespace WpfApplication7
{
/// <summary>
/// Interaktionslogik für MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
items soureitems = new items();
for(int i = 0; i <= 10; i++)
{
item sourceitem = new item();
sourceitem.Name = "John";
sourceitem.LastName = "Doe";
sourceitem.Caption = "";
soureitems.Add(sourceitem);
}
this.DataContext = soureitems;
}
private void Button_Click(object sender, RoutedEventArgs e)
{
items sourceitems = (items)(this.DataContext);
this.DataContext = null;
foreach (item sourceitem in sourceitems)
{
if(sourceitem.Caption != "ShowCombobox")
{
sourceitem.Caption = "ShowCombobox";
} else
{
sourceitem.Caption = "";
}
}
this.DataContext = sourceitems;
}
}
public class items : System.Collections.ObjectModel.ObservableCollection<item> { }
public class item
{
string _Name;
string _LastName;
string _Caption;
public string Name {
get { return _Name; }
set { _Name = value; }
}
public string LastName
{
get { return _LastName; }
set { _LastName = value; }
}
public string Caption
{
get { return _Caption; }
set { _Caption = value; }
}
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.