Моя конечная цель - создать сетку данных с автоматически сгенерированными столбцами (потому что я никогда не буду точно знать, сколько свойств класса нужно будет сгенерировать). Эта сетка данных всегда будет иметь первый столбец в качестве флажка. Если пользователь выбирает несколько строк в таблице данных, а затем проверяет один из выбранных флажков, все флажки (в первом столбце или связанном столбце - либо в порядке) также будут проверены.
Я экспериментировал с использованием DataGrid.RowHeaderTemplate в xaml следующим образом:
<DataGrid x:Name="SheetListGrid"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
HeadersVisibility="All"
AutoGenerateColumns="True"
CanUserResizeRows="False"
AlternatingRowBackground="LightGray"
AutoGeneratingColumn="SheetListGrid_AutoGeneratingColumn">
<DataGrid.RowHeaderTemplate>
<DataTemplate>
<Grid>
<CheckBox Checked="CheckBox_Checked"
IsChecked="{Binding Path=Selected, Mode=TwoWay}"/>
</Grid>
</DataTemplate>
</DataGrid.RowHeaderTemplate>
</DataGrid>
Но у меня возникли проблемы с одновременным переключением нескольких флажков.
Моя вторая попытка состояла в том, чтобы полностью удалить DataGrid.RowHeaderTemplate и поместить его в обработчик событий AutoGeneratingColumn DataGrid следующим образом:
Изменить: Основная цель этого состояла в том, чтобы добавить свой собственный столбец флажок и иметь возможность один раз щелкнуть состояние флажка.
private void SheetListGrid_AutoGeneratingColumn(object sender, DataGridAutoGeneratingColumnEventArgs e)
{
if (e.Column is DataGridCheckBoxColumn && !e.Column.IsReadOnly)
{
FrameworkElementFactory checkboxFactory = new FrameworkElementFactory(typeof(CheckBox));
checkboxFactory.SetValue(HorizontalAlignmentProperty, HorizontalAlignment.Center);
checkboxFactory.SetValue(VerticalAlignmentProperty, VerticalAlignment.Center);
checkboxFactory.SetBinding(ToggleButton.IsCheckedProperty, new Binding(e.PropertyName) { UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged });
e.Column = new DataGridTemplateColumn
{
Header = e.Column.Header,
CellTemplate = new DataTemplate { VisualTree = checkboxFactory },
SortMemberPath = e.Column.SortMemberPath
};
// notice I tried registering the event handler here as well.
// but this caused a continuous loop of CheckBox_Checked to be
// fired.
// register the checkbox event handler
//checkboxFactory.AddHandler(CheckBox.CheckedEvent, new RoutedEventHandler(CheckBox_Checked));
}
}
Вот мой обработчик событий CheckBox_Checked на случай, если это будет полезно ...
private void CheckBox_Checked(object sender, RoutedEventArgs e)
{
// get the selected sheets
var selectedSheets = SheetListGrid.SelectedItems;
if (selectedSheets.Count == 0) return;
foreach (var item in selectedSheets)
{
//DataGridRow row = SheetListGrid.ItemContainerGenerator.ContainerFromItem(item) as DataGridRow;
FakeSheet sheet = item as FakeSheet;
if (sheet.Selected == false)
sheet.Selected = true;
}
SheetListGrid.Items.Refresh();
}
Мне кажется, что я что-то упускаю, чтобы сделать это намного проще, но я не могу понять это, и я почти растопил свою оперативную память от количества открытых вкладок. Должен отметить, что этот проект будет библиотекой классов, и я не могу включать какие-либо сторонние сборки. Кроме того, я хотел бы попытаться избежать использования Windows.Interactivity, поскольку у меня раньше были проблемы с распространением этой библиотеки классов среди других, и на компьютере работала отдельная версия, что вызывало ошибки.