Я разрабатываю приложение, выполняющее проверки в списке элементов. Каждый элемент имеет список проверок, которые необходимо выполнить на нем. Каждая проверка может быть одной из трех типов: CheckBox, ComboBox, TextBox.WPF DataGrid различные элементы управления в одном столбце - неправильное связывание
Я хотел бы иметь Datagrid с 2 столбцами (один для названия элемента, второй для списка проверок). Второй столбец содержит другой DataGrid с двумя столбцами (один для имени проверки, второй для контроля проверки). Цель состоит в том, чтобы иметь разные типы элементов управления в одном столбце, связанные с моделями Check.
Проблема заключается в том, что связывание с CheckValue не работает, однако привязки со всеми другими свойствами работают нормально.
Последний столбец содержит CheckBoxes, TextBox и ComboBox, однако они не заполнены никакими значениями. Кто-нибудь знает, что не так с кодом ниже?
Ниже приведены примеры типовых классов
public class Item
{
public string ItemName { get; set; }
public ObservableCollection<Check> Checks { get; set; }
public Item()
{
Checks = new ObservableCollection<Check>();
}
}
public enum CheckType
{
CheckBox,
ComboBox,
TextBox
}
public abstract class Check
{
public string CheckName { get; set; }
public CheckType CheckType { get; protected set; }
public abstract object CheckValue { get; set; }
}
public class CheckBox : Check
{
private bool checkValue;
public CheckBox()
{
CheckType = CheckType.CheckBox;
}
public override object CheckValue
{
get
{
return checkValue;
}
set
{
checkValue = (bool)value;
}
}
}
public class ComboBox : Check
{
private List<string> checkValue;
public ComboBox()
{
CheckType = CheckType.ComboBox;
}
public override object CheckValue
{
get
{
return checkValue;
}
set
{
checkValue = value as List<string>;
}
}
}
public class TextBox : Check
{
private string checkValue;
public TextBox()
{
CheckType = CheckType.TextBox;
}
public override object CheckValue
{
get
{
return checkValue;
}
set
{
checkValue = value as string;
}
}
}
public class MainViewModel
{
public ObservableCollection<Item> Items { get; set; }
public MainViewModel()
{
Items = new ObservableCollection<Item>();
Item item = new Item();
item.ItemName = "First item";
Check check1 = new CheckBox() { CheckName = "Check 1", CheckValue = true };
Check check2 = new CheckBox() { CheckName = "Check 2", CheckValue = false };
Check text1 = new TextBox() { CheckName = "Check 3", CheckValue = "Please enter check" };
Check combo1 = new ComboBox() { CheckName = "Check 4", CheckValue = new List<string> { "Value1", "Value2" } };
item.Checks.Add(check1);
item.Checks.Add(check2);
item.Checks.Add(text1);
item.Checks.Add(combo1);
Items.Add(item);
}
}
И, наконец, вот XAML код главного окна.
<Window x:Class="ItemTest.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:vm ="clr-namespace:ItemTest"
Title="MainWindow" Height="350" Width="525">
<Window.Resources>
<vm:MainViewModel x:Key="mainViewModel"/>
</Window.Resources>
<Grid DataContext="{Binding Source={StaticResource mainViewModel}}">
<DataGrid ItemsSource="{Binding Path=Items}" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn Header="Item" Binding="{Binding ItemName}" />
<DataGridTemplateColumn Header="Checks">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<DataGrid ItemsSource="{Binding Checks}" AutoGenerateColumns="False" HeadersVisibility="None">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding CheckName}" />
<DataGridTemplateColumn>
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<ContentControl>
<ContentControl.Style>
<Style TargetType="ContentControl">
<Style.Triggers>
<DataTrigger Binding="{Binding CheckType}" Value="CheckBox">
<Setter Property="ContentTemplate">
<Setter.Value>
<DataTemplate>
<CheckBox IsChecked="{Binding CheckValue}"/>
</DataTemplate>
</Setter.Value>
</Setter>
</DataTrigger>
<DataTrigger Binding="{Binding CheckType}" Value="ComboBox">
<Setter Property="ContentTemplate">
<Setter.Value>
<DataTemplate>
<ComboBox ItemsSource="{Binding CheckValue}" />
</DataTemplate>
</Setter.Value>
</Setter>
</DataTrigger>
<DataTrigger Binding="{Binding CheckType}" Value="TextBox">
<Setter Property="ContentTemplate">
<Setter.Value>
<DataTemplate>
<TextBox Text="{Binding CheckValue}" />
</DataTemplate>
</Setter.Value>
</Setter>
</DataTrigger>
</Style.Triggers>
</Style>
</ContentControl.Style>
</ContentControl>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
</Grid>
Отличный ответ! Это, в конце концов, работает :-) Спасибо ночной кодер, я потратил так много времени, чтобы решить эту проблему. – JacekT
@ JacekT, приветствую вас :) И да, что мне не нравится в WPF, так это то, что если у вас мало опыта, вы можете потратить много времени, пытаясь заставить его работать должным образом. К сожалению, некоторые (многие?) Вещи не кажутся очевидными. – nightcoder
@ nightcoder определенно много;) – Mafii