Привязка элементов внутри элемента с другой привязкой
Возникла следующая проблема.
Есть 2 ObservableCollection: это EmpList и AbsCatList. DataGrid привязывается к EmpList и показывает оттуда данные. Внутри грида есть ComboBox, который хранит данные из AbsCatList. Но его тег необходимо указать из EmpList.
И вопрос заключается в следующем, как в ComboBox показывать данные из AbsCatList, а указать его тег - из EmpList?
<Page.Resources>
<viewmodel:EmployerList x:Key="emp"/>
<viewmodel:AbsenceCategoryList x:Key="absCat"/>
</Page.Resources>
<Grid Background="White">
<DataGrid Name="TimeSheetGrid" IsReadOnly="True" AutoGenerateColumns="False"
DataContext="{Binding Source={StaticResource emp}}"
ItemsSource="{Binding Path=EmpList}"
SelectedValuePath="EmpID">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding EmpName}" Width="Auto">
<DataGridTextColumn.Header>Тип</DataGridTextColumn.Header>
</DataGridTextColumn>
<DataGridTemplateColumn>
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<ComboBox Width="230" IsReadOnly="True"
DataContext="{Binding Source={StaticResource absCat}}"
ItemsSource="{Binding Path=AbsCatList}"
DisplayMemberPath="Name" SelectedValuePath="Id"
Tag="{Binding Path=EmpList, ElementName=EmpID}"
SelectionChanged="ComboBox_SelectionChanged"/>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
</Grid>
Ответы (1 шт):
Покажу простой пример с вот такой разметкой
<Window x:Class="WpfAppDGCombo.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:WpfAppDGCombo"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800"
d:DataContext="{d:DesignInstance local:MainViewModel}">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition/>
</Grid.RowDefinitions>
<StackPanel Orientation="Horizontal">
<Button Padding="10,5" Content="Click me" Margin="5" Click="Button_Click"/>
</StackPanel>
<DataGrid Grid.Row="1" ItemsSource="{Binding Members}" AutoGenerateColumns="False">
<DataGrid.Resources>
<CollectionViewSource x:Key="Genders" Source="{Binding Genders}"/>
</DataGrid.Resources>
<DataGrid.Columns>
<DataGridTextColumn Header="Имя" Binding="{Binding Name}"/>
<DataGridComboBoxColumn Header="Пол" ItemsSource="{Binding Source={StaticResource Genders}}"
DisplayMemberPath="Name"
SelectedValuePath="Id"
SelectedValueBinding="{Binding GenderId}"/>
</DataGrid.Columns>
</DataGrid>
</Grid>
</Window>
Вот такой код-бихайнд
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
DataContext = new MainViewModel();
}
private void Button_Click(object sender, RoutedEventArgs e)
{
MainViewModel vm = (MainViewModel)DataContext;
Debug.WriteLine(JsonSerializer.Serialize(vm.Members, new JsonSerializerOptions { WriteIndented = true, Encoder = JavaScriptEncoder.UnsafeRelaxedJsonEscaping }));
}
}
Здесь обработчик события только для простоты, я советую использовать команды.
Вот такие модели
public class Gender
{
public int Id { get; set; }
public string Name { get; set; }
}
public class Member
{
public string Name { get; set; }
public int GenderId { get; set; }
}
И вот такая вьюмодель
public class MainViewModel
{
public Gender[] Genders { get; }
public ObservableCollection<Member> Members { get; }
public MainViewModel()
{
Genders = new Gender[]
{
new Gender { Id = 0, Name = "не задан" },
new Gender { Id = 1, Name = "Мужской" },
new Gender { Id = 2, Name = "Женский" }
};
Members = new ObservableCollection<Member>();
}
}
Запускаю, заполняю данными таблицу руками
Жму кнопку, получаю вывод в консоль студии
[
{
"Name": "Анатолий",
"GenderId": 1
},
{
"Name": "Жанна",
"GenderId": 2
},
{
"Name": "Кто-то",
"GenderId": 0
}
]
Как видите, Tag или обработчик SelectedItemChanged мне не потребовались.
Если хотите управлять данными из кода в реальном времени, то реализуйте INotifyPropertyChanged для вьюмодели и классов с изменяемыми из кода данными.

