views:

280

answers:

2

The normal convention for UI controls is for selected text, items, or rows to be brightly colored (e.g., bright blue) when the parent control is in focus and desaturated/dim (e.g., pale blue) when the control is out of focus.

In contrast to the ListView/GridView, the WPF DataGrid control does not follow this convention by default. Selected rows appear bright even if another control on in the same window is clearly in focus.

I think this should just be a matter of adding a trigger to the DataGridCell that sets the background to {DynamicResource {x:Static SystemColors.ControlBrushKey}} if the DataGrid is out of focus, but I can't figure out which property to check. IsFocused sounded like what I want, but that doesn't work. IsMouseCaptured doesn't seem to work either.

Here's the latest trigger I tried:

<MultiDataTrigger>
    <MultiDataTrigger.Conditions>
        <Condition
            Binding="{Binding IsSelected}"
            Value="True" />
        <Condition
            Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wt:DataGrid}, Path=IsFocused}"
            Value="False"/>
    </MultiDataTrigger.Conditions>
    <Setter
        Property="BorderBrush"
        Value="{DynamicResource {x:Static SystemColors.ControlBrushKey}}" />
    <Setter
        Property="Background"
        Value="{DynamicResource {x:Static SystemColors.ControlBrushKey}}" />
    <Setter
        Property="Foreground"
        Value="Gray" />
</MultiDataTrigger>

What can I do to make this trigger dim the cell when the cell is selected and the parent control is not in focus?

A: 

Pulling from a bit of my code: This is the trigger for a treeview items background when the treeview is out of focus.

                        <MultiTrigger>
                            <MultiTrigger.Conditions>
                                <Condition Property="IsSelected" Value="true"/>
                                <Condition Property="IsSelectionActive" Value="false"/>
                            </MultiTrigger.Conditions>
                            <Setter Property="Background" TargetName="SelectBorder">
                                <Setter.Value>
                                    <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
                                        <GradientStop Color="#939F90" Offset="0"/>
                                        <GradientStop Color="#BCC4BA" Offset="1"/>
                                    </LinearGradientBrush>
                                </Setter.Value>
                            </Setter>
                            <Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
                        </MultiTrigger>

I believe the IsSelectionActive is the key condition...

Alastair Pitts
@AP, thanks for the idea, but I get a compiler error ("cannot find the style property 'IsSelectionActive'").
DanM
lemme dig some more, see what else is floating around
Alastair Pitts
I came up with a solution (see my answer) that seems to work. Thanks again for your help.
DanM
A: 

Well, it's a monstrosity, but it seems to work:

<MultiDataTrigger>
    <MultiDataTrigger.Conditions>
        <Condition
            Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wt:DataGridRow}, Path=IsSelected}"
            Value="True" />
        <Condition
            Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wt:DataGrid}, Path=IsKeyboardFocusWithin}"
            Value="True" />
    </MultiDataTrigger.Conditions>
    <Setter
        Property="BorderBrush"
        Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" />
    <Setter
        Property="Background"
        Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" />
    <Setter
        Property="Foreground"
        Value="Black" />
</MultiDataTrigger>
<MultiDataTrigger>
    <MultiDataTrigger.Conditions>
        <Condition
            Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wt:DataGridRow}, Path=IsSelected}"
            Value="True" />
        <Condition
            Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wt:DataGrid}, Path=IsKeyboardFocusWithin}"
            Value="False" />
    </MultiDataTrigger.Conditions>
    <Setter
        Property="BorderBrush"
        Value="{DynamicResource {x:Static SystemColors.ControlBrushKey}}" />
    <Setter
        Property="Background"
        Value="{DynamicResource {x:Static SystemColors.ControlBrushKey}}" />
    <Setter
        Property="Foreground"
        Value="Gray" />
</MultiDataTrigger>
DanM