如何删除WPF按钮上的默认鼠标悬停效果?


84

我的问题是,在WPF中,每当我尝试使用触发器或动画来更改按钮背景的颜色时,默认的鼠标悬停效果(灰色和橙色发光效果)似乎都优先。

经过广泛的搜索,我对如何消除这种影响一无所知。

Answers:


17

您需要创建自己的自定义按钮模板,以完全控制所有状态下的外观。这是一个教程


2
谢谢,那太完美了。这比我想象的要复杂得多,但是现在一切正常。
Nellius

18
出于某种原因,关于为WPF控件创建自定义模板有100个答案,它们都是不必要的错误。没有理由为一个按钮编写50行模板代码来更改1件事。您所要做的就是在xaml设计器中右键单击该控件并创建模板代码的副本。VS将从该确切的按钮创建样式,您可以从那里进行调整。实际需要2秒。
松饼人

@TheMuffinMan太棒了,但是您发现它需要50行模板代码来阻止按钮更改鼠标悬停时的背景颜色,这还有些奇怪吗?多么复杂的WPF框架是多么愚蠢的事情。
Ash Ash

@Ash或有人可能会争辩说它在指导用户走的方向。如果您的按钮需要新的悬停状态,则可能是新的TYPE按钮;可能是导航按钮,任务栏按钮等。如果是这样,则不应为它修改一次性属性,它应该具有自己的控件或样式组。这就是您要做的事情。
Matt Kenefick

107

这类似于Mark Heath提到的解决方案,但是没有太多的代码来创建一个非常基本的按钮,而没有内置的鼠标悬停在动画效果上。它保留了将鼠标边框显示为黑色的简单鼠标悬停效果。

例如,可以将样式插入Window.Resources或UserControl.Resources部分(如图所示)。

<UserControl.Resources>
    <!-- This style is used for buttons, to remove the WPF default 'animated' mouse over effect -->
    <Style x:Key="MyButtonStyle" TargetType="Button">
        <Setter Property="OverridesDefaultStyle" Value="True"/>
        <Setter Property="Margin" Value="5"/>
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="Button">
                    <Border Name="border" 
                        BorderThickness="1"
                        Padding="4,2" 
                        BorderBrush="DarkGray" 
                        CornerRadius="3" 
                        Background="{TemplateBinding Background}">
                        <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center" />
                    </Border>
                    <ControlTemplate.Triggers>
                        <Trigger Property="IsMouseOver" Value="True">
                            <Setter TargetName="border" Property="BorderBrush" Value="Black" />
                        </Trigger>
                    </ControlTemplate.Triggers>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>
</UserControl.Resources>

<!-- usage in xaml -->
<Button Style="{StaticResource MyButtonStyle}">Hello!</Button>

2
我非常喜欢这种解决方案。但是,仅当鼠标悬停在按钮上的文本上方时,鼠标悬停触发器才会激活。我在按钮内添加了具有指定宽度的文本块,以解决该问题。
戴夫

先生,你是圣人。
krobelusmeetsyndra

25

只是添加一个非常简单的解决方案,对我来说已经足够了,我认为可以解决OP的问题。我在此答案中使用了解决方案但使用的是常规Background值而不是图像。

<Style x:Key="SomeButtonStyle" TargetType="Button">
    <Setter Property="Background" Value="Transparent" />
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="Button">
                <Grid Background="{TemplateBinding Background}">
                    <ContentPresenter />
                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

除了强制模板按钮Background始终将其作为Transparent背景外,没有其他重新模板化的操作-完成此操作后,鼠标悬停不再影响背景。显然替换Transparent为任何首选值。


10

松饼人有一个非常简单的答案,对我有用。

要添加更具体的方向,至少对于VS 2013:

  • 右键单击控件
  • 选择编辑模板=>编辑副本...
  • 我选择了“应用程序”作为样式保存位置
    • 在这里,您可以直接编辑App.xaml并查看直观命名的属性。为了我的目的,我只设置了RenderMouseOver =“ False”
  • 然后,在MainWindow.xaml或您的GUI所在的任何位置,都可以将新样式粘贴到Button标记的末尾,例如 ... Style="{DynamicResource MouseOverNonDefault}"/>

谁是松饼人?
Mike W

大声笑。他对问题所有者接受的答案进行了第二次答复。不确定您是在认真询问还是在开玩笑。像松饼人这样的名字很难说。
Benji-Man

5

此链接帮助我很多 http://www.codescratcher.com/wpf/remove-default-mouse-over-effect-on-wpf-buttons/

