📜  鼠标悬停时的wpf发光图像-任何(1)

📅  最后修改于: 2023-12-03 14:58:53.721000             🧑  作者: Mango

实现鼠标悬停时的 WPF 发光图像

在 WPF 中,我们可以使用多种方式为控件添加一些视觉效果以提升用户体验。其中一种较为常见且较为简单的方式是:在鼠标悬停时为控件添加一些发光效果。

本篇文章将会介绍如何实现一个简单的发光效果以及如何为其添加更多的自定义配置项。

代码实现

下面是一个简单的鼠标悬停时发光的 WPF 控件:

<Grid>
    <Border x:Name="border" Background="White" CornerRadius="5" BorderBrush="Gray" BorderThickness="1" Padding="10">
        <TextBlock Text="Hello World!"/>
    </Border>
</Grid>

为了实现鼠标悬停时的发光效果,我们需要使用一个 Trigger 来监听鼠标的悬停事件并在触发时修改 Border 的背景颜色。

具体来讲,我们需要为 Border 添加一个 Trigger,它将会在鼠标进入 Border 区域时触发。在 Trigger 中,我们可以使用 Setter 来设置 Border 的 Background 属性。由于我们想要实现发光效果,我们需要使用 Brush 类型中的 LinearGradientBrush,并且将其 SpreadMethod 属性设置为 Reflect。

最终代码如下所示:

<Grid>
    <Border x:Name="border" Background="White" CornerRadius="5" BorderBrush="Gray" BorderThickness="1" Padding="10">
        <Border.Triggers>
            <Trigger Property="IsMouseOver" Value="True">
                <Setter Property="Background">
                    <Setter.Value>
                        <LinearGradientBrush StartPoint="0.5,0" EndPoint="0.5,1" SpreadMethod="Reflect">
                            <GradientStop Offset="0.3" Color="Transparent"/>
                            <GradientStop Offset="0.7" Color="White"/>
                            <GradientStop Offset="1.0" Color="Transparent"/>
                        </LinearGradientBrush>
                    </Setter.Value>
                </Setter>
            </Trigger>
        </Border.Triggers>
        <TextBlock Text="Hello World!"/>
    </Border>
</Grid>
自定义配置项

上述代码中的发光效果是一种比较简单的实现方式。如果需要更多的自定义配置项,比如调整光晕的强度、颜色、位置等,我们可以将发光效果封装成一个自定义控件。

下面是一个稍微复杂一些的实现方式:

先定义一个叫做 GlowBorder 的控件,它继承自 Border,可以接受一系列自定义配置项。

public class GlowBorder : Border
{
    // 光晕颜色
    public Brush GlowColor
    {
        get { return (Brush)GetValue(GlowColorProperty); }
        set { SetValue(GlowColorProperty, value); }
    }

    public static readonly DependencyProperty GlowColorProperty =
        DependencyProperty.Register("GlowColor", typeof(Brush), typeof(GlowBorder), new PropertyMetadata(Brushes.White));

    // 光晕强度
    public double GlowStrength
    {
        get { return (double)GetValue(GlowStrengthProperty); }
        set { SetValue(GlowStrengthProperty, value); }
    }

    public static readonly DependencyProperty GlowStrengthProperty =
        DependencyProperty.Register("GlowStrength", typeof(double), typeof(GlowBorder), new PropertyMetadata(1.0, OnGlowStrengthChanged));

    // 光晕位置
    public Thickness GlowMargin
    {
        get { return (Thickness)GetValue(GlowMarginProperty); }
        set { SetValue(GlowMarginProperty, value); }
    }

    public static readonly DependencyProperty GlowMarginProperty =
        DependencyProperty.Register("GlowMargin", typeof(Thickness), typeof(GlowBorder), new PropertyMetadata(new Thickness(0)));

    private static void OnGlowStrengthChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        var border = (GlowBorder)d;
        var strength = (double)e.NewValue;
        var brush = (LinearGradientBrush)border.FindResource("GlowBrush");

        brush.GradientStops[0].Offset = (1 - strength) / 2;
        brush.GradientStops[2].Offset = (1 + strength) / 2;

        border.InvalidateVisual();
    }
}

通过上述代码,我们为控件添加了三个自定义配置项:GlowColor(光晕颜色)、GlowStrength(光晕强度)和 GlowMargin(光晕位置)。同时,在 GlowStrength 属性值变化时,我们会修改 LinearGradientBrush 的 GradientStops 属性。

最后,我们需要为控件设置模板(Template)。

<Grid.Resources>
    <LinearGradientBrush x:Key="GlowBrush" StartPoint="0.5,0" EndPoint="0.5,1" SpreadMethod="Reflect">
        <GradientStop Offset="0.3" Color="Transparent"/>
        <GradientStop Offset="0.7" Color="{Binding RelativeSource={RelativeSource TemplatedParent}, Path=GlowColor}"/>
        <GradientStop Offset="1.0" Color="Transparent"/>
    </LinearGradientBrush>
    <Style TargetType="{x:Type local:GlowBorder}">
        <Setter Property="Background" Value="White"/>
        <Setter Property="BorderBrush" Value="Gray"/>
        <Setter Property="BorderThickness" Value="1"/>
        <Setter Property="Padding" Value="10"/>
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type local:GlowBorder}">
                    <Grid>
                        <Border x:Name="border" Background="{TemplateBinding Background}" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Padding="{TemplateBinding Padding}" CornerRadius="{TemplateBinding CornerRadius}"/>
                        <Border x:Name="glow" Background="{StaticResource GlowBrush}" BorderThickness="0" Margin="{TemplateBinding GlowMargin}" CornerRadius="{TemplateBinding CornerRadius}"/>
                        <ContentPresenter/>
                    </Grid>
                    <ControlTemplate.Triggers>
                        <Trigger Property="IsMouseOver" Value="True">
                            <Setter TargetName="glow" Property="Opacity" Value="1"/>
                        </Trigger>
                        <Trigger Property="IsMouseOver" Value="False">
                            <Setter TargetName="glow" Property="Opacity" Value="0"/>
                        </Trigger>
                    </ControlTemplate.Triggers>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>
</Grid.Resources>

在上述代码中,我们定义了一个 LinearGradientBrush 的资源(GlowBrush),并将它用作光晕层的背景。同时,我们在控件模板中添加了一个光晕层,并将它的背景设置为 GlowBrush。

在触发 IsMouseOver 事件时,我们会修改光晕层的 Opacity 属性以显示或隐藏光晕层。

最后,我们只需要将之前的 Border 改成 GlowBorder 即可:

<Grid>
    <local:GlowBorder x:Name="border" Background="White" CornerRadius="5" BorderBrush="Gray" BorderThickness="1" Padding="10" GlowColor="Red" GlowStrength="0.5" GlowMargin="-5">
        <TextBlock Text="Hello World!"/>
    </local:GlowBorder>
</Grid>

我们还为 GlowBorder 的属性 GlowColor、GlowStrength 和 GlowMargin 提供了一些默认值,以便在使用时可以不必手动设置。

总结

至此,我们已经学会了如何实现一个简单的 WPF 发光效果,以及如何为其添加自定义配置项。

当然,以上代码只是一种比较简单的实现方式。如果有更高级、更灵活的实现方式,也可以在此基础上进行进一步的扩展和优化。