WPF 可动画按钮






4.80/5 (9投票s)
一个按钮,消除了为定义按钮状态变化故事板而使用触发器的需要。
引言
本文介绍如何简化定义按钮鼠标悬停、按下、启用和禁用动画的过程。 当包含所有 IsMouseOver、IsPressed 和 IsEnabled 状态时,定义触发器的过程非常复杂。 您还需要努力精确地定义 BeginStoryboard/StopStoryboard,才能启动所需的动画。 其中一些状态是重叠的。 例如,当按钮处于 IsPressed 状态时,它很可能也处于 IsMouseOver 状态,这会导致动画行为不正确。 每次为这种常见问题定义所有这些复杂的触发器也令人烦恼。
解决方案
我定义了一个新的控件 - AnimatableButton,它继承自标准的 WPF Button。 这个新的 AnimatableButton 监听按钮的状态变化,查找相应的动画,并运行它。 您需要做的就是定义具有预定义名称的故事板 - “NormalAnimation”、“MouseOverAnimation”、“PressedAnimation” 或 “DisabledAnimation”。 您可以将它们定义在按钮的资源字典或模板中。 这就是您需要做的全部。 AnimatableButton 会为您完成剩下的工作。
选择运行哪个动画的逻辑位于 GetAnimationName 方法中
protected virtual string GetCurrentAnimationName()
{
   switch (State)
   {
      case ButtonState.Normal:
         return "NormalAnimation";
      case ButtonState.MouseOver:
         return "MouseOverAnimation";
      case ButtonState.Pressed:
         return "PressedAnimation";
      case ButtonState.Disabled:
         return "DisabledAnimation";
      default:
         return string.Empty;
   }
}
如您所见,此方法是 virtual,这意味着您可以扩展 AnimatableButton 并覆盖其功能。 这将允许您根据 IsMouseOver、IsPressed 和 IsEnabled 以外的状态运行动画。 您还可以通过调用 InvalidateAnimation() 强制按钮更新其视觉状态。 后者将根据 GetAnimationName 方法运行动画。
该按钮还公开其 State。 这是一个枚举,具有以下值:Normal、MouseOver、Pressed 和 Disabled。 您可以使用它来满足自己的需求。
使用示例
下面是一个具有模板和动画定义的按钮示例。 请注意,没有定义任何触发器。
<common:AnimatableButton >
  <common:AnimatableButton.Style>
    <Style TargetType="{x:Type common:AnimatableButton}">
      <Style.Setters>
        <Setter Property="Template">
          <Setter.Value>
            <ControlTemplate TargetType="{x:Type common:AnimatableButton}">
              <Border>
                <Border.Background>
                  <SolidColorBrush x:Name="bg" />
                </Border.Background>
                <ContentPresenter />
              </Border>
              <ControlTemplate.Resources>
                <Storyboard x:Key="NormalAnimation">
                  <ColorAnimation To="Yellow" Duration="0:0:0.200" 
                    Storyboard.TargetName="bg" 
                    Storyboard.TargetProperty="Color" />
                </Storyboard>
                <Storyboard x:Key="MouseOverAnimation">
                  <ColorAnimation To="Red" Duration="0:0:0.200" 
                    Storyboard.TargetName="bg" 
                    Storyboard.TargetProperty="Color" />
                </Storyboard>
                <Storyboard x:Key="PressedAnimation">
                  <ColorAnimation To="Blue" Duration="0:0:0.200" 
                    Storyboard.TargetName="bg" 
                    Storyboard.TargetProperty="Color" />
                </Storyboard>
                <Storyboard x:Key="DisabledAnimation">
                  <ColorAnimation To="DarkGray" Duration="0:0:0.200" 
                    Storyboard.TargetName="bg" 
                    Storyboard.TargetProperty="Color" />
                </Storyboard>
              </ControlTemplate.Resources>
            </ControlTemplate>
          </Setter.Value>
        </Setter>
      </Style.Setters>
    </Style>
  </common:AnimatableButton.Style>
</common:AnimatableButton>
Origin
本文的原始出处可以在 WPF Animatable Button 找到。


