WPF快速指导15:动画
WPF快速指导15:动画
在WPF或者SilverLight中,所谓动画,就是让一个对象的属性,随着时间而发生变化。动画由时间线(timeline)控制。时间线在C#中的原型为:
public abstract class Timeline : Animatable
{
//省略
}
它是一个抽象类。在WPF中,定义了各类时间线,最常用的有DoubleAnimation,它便继承自Timeline。
1:Storyboard及一个简单示例
容纳时间线的是故事板(Storyboard)。下面是一个最简单的例子:
前台:
<Canvas x:Name="Carrier" Width="800" Height="600" Background="Silver" MouseLeftButtonDown="Carrier_MouseLeftButtonDown" >
<Image x:Name="image1" Source="/WpfApplication1;component/run.jpg">
</Image>
<Button x:Name="buttonTest" Click="buttonTest_Click" Canvas.Top="250" Content="测试">
</Button>
</Canvas>
后台:
private void buttonTest_Click(object sender, RoutedEventArgs e)
{
TranslateTransform animatedTranslateTransform = new TranslateTransform();
image1.RenderTransform = animatedTranslateTransform;
DoubleAnimation doubleAnimation = new DoubleAnimation(0, 360, new Duration(TimeSpan.FromMilliseconds(1000)));
this.RegisterName("AnimatedTranslateTransform", animatedTranslateTransform);
Storyboard.SetTargetName(doubleAnimation, "AnimatedTranslateTransform");
Storyboard.SetTargetProperty(doubleAnimation, new PropertyPath(TranslateTransform.XProperty));
Storyboard translationStoryboard = new Storyboard();
translationStoryboard.Children.Add(doubleAnimation);
translationStoryboard.Begin(this);
}
在这个示例中,Storyboard中,我们使用了DoubleAnimation对象,它表示:随着时间改变一个数值。Storyboard通过SetTargetName方法将DoubleAnimation对象和animatedTranslateTransform联系起来。而animatedTranslateTransform又被指向image1.RenderTransform(关于RenderTransform属性,不明白的可以查看上篇《WPF快速指导14:变换》)。这就相当于说,动画被关联到了image1对象上。
这里面要重点讲一下SetTargetProperty方法。该方法第一个参数指定动画对象,第二个方法指的是,在SetTarget方法中被关联的那个的对象的一个属性。在本文的实例中,这个属性是TranslateTransform.XProperty。串联起来,本示例的需求就是:“在1000毫秒的时间里,让image1的TranslateTransform.XProperty属性由0变为360”。如果我们换一个属性,如TranslateTransform.XProperty,则表达的意思是:“在1000毫秒的时间里,让image1离最高处由0变为360”。
本示例运行效果:
2:关键帧
在上面的这个例子中,我们使用的线性插值。为了调整这个行为,可以用一组关键帧(key frame)来过渡。这也就是说,为了更改动画从起始属性到结束属性的线性行为,可插入一个或者多个关键帧。查看下面的示例:
TranslateTransform animatedTranslateTransform = new TranslateTransform();
image1.RenderTransform = animatedTranslateTransform;
this.RegisterName("AnimatedTranslateTransform", animatedTranslateTransform);
DoubleAnimationUsingKeyFrames translationAnimation = new DoubleAnimationUsingKeyFrames();
translationAnimation.Duration = TimeSpan.FromSeconds(6);
translationAnimation.KeyFrames.Add(new LinearDoubleKeyFrame(500, KeyTime.FromTimeSpan(TimeSpan.FromSeconds(3))));
translationAnimation.KeyFrames.Add(new DiscreteDoubleKeyFrame(400, KeyTime.FromTimeSpan(TimeSpan.FromSeconds(4))));
translationAnimation.KeyFrames.Add(new SplineDoubleKeyFrame(0, KeyTime.FromTimeSpan(TimeSpan.FromSeconds(6)), new KeySpline(0.6, 0.0, 0.9,
0.0)));
translationAnimation.RepeatBehavior = RepeatBehavior.Forever;
Storyboard.SetTargetName(translationAnimation, "AnimatedTranslateTransform");
Storyboard.SetTargetProperty(translationAnimation, new PropertyPath(TranslateTransform.XProperty));
Storyboard translationStoryboard = new Storyboard();
translationStoryboard.Children.Add(translationAnimation);
translationStoryboard.Begin(this);
在这个示例中,一个共有3个关键帧:LinearDoubleKeyFrame,DiscreteDoubleKeyFrame,SplineDoubleKeyFrame。
LinearDoubleKeyFrame指的是:这是一个线性关键帧。
DiscreteDoubleKeyFrame指的是:这是一个离散关键帧。
SplineDoubleKeyFrame指的是:这是一个加速和减速关键帧。
要体会它们之间的差异,可以运行代码,任何语言描述不抵一次视觉感受。
3:动画缓动
缓动(Easing)允许我们创建各类动画效果,类似反弹或者弹簧效果。如BounceEase,模拟的就是一种弹跳效果。在第一个示例中,我们加入如下语句:
doubleAnimation.EasingFunction = new BounceEase() { Bounces=2, EasingMode = EasingMode.EaseOut, Bounciness = 2 };
就会发现图片在到达终点会弹跳,然后结束。所有内建的缓动类,都在System.Windows.Media.Animation命名空间中,它们都以Ease结尾。
本代码的源码下载:WpfApplication1.rar
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· .NET周刊【3月第1期 2025-03-02】
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器