Set IsMouseOver property for the entire control and not on the DrawingData

1.9k Views Asked by At

I am drawing a triangle using a Path, and the IsMouseOver property is true only if the mouse pointer is over the triangle. I would like it to be True also when the pointer is over the background of path (transparent). How can I obtain this result?

<!-- language: lang-xml -->
<Style TargetType="{x:Type Path}">
    <Setter Property="Stretch" Value="Uniform"/>
    <Setter Property="Fill" Value="#FF9C9C9C"/>
    <Setter Property="Cursor" Value="Hand"/>
    <Style.Triggers>
        <Trigger Property="IsMouseOver" Value="True">
            <Setter Property="Fill" Value="#FFBDBDBD"/>
            <Setter Property="Effect">
                <Setter.Value>
                    <DropShadowEffect x:Name="DropShadowEffect" BlurRadius="12" Color="#FF9C9C9C" ShadowDepth="0"/>
                </Setter.Value>
            </Setter>
        </Trigger>
    </Style.Triggers>
</Style>

<Path Margin="6,0,0,0" StrokeThickness="0" Width="35" Height="17" Data="M0,0 L8,5, 0,10 Z"/>
3

There are 3 best solutions below

5
On BEST ANSWER

Perhaps you have not asked the correct question? You showed your code (which works just fine) and said

I would like [the IsMouseOver property to be] True also when the pointer is over the background of path

The IsMouseOver property is true when you put the mouse over the centre (where the Background is) of the Path. However, your title says

Set IsMouseOver property for the entire control and not on the DrawingData

which is of course, something very different (and a good reason to read over your question before posting it). If you want to have the Path.Effect change when you put your mouse over the entire control then you simply have to write a Style that accesses that control instead. Again, you failed to let us know what type that control might be, so I'll just assume that it is a Window. Try this:

<Style TargetType="{x:Type Path}">
    <Setter Property="Stretch" Value="Uniform"/>
    <Setter Property="Fill" Value="#FF9C9C9C"/>
    <Setter Property="Cursor" Value="Hand"/>
    <Style.Triggers>
        <DataTrigger Binding="{Binding IsMouseOver, RelativeSource={RelativeSource 
            AncestorType={x:Type Window}}}" Value="True">
            <Setter Property="Fill" Value="#FFBDBDBD"/>
            <Setter Property="Effect">
                <Setter.Value>
                    <DropShadowEffect x:Name="DropShadowEffect" BlurRadius="12" 
                        Color="#FF9C9C9C" ShadowDepth="0"/>
                </Setter.Value>
            </Setter>
        </DataTrigger>
    </Style.Triggers>
</Style>

If that is still not what you're after, then perhaps it would be an idea to be more specific about what you do want.


UPDATE >>>

Now that you've explained that the Path is in a Button, I can suggest that you simply add a Style for the Button to change the Cursor:

<Style TargetType="{x:Type Button}">
    <Style.Triggers>
        <Trigger Property="IsMouseOver" Value="True">
            <Setter Property="Cursor" Value="Hand" />
        </Trigger>
    </Style.Triggers>
</Style>
0
On

One way is to place a border around the path, and then bind to the border's IsMouseOver property instead of the path's. For this to work, the border's background has to be explicitly set to "Transparent" (or whatever color you like).

Place a border around the path:

<Border x:Name="Border" Background="Transparent" Margin="6,0,0,0" Width="17" Height="17">
    <Path StrokeThickness="0" Data="M0,0 L8,5, 0,10 Z"/>
</Border>

Then bind to the border's IsMouseOver property instead of the path's:

<DataTrigger Binding="{Binding IsMouseOver, ElementName=Border}" Value="True">
0
On

Since path is a kind of shape so the drawn shape is the region which triggers mouse move all other events are passed to the control below

I tried to achieve the same using a different approach

style

    <Style TargetType="{x:Type ContentControl}" x:Key="icon">
        <Setter Property="Background" Value="#FF9C9C9C"/>
        <Setter Property="Cursor" Value="Hand"/>
        <Setter Property="Template" >
            <Setter.Value>
                <ControlTemplate TargetType="ContentControl">
                    <Border Background="Transparent">
                        <Path Stretch="Uniform" Fill="{TemplateBinding Background}" Margin="6,0,0,0" StrokeThickness="0" Data="{Binding Content, RelativeSource={RelativeSource TemplatedParent}}"/>
                    </Border>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
        <Style.Triggers>
            <Trigger Property="IsMouseOver" Value="True">
                <Setter Property="Background" Value="#FFBDBDBD"/>
                <Setter Property="Effect">
                    <Setter.Value>
                        <DropShadowEffect x:Name="DropShadowEffect" BlurRadius="12" Color="#FF9C9C9C" ShadowDepth="0"/>
                    </Setter.Value>
                </Setter>
            </Trigger>
        </Style.Triggers>
    </Style>

usage

    <ContentControl Style="{StaticResource icon}" Width="35" Height="17" Content="M0,0 L8,5, 0,10 Z"/>

in the style above i add a border with transparent background which effectively creates a transparent region for mouse events thus will be able to capture mouse move over full control