Как повторно использовать пользовательский код столбца сетки данных в WPF?
Используя VS 2010, я планирую создать несколько столбцов шаблона таблицы данных, но все они будут содержать текстовый блок, и я хочу, чтобы они вели себя как текстовый столбец с точки зрения сортировки, фильтрации, редактирования и т. Д. (Например, столбец, который имеет textblock и изображение внутри стековой панели, но с точки зрения поведения это действительно должно быть связано с текстом.)
При использовании столбца шаблона я узнал, что большая часть функциональности, связанной с обычной текстовой ячейкой, должна быть переделана. Например, чтобы сделать текст редактируемым, необходимо предоставить шаблон редактирования ячейки, например:
<DataGridTemplateColumn.CellEditingTemplate>
<DataTemplate>
<TextBox
FocusManager.FocusedElement="{Binding RelativeSource={RelativeSource Self}}"
Text="{Binding Path=SomeProperty, Mode=TwoWay, UpdateSourceTrigger=LostFocus}">
</TextBox>
</DataTemplate>
</DataGridTemplateColumn.CellEditingTemplate>
(И вы также должны обрабатывать события сетки, чтобы убедиться, что он ведет себя как обычное текстовое поле, например, автоматически начинает режим редактирования, если пользователь нажимает клавишу, или вкладки в ячейку и т. Д.)
Поэтому мой вопрос заключается в том, каков наилучший способ (если таковой имеется) для меня, чтобы избежать необходимости явно писать этот код (а также код для сортировки, копирования, фильтрации и т. Д., Как текстовую ячейку, для КАЖДОГО столбца шаблона, который я создаю так " Я предполагаю, что это плохая практика - воспроизводить код на половину страницы для каждого столбца, где единственными отличиями могут быть имя связанного свойства и несколько визуальных изменений.
Я вне этого разочарован и вообще с WPF. Я искал в Интернете, я пробовал украшения, я пытался унаследовать столбец сетки данных, я пытался определить пользовательские элементы управления для шаблонов данных, и все кажется неудачным с некоторой неприятной "ошибкой". Это третий вопрос, который я задавал по этому поводу с различными деталями, с минимальным ответом. НЕ ДОЛЖНО быть таким сложным, чтобы понять, как реализовать те, что в основном представляют собой прославленные текстовые столбцы, без необходимости заново изобретать все колесо каждый раз и во всех отношениях. По моему скромному мнению, по крайней мере.
2 ответа
Можете ли вы показать мне, как использовать стили ячеек, чтобы изменить существующий DataGridTextColumn, чтобы он отображал текст вместе с изображением рядом с ним?
Вот:
<DataGridTextColumn Binding="{Binding LastName}">
<DataGridTextColumn.CellStyle>
<Style TargetType="DataGridCell">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="DataGridCell">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition/>
<ColumnDefinition Width="16"/>
</Grid.ColumnDefinitions>
<ContentPresenter ContentSource="Content"/>
<Image Source="/Images/Homer.jpg" Grid.Column="1"/>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</DataGridTextColumn.CellStyle>
</DataGridTextColumn>
Проделав дополнительную работу, вы можете определить эти шаблоны и стиль как Resources
в вашем приложении и использовать их каждый раз.
Что касается источника изображения, вы можете использовать Attached Property
определить его в DataGridTextColumn
или даже Tag
имущество.
Изменить: Пример с прикрепленным свойством:
<DataGrid ...>
<DataGrid.Resources>
<ControlTemplate TargetType="DataGridCell" x:Key="TextAndImageDataGridCellTemplate">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition/>
<ColumnDefinition Width="16"/>
</Grid.ColumnDefinitions>
<ContentPresenter ContentSource="Content"/>
<Image Source="{Binding Column.(local:GridColumnProperties.ImageSource), RelativeSource={RelativeSource TemplatedParent}}" Grid.Column="1"/>
</Grid>
</ControlTemplate>
</DataGrid.Resources>
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding LastName}"
local:GridColumnProperties.ImageSource="/Images/Homer.jpg">
<DataGridTextColumn.CellStyle>
<Style TargetType="DataGridCell">
<Setter Property="Template" Value="{StaticResource TextAndImageDataGridCellTemplate}"/>
</Style>
</DataGridTextColumn.CellStyle>
</DataGridTextColumn>
</DataGrid.Columns>
</DataGrid>
Код:
public static class GridColumnProperties
{
public static readonly DependencyProperty ImageSourceProperty = DependencyProperty.RegisterAttached("ImageSource", typeof(ImageSource), typeof(GridColumnProperties), new PropertyMetadata());
public static void SetImageSource(DependencyObject obj, ImageSource value)
{
obj.SetValue(ImageSourceProperty, value);
}
public static ImageSource GetImageSource(DependencyObject obj)
{
return obj.GetValue(ImageSourceProperty) as ImageSource;
}
}
Создайте проект библиотеки, добавьте код и разметку, а также ссылку на эту новую DLL из проектов.