UserControl.ResourcesWindow.Resources中定义样式

 <Window.Resources>
        <Style x:Key="MyButton" TargetType="Button">
            <Setter Property="OverridesDefaultStyle" Value="True" />
            <Setter Property="Cursor" Value="Hand" />
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="Button">
                        <Border Name="border" BorderThickness="0" BorderBrush="Black" Background="{TemplateBinding Background}">
                            <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center" />
                        </Border>
                        <ControlTemplate.Triggers>
                            <Trigger Property="IsMouseOver" Value="True">
                                <Setter Property="Opacity" Value="0.8" />
                            </Trigger>
                        </ControlTemplate.Triggers>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>
    </Window.Resources>

然后通过Style =“ {StaticResource MyButton}”将样式添加到您的按钮中

<Button Name="btnSecond" Width="350" Height="120" Margin="15" Style="{StaticResource MyButton}">
    <Button.Background>
        <ImageBrush ImageSource="/Remove_Default_Button_Effect;component/Images/WithStyle.jpg"></ImageBrush>
    </Button.Background>
</Button>

4

如果有人不想覆盖默认的控制模板,那么这里就是解决方案。

您可以为具有TextBlock的按钮创建DataTemplate,然后可以在IsMouseOver属性上编写属性触发器以禁用鼠标悬停效果。TextBlock和Button的高度应相同。

<Button Background="Black" Margin="0" Padding="0" BorderThickness="0" Cursor="Hand" Height="20">
    <Button.ContentTemplate>
        <DataTemplate>
            <TextBlock Text="GO" Foreground="White" HorizontalAlignment="Center" VerticalAlignment="Center" TextDecorations="Underline" Margin="0" Padding="0" Height="20">
                <TextBlock.Style>
                    <Style TargetType="TextBlock">
                        <Style.Triggers>
                            <Trigger Property ="IsMouseOver" Value="True">
                                <Setter Property= "Background" Value="Black"/>
                            </Trigger>
                        </Style.Triggers>
                    </Style>
                </TextBlock.Style>
            </TextBlock>
        </DataTemplate>
    </Button.ContentTemplate>
</Button>

1

对dodgy_coder的答案的扩展,增加了对...的支持。

  • 保持WPF按钮样式
  • 添加对IsSelected和悬停的支持,即切换按钮

        <Style x:Key="Button.Hoverless" TargetType="{x:Type ButtonBase}">
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="{x:Type ButtonBase}">
                        <Border Name="border"
                                BorderThickness="{TemplateBinding BorderThickness}"
                                Padding="{TemplateBinding Padding}"
                                BorderBrush="{TemplateBinding BorderBrush}"
                                Background="{TemplateBinding Background}">
                            <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center" />
                        </Border>
                        <ControlTemplate.Triggers>
                            <MultiTrigger>
                                <MultiTrigger.Conditions>
                                    <Condition Property="IsMouseOver" Value="True" />
                                    <Condition Property="Selector.IsSelected" Value="False" />
                                </MultiTrigger.Conditions>
                                <Setter Property="Background" Value="#FFBEE6FD" />
                            </MultiTrigger>
    
                            <MultiTrigger>
                                <MultiTrigger.Conditions>
                                    <Condition Property="IsMouseOver" Value="True" />
                                    <Condition Property="Selector.IsSelected" Value="True" />
                                </MultiTrigger.Conditions>
                                <Setter Property="Background" Value="#BB90EE90" />
                            </MultiTrigger>
    
                            <MultiTrigger>
                                <MultiTrigger.Conditions>
                                    <Condition Property="IsMouseOver" Value="False" />
                                    <Condition Property="Selector.IsSelected" Value="True" />
                                </MultiTrigger.Conditions>
                                <Setter Property="Background" Value="LightGreen" />
                            </MultiTrigger>
    
                            <Trigger Property="IsPressed" Value="True">
                                <Setter TargetName="border" Property="Opacity" Value="0.95" />
                            </Trigger>
                        </ControlTemplate.Triggers>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>
    

例子..

<Button Content="Wipe On" Selector.IsSelected="True" /> <Button Content="Wipe Off" Selector.IsSelected="False" />


0

使用模板触发器:

<Style x:Key="ButtonStyle" TargetType="{x:Type Button}">
    <Setter Property="Background" Value="White"></Setter>
    ...
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type Button}">
                <Border Background="{TemplateBinding Background}">
                    <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center"/>
                </Border>
                <ControlTemplate.Triggers>
                    <Trigger Property="IsMouseOver" Value="True">
                        <Setter Property="Background" Value="White"/>
                    </Trigger>
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.