WPF Styling DataGrid header

167 views Asked by At

Good day, collegues. My previous developer was modified default DataGridColumnHeadersPresenter. In result this modified style is now allaying to all DataGrid in solution.

Now I have got task from team leader to implement filter in DataGrid header. I've created my own style for DataGridColumnHeader but it doesn't work. Here it is:

<Style TargetType="{x:Type DataGridColumnHeader}" x:Key="FiltrableHeader"  >

        <Setter Property="VerticalAlignment" Value="Center"></Setter>
        <Setter Property="BorderBrush" Value="Transparent"/>
        <Setter Property="BorderThickness" Value="0"/>
        <Setter Property="Background" Value="Red"/>
        <Setter Property="SeparatorBrush" Value="{DynamicResource Pallete.Secondary.Darkest}"/>
        <Setter Property="Margin" Value="0,0,2,2"/>
        <Setter Property="Template">

            <Setter.Value>
                <ControlTemplate>
                    <ControlTemplate.Resources>
                        <Storyboard x:Key="ShowFilterControl">
                            <ObjectAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="filterTextBox" Storyboard.TargetProperty="(UIElement.Visibility)">
                                <DiscreteObjectKeyFrame KeyTime="00:00:00" Value="{x:Static Visibility.Visible}"/>
                                <DiscreteObjectKeyFrame KeyTime="00:00:00.5000000" Value="{x:Static Visibility.Visible}"/>
                            </ObjectAnimationUsingKeyFrames>
                            <ColorAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="filterTextBox" Storyboard.TargetProperty= "(Panel.Background).(SolidColorBrush.Color)">
                                <SplineColorKeyFrame KeyTime="00:00:00"  Value="Transparent"/>
                                <SplineColorKeyFrame  KeyTime="00:00:00.5000000" Value="White"/>
                            </ColorAnimationUsingKeyFrames>
                        </Storyboard>
                        <Storyboard x:Key="HideFilterControl">
                            <ObjectAnimationUsingKeyFrames BeginTime="00:00:00" Storyboard.TargetName="filterTextBox" Storyboard.TargetProperty="(UIElement.Visibility)">
                                <DiscreteObjectKeyFrame KeyTime="00:00:00.4000000" Value="{x:Static Visibility.Collapsed}"/>
                            </ObjectAnimationUsingKeyFrames>
                            <ColorAnimationUsingKeyFrames BeginTime="00:00:00"  Storyboard.TargetName="filterTextBox" Storyboard.TargetProperty= "(UIElement.OpacityMask).(SolidColorBrush.Color)">
                                <SplineColorKeyFrame KeyTime="00:00:00" Value="Black"/>
                                <SplineColorKeyFrame  KeyTime="00:00:00.4000000" Value="#00000000"/>
                            </ColorAnimationUsingKeyFrames>
                        </Storyboard>
                    </ControlTemplate.Resources>
                    <Grid x:Name="grid" Width="Auto"  Height="Auto" RenderTransformOrigin="0.5,0.5">
                        <Grid.RenderTransform>
                            <TransformGroup>
                                <ScaleTransform/>
                                <SkewTransform/>
                                <RotateTransform/>
                                <TranslateTransform/>
                            </TransformGroup>
                        </Grid.RenderTransform>
                        <Grid.ColumnDefinitions>
                            <ColumnDefinition Width="*"/>
                        </Grid.ColumnDefinitions>
                        <StackPanel Height="50" >
                            <ContentPresenter x:Name="contentPresenter"
                                 HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
                                 VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
                                 SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" >
                                <ContentPresenter.Content>
                                    <MultiBinding Converter="{StaticResource headerConverter}">
                                        <MultiBinding.Bindings>
                                            <Binding ElementName="filterTextBox"  Path="Text" />
                                            <Binding RelativeSource="{RelativeSource TemplatedParent}" Path="Content" />
                                        </MultiBinding.Bindings>
                                    </MultiBinding>
                                </ContentPresenter.Content>
                            </ContentPresenter>
                            <TextBox x:Name="filterTextBox"
                                    MinWidth="25" Height="23" OpacityMask="Black" Padding="3"  Margin="3 0"
                                    Visibility="Collapsed" TextWrapping="Wrap"
                                    Grid.Column="0"
                                    Grid.ColumnSpan="1"/>
                        </StackPanel>
                    </Grid>
                    <ControlTemplate.Triggers>
                        <Trigger Property="IsMouseOver" Value="True">
                            <Trigger.EnterActions>
                                <BeginStoryboard x:Name="ShowFilterControl_BeginStoryboard" Storyboard="{StaticResource ShowFilterControl}"/>
                                <StopStoryboard BeginStoryboardName="HideFilterControl_BeginShowFilterControl"/>
                            </Trigger.EnterActions>
                            <Trigger.ExitActions>
                                <BeginStoryboard x:Name="HideFilterControl_BeginShowFilterControl"  Storyboard="{StaticResource HideFilterControl}"/>
                                <StopStoryboard BeginStoryboardName="ShowFilterControl_BeginStoryboard"/>
                            </Trigger.ExitActions>
                        </Trigger>
                    </ControlTemplate.Triggers>
                </ControlTemplate>
            </Setter.Value>

        </Setter>
    </Style>

And when I use this style in my XAML on DataGrid :

<c:FilteringDataGrid
    ItemsSource="{Binding Coefficients}"
    Style="{StaticResource DataGridStyle}"
    CanUserAddRows="False"
    CanUserDeleteRows="False"
    CanUserSortColumns="False"
    SelectionMode="Single"
    AutoGenerateColumns="True"
    ColumnHeaderStyle="{StaticResource FiltrableHeader}"
>

only height of header is set to 50 (defined in style).

Where I'm wrong? How to override default DataGridColumnHeadersPresenter? If I put all my style settings in DataGridColumnHeadersPresenter all works fine, but on all DataGrids in solution.

Thank you!

1

There are 1 answers

1
mm8 On

How to "override" the style that is currently being applied depends on how DataGridStyle is defined.

If I put all my style settings in DataGridColumnHeadersPresenter all works fine, but on all DataGrids in solution.

You could then create a copy of DataGridStyle and add an x:Key to it along with your DataGridColumnHeader style:

<Style x:Key="CopyOfDataGridStyle" TargetType="..." />

You would then assign the Style property of this particular DataGrid to the new Style

<c:FilteringDataGrid
    ItemsSource="{Binding Coefficients}"
    Style="{StaticResource CopyOfDataGridStyle}" ... />

Then it won't affect any other DataGrid controls in your application.