Reputation: 12338
I want to change the content of a DataGridCell. I have a column in the datagridview like so
<DataGridCheckBoxColumn CellStyle="ChangeContentOfCellSstyle"...
Then I have a DataTrigger like so:
<Style TargetType="DataGridCell" x:Key="ChangeContentOfCellSstyle">
<Style.Triggers>
<DataTrigger Binding="{Binding IsWashed}" Value="True">
<Setter Property="Content" Value="The new value for the cell."/>
<Setter Property="Background" Value="Red"/> //sets the background of the cell to red just to show the trigger is working
</DataTrigger>
</Style.Triggers>
</Style>
But the content of the cell is not changing. Not even when I try the same with a DataGridTextColumn although the cell turns red.
Upvotes: 1
Views: 2521
Reputation: 979
The above did not work in my situation where I wanted to change the cell content based on a property bound to the row. I came up with the following solution.
<DataGridTemplateColumn >
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<ContentPresenter
Style="{StaticResource LockedStyle}" Content="{Binding}">
</ContentPresenter>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
With the following styles in the resource dictionary:
<DataTemplate x:Key="LockedTemplate">
<TextBlock FontFamily="Segoe MDL2 Assets" Text="" ></TextBlock>
</DataTemplate>
<DataTemplate x:Key="UnLockedTemplate">
<TextBlock FontFamily="Segoe MDL2 Assets" Text=""></TextBlock>
</DataTemplate>
<DataTemplate x:Key="NoneTemplate"></DataTemplate>
<Style x:Key="LockedStyle" TargetType="ContentPresenter">
<Setter Property="ContentTemplate" Value="{StaticResource NoneTemplate}"/>
<Style.Triggers>
<DataTrigger Binding="{Binding IsLocked}" Value="true">
<Setter Property="ContentTemplate" Value="{StaticResource LockedTemplate}"/>
</DataTrigger>
<DataTrigger Binding="{Binding IsLocked}" Value="false">
<Setter Property="ContentTemplate" Value="{StaticResource UnLockedTemplate}"/>
</DataTrigger>
</Style.Triggers>
</Style>
Upvotes: 0
Reputation: 309
This answer is really a comment on @Andy's answer. It seems I can't format code in a comment.
Note that you can inline the DataTemplate
definitions in your XAML, to put everything all together in one place.
<local:IsWashedStyleSelector x:Key="isWashedStyleSelector">
<local:IsWashedStyleSelector.TrueStyle>
<DataTemplate>
<Button>It's true</Button>
</DataTemplate>
</local:IsWashedStyleSelector.TrueStyle>
<local:IsWashedStyleSelector.FalseStyle>
<DataTemplate>
<Label>is false</Label>
</DataTemplate>
</local:IsWashedStyleSelector.FalseStyle>
</local:IsWashedStyleSelector>
Of course, this is for when you want to use those DataTemplate
definitions in only the one place.
Upvotes: 0
Reputation: 6466
I've removed my previous answer since using a template selector is a much better way of doing this.
first I create a DataTemplateSelector class that can be used to switch between DataTemplates based on a binding, note the 2 properties that take in references to the styles that will be applied, I could have used find resource here but I think this is cleaner and doesn't require view designers to stick to hard coded template keys.
public class IsWashedStyleSelector : DataTemplateSelector
{
public DataTemplate TrueStyle { get; set; }
public DataTemplate FalseStyle { get; set; }
public override DataTemplate SelectTemplate(object item, DependencyObject container)
{
TestClass targetItem = item as TestClass;
if (targetItem != null)
{
return targetItem.IsWashed ? TrueStyle : FalseStyle;
}
return base.SelectTemplate(item, container);
}
}
Now to use this template selector I have to define 2 data templates and also instance the selector in xaml resources.
<DataTemplate x:Key="styleIsWashedTrue">
<Button>It's true</Button>
</DataTemplate>
<DataTemplate x:Key="styleIsWashedFalse">
<Label>is false</Label>
</DataTemplate>
<local:IsWashedStyleSelector x:Key="isWashedStyleSelector" TrueStyle="{StaticResource styleIsWashedTrue}" FalseStyle="{StaticResource styleIsWashedFalse}"/>
Finally the selector can be used in a DataGridTemplateColumn like so.
<DataGrid ItemsSource="{Binding Items}" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridCheckBoxColumn Binding="{Binding IsWashed}"/>
<DataGridTextColumn Binding="{Binding Text}"/>
<DataGridTemplateColumn CellTemplateSelector="{StaticResource isWashedStyleSelector}"/>
</DataGrid.Columns>
</DataGrid>
Upvotes: 1