使用不同画笔为颜色属性设置动画

时间:2013-10-20 18:30:15

标签: wpf xaml

我在ControlTemplate.Resources中有以下内容:

<ColorAnimation
    Storyboard.TargetName="border"
    Storyboard.TargetProperty="Background.(SolidColorBrush.Color)"
    To="Orange"
    Duration="0:0:0.2" />

如果我想要更改为橙色的原始背景是纯色,它可以正常工作。但是当原始背景为LinearGradientBrush时,我也想要这项工作。在第二种情况下,动画试图徒劳地改变属性,没有任何反应。

我如何指定一个替换背景的动画,无论它是什么类型的?

1 个答案:

答案 0 :(得分:4)

如果您的BackgroundLinearGradientBrush,那么您必须将每个GradientStop设置为您想要的Color动画,例如橙色:

      <Storyboard x:Key="Storyboard1">
        <ColorAnimationUsingKeyFrames Storyboard.TargetProperty="Background.(GradientBrush.GradientStops)[0].(GradientStop.Color)" Storyboard.TargetName="border">
            <EasingColorKeyFrame KeyTime="0:0:2" Value="Orange"/>
        </ColorAnimationUsingKeyFrames>
        <ColorAnimationUsingKeyFrames Storyboard.TargetProperty="Background.(GradientBrush.GradientStops)[1].(GradientStop.Color)" Storyboard.TargetName="border">
            <EasingColorKeyFrame KeyTime="0:0:2" Value="Orange"/>
        </ColorAnimationUsingKeyFrames>
    </Storyboard>

但是,如果您想要Animate整个Brush,无论其类型如何,那么您将不得不创建自己的动画。我已经创建了自己的BrushAnimation类来为画笔设置动画

    public class BrushAnimation : AnimationTimeline
    {
        static BrushAnimation()
        {
            FromProperty = DependencyProperty.Register("From", typeof(Brush),
                typeof(BrushAnimation),new PropertyMetadata(new SolidColorBrush()));

            ToProperty = DependencyProperty.Register("To", typeof(Brush),
                typeof(BrushAnimation), new PropertyMetadata(new SolidColorBrush()));
        }

        public override Type TargetPropertyType
        {
            get
            {
                return typeof(Brush);
            }
        }

        protected override System.Windows.Freezable CreateInstanceCore()
        {
            return new BrushAnimation();
        }

        public static readonly DependencyProperty FromProperty;
        public Brush From
        {
            get
            {
                return (Brush)GetValue(BrushAnimation.FromProperty);
            }
            set
            {
                SetValue(BrushAnimation.FromProperty, value);
            }
        }

        public static readonly DependencyProperty ToProperty;
        public Brush To
        {
            get
            {
                return (Brush)GetValue(BrushAnimation.ToProperty);
            }
            set
            {
                SetValue(BrushAnimation.ToProperty, value);
            }
        }


        public override object GetCurrentValue(object defaultOriginValue,
            object defaultDestinationValue, AnimationClock animationClock)
        {
            Brush fromVal = ((Brush)GetValue(BrushAnimation.FromProperty));
            Brush toVal = ((Brush)GetValue(BrushAnimation.ToProperty));

            SolidColorBrush solid = toVal as SolidColorBrush;

            if(fromVal is LinearGradientBrush)
            {
                LinearGradientBrush brush = fromVal as LinearGradientBrush;
                LinearGradientBrush newBrush = new LinearGradientBrush();
                foreach(var stop in brush.GradientStops)
                {
                    ColorAnimation animation = new ColorAnimation(stop.Color,solid.Color,this.Duration);
                    Color color = animation.GetCurrentValue(stop.Color, solid.Color, animationClock);
                    newBrush.GradientStops.Add(new GradientStop(color,stop.Offset));
                }

                return newBrush;
            }
            else
            {
                SolidColorBrush brush = fromVal as SolidColorBrush;
                SolidColorBrush newsolid = new SolidColorBrush();
                ColorAnimation solidAnimation = new ColorAnimation(brush.Color, solid.Color, this.Duration);
                newsolid.Color = solidAnimation.GetCurrentValue(brush.Color, solid.Color, animationClock);

                return newsolid;

            }

        }

我正在使用这个动画在我的窗口上动画Canvas.Background

    <Storyboard x:Key="MyStoryBoard" RepeatBehavior="Forever" AutoReverse="True">
        <local:BrushAnimation Storyboard.TargetName="Canvas1"
                        Storyboard.TargetProperty = "(Canvas.Background)" 
                        To="Orange" Duration="0:0:5"/>
    </Storyboard>

你可以使用StaticResource设置动画的From属性,或者在代码隐藏中将其设置为Control of Background:

    public partial class Window1 : Window
    {
        public Window1()
        {
            InitializeComponent();
            ((BrushAnimation) ((Storyboard) Resources["SolidStoryBoard"]).Children[0]).From = Canvas1.Background;
        }
    }