ContentTemplate Обязательный вопрос
В моем приложении есть элемент управления DataGrid из WPF Toolkit. Мне нужно заменить TextBlock по умолчанию, используемый для ячеек с настроенным TextBlock. XAML-код выглядит примерно так:
<Window.Resources>
<Style x:Key="cellStyle" TargetType="{x:Type tk:DataGridCell}">
<Setter Property="ContentTemplate">
<Setter.Value>
<DataTemplate>
<TextBlock Background="Yellow" />
</DataTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
<Grid>
<tk:DataGrid
ItemsSource="{Binding Path=Products}"
CellStyle="{StaticResource cellStyle}"
AutoGenerateColumns="False">
<tk:DataGrid.Columns>
<tk:DataGridTextColumn
Header="Id"
Binding="{Binding Path=Id}"/>
<tk:DataGridTextColumn
Header="Product"
Binding="{Binding Path=Name}"/>
</tk:DataGrid.Columns>
</tk:DataGrid>
</Grid>
После замены TextBlock вся привязка данных теряется и все ячейки пусты. Добавление свойства Text="{Binding}" в новый TextBlock не помогает. В этом случае все ячейки содержат имя типа DataGridTestApp.Product. Какое будет правильное связующее выражение для TextBlock?
PS На всякий случай: код для MainWindowViewModel
internal sealed class MainWindowViewModel
{
public MainWindowViewModel()
{
_products = new ObservableCollection<Product>()
{
new Product(1, "ProductName1"),
new Product(2, "ProductName2"),
new Product(3, "ProductName3"),
new Product(4, "ProductName4"),
new Product(5, "ProductName5"),
};
}
public ObservableCollection<Product> Products
{
get { return _products; }
}
private ObservableCollection<Product> _products;
}
2 ответа
Если вы посмотрите на исходный код Toolkit, вы найдете существующий стиль для ячейки сетки данных (для отображения столбца используется предъявитель содержимого)
<Style x:Key="{x:Type dg:DataGridCell}" TargetType="{x:Type dg:DataGridCell}">
<Setter Property="Background" Value="Transparent" />
<Setter Property="BorderBrush" Value="Transparent" />
<Setter Property="BorderThickness" Value="1" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type dg:DataGridCell}">
<Border Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
SnapsToDevicePixels="True">
<ContentPresenter SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"/>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" />
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.HighlightTextBrushKey}}" />
<Setter Property="BorderBrush" Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" />
</Trigger>
<Trigger Property="IsKeyboardFocusWithin" Value="True">
<Setter Property="BorderBrush" Value="{DynamicResource {x:Static dg:DataGrid.FocusBorderBrushKey}}" />
</Trigger>
</Style.Triggers>
</Style>
Чтобы получить ваш желтый фон, я бы просто заменил
<Setter Property="Background" Value="Transparent" />
с
<Setter Property="Background" Value="Yellow" />
Если вы отчаянно пытаетесь переопределить TextBlock внутри, используйте шаблон выше, но добавьте его только внутри границы.
<Border.Resources>
<Style TargetType="{x:Type TextBlock}">
<Setter Property="Margin" Value="0,5" />
<Setter Property="Background" Value="Yellow" />
</Style>
</Border.Resources>
Контекст данных TextBlock является продуктом. Если это название продукта, который вы хотите отобразить, используйте это:
<Window.Resources>
<Style x:Key="cellStyle" TargetType="{x:Type tk:DataGridCell}">
<Setter Property="ContentTemplate">
<Setter.Value>
<DataTemplate>
<TextBlock Background="Yellow" Text="{Binding Name}" />
</DataTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
К сожалению, если вы переопределите шаблон, вы потеряете все привязки, установленные в DataGridTextColumn.