本章介绍关键帧动画之前, 首先需要讲解一下关于WPF当中基础动画与本章所讲的关键帧动画的区别。
动画与关键帧的区别
普通动画
WPF基础动画当中, 我们熟悉的From/To/By驱动的动画, 主要在两个值之间创建过渡效果, 如下图所示:
下面是使用普通的ThicknessAnimation创建的爱心跳动的动画
关键帧
对于关键帧动画而言,关键帧动画没有From/To/By的属性, 而关键帧动画的值则是使用帧对象来进行描述, 故称之为关键帧动画, 如下所示:
下面是使用关键帧动画创建的一个矩形位移的动画
注: 能够注意到, 左下角, 描述了整个动画的过程:
1.首先5秒内, 矩形从位置0 -> 500 : LinearDoubleKeyFrame Value="500" KeyTime="0:0:5"
2.从5-10秒内, 矩形位置500 -> 200 : SplineDoubleKeyFrame KeySpline="0.25,0.5 0.75,1" Value="200" KeyTime="0:0:10"
3.从10-12秒内, 矩形位置200 -> 290 : LinearDoubleKeyFrame Value="290" KeyTime="0:0:12"
4.从12-13.5秒内, 矩形位置290 -> 300 : LinearDoubleKeyFrame Value="300" KeyTime="0:0:13.5"
5.从13.5-15秒内, 矩形位置300 -> 0 : SplineDoubleKeyFrame KeySpline="0.25,0.5 0.75,1" Value="0" KeyTime="0:0:15"
注: 关键帧对象(Frame) 主要包含两个参数, Value是目标值, KeyTime 则表达的是时间
到目前为止, 我们应该可以理解普通动画与关键帧动画的区别, 对于帧动画而言, 在于控制每一个帧的表现形式, 这一点并不像普通动画中, 对于整个动画的控制我们只能从开始到结束, 而帧动画可以控制开始到结束的整个过程。
介绍关键帧动画
下面,介绍了如何创建一个简单的关键帧动画。
1.如下代码,创建了一个矩形, 为其添加了一个点击时间触发动画, 该动画在Storyboard中定义并且触发:
说明:以上的创建了一个DoubleAnimation类型的帧动画, 为其绑定了一个目标及目标的动画依赖属性 "Y", Duration则为其设定了一个帧动画持续时间,在关键帧动画的集合中, 定义了多个线性关键帧(LinearDoubleKeyFrame), 为其设定了Value目标值和KeyTime持续时间。
此处说讲到的线性关键帧所属其中的一种类型, 在后面将会有更多的介绍。
关键帧动画类型
关键帧动画属于System.Windows.Media.Animation命令空间下, 命名规则约定为
AnimationUsingKeyFrames
Type: 为动画的值类型, 例如上面的动画当中, 需要给举行的X轴移动位置, X的值属于双精度类型, 所以定义的类型为 :DoubleAnimationUsingKeyFrames 。
关键帧的动画类型列表
帧对象的类型
正如我们创建不同类型的动画, 我们需要按照约定命名方式定义, 如: DoubleAnimation, ColorAnimation 等等。
对于帧动画而言, 主要由一个或者N个帧对象组成(Frame), 帧对象同时也拥有不同的种类, 故帧对象遵循一下的命名约定:
<插值方法><类型>
插值方法: 是帧对象使用的插值方法, 如: 离散(Discrete)、线性(Linear) 、样条(Spline) 等。
类型: 是动画的值类型, 例如Double、Decimal等。
KeyFrame: 固定的帧对象语法结束
关键帧的主要目的是指定 和KeyTime、Value 每个关键帧类型都可提供这两种属性。
- 属性Value指定该关键帧的目标值。
- 该KeyTime属性指定何时(在动画的Duration)中到达关键帧。 Value
当关键帧动画开始时,按其KeyTime属性定义的顺序遍接其关键帧。 - 如果时间 0 时没有关键帧,动画会在目标属性的当前值和第Value一个关键帧之间的转换;否则,动画的输出值将成为第一个关键帧的值。
- 动画使用第二个关键帧指定的Value插值方法在第一个关键帧和第二个关键帧之间创建过渡。 转换从第一个关键帧开始KeyTime,并在到达第二个关键帧KeyTime时结束。
- 动画将继续,这会创建每个后续关键帧和其前面的关键帧之间的过渡。
- 最后,动画转换为关键帧的值,其最大键时间等于或小于动画的值Duration。
如果动画的Duration或Automatic其Duration等于最后一个关键帧的时间,则动画结束。 否则,如果动画大于Duration最后一个关键帧的键时间,则动画将保留关键帧值,直到到达其Duration的末尾。 与所有动画一样,关键帧动画使用其FillBehavior属性来确定在到达活动周期结束时是否保留最终值。
插值方法
下面将主要介绍有三种不同类型的内插方法: 线性、离散和曲线。
线性内插
使用线性内插,动画将以段持续时间的固定速度进行播放。 例如,如果关键帧段从 0 过渡到 10,持续时间为 5 秒,则动画会在指定时间输出以下值:
离散内插
使用离散内插,动画函数将从一个值跳到下一个值,没有内插。 如果关键帧段从 0 过渡到 10,持续时间为 5 秒,则动画会在指定时间输出以下值:
注: 通过观察线性和离散的插入比较, 可以清晰的看出来, 离线类型的插入方式, 在动画的执行过程中, 我们无法在规定的时间内观察其变化效果, 直接至时间结束后, 到指定的目标值。
曲线内插
曲线内插可能很难理解;使用不同的设置进行体验有助于理解。 通过主曲线动画示例,可以更改主曲线值,并查看由此所产生的动画结果, 可以查看最上方视频进行理解。
组合内插
可在一个关键帧动画中使用具有不同内插类型的关键帧。 如果两个具有不同内插的关键帧动画彼此跟随,第二个关键帧的内插方法将用于创建从第一个值到第二个值的过渡。
下面的示例,演示了一个使用DoubleAnimationUsingKeyFrames创建使用线性、拼接和离散插值的示例:
Duration与KeyTime
与其他动画一样,关键帧动画具有属性Duration。 除了指定动画的Duration外,还需要指定每个关键帧的持续时间的哪一部分。 为此,您可以为每个动画的关键KeyTime帧描述 。 每个关键帧指定KeyTime该关键帧的结束时间。
属性KeyTime不指定密钥时间播放的时间。 关键帧的播放时长由关键帧的结束时间、前一个关键帧的结束时间以及动画的持续时间确定。 关键时间可以指定为时间值、百分比或特殊值Uniform或Paced。
TimeSpan
以下示例演示一个持续时间为 10 秒钟、有四个关键帧(这些关键帧的关键时间指定为时间值)的动画。
- 在前 3 秒钟内,第一个关键帧在基值和 100 之间进行动画处理,结束时间 = 0:0:03。
- 第二个关键帧在 100 和 200 之间进行动画处理。 它在第一个关键帧结束后开始(开始时间 = 3 秒),播放 5 秒钟,结束时间 = 0:0:8。
- 第三个关键帧在 200 和 500 之间进行动画处理。 它在第二个关键帧结束时开始(开始时间 = 8 秒),播放 1 秒钟,结束时间 = 0:0:9。
- 第四个关键帧在 500 和 600 之间进行动画处理。 它在第三个关键帧结束时开始(开始时间 = 9 秒),播放 1 秒钟,结束时间 = 0:0:10。
百分比
百分比值指定关键帧以动画的某些Duration百分比结束。 在 XAML 中,指定百分比作为 % 符号后的数字。 在代码中,使用FromPercent方法并传递一个Double指示百分比的方法。 该值必须大于或等于 0 并且小于或等于 100%。 以下示例演示一个持续时间为 10 秒钟、有四个关键帧(这些关键帧的关键时间指定为百分比)的动画。
- 在前 3 秒钟内,第一个关键帧将在基值和 100 之间进行动画处理,结束时间 = 0:0:3。
- 第二个关键帧在 100 和 200 之间进行动画处理。 它在第一个关键帧结束后开始(开始时间 = 3 秒),播放 5 秒钟,结束时间 = 0:0:8 (0.8 * 10 = 8)。
- 第三个关键帧在 200 和 500 之间进行动画处理。 它在第二个关键帧结束时开始(开始时间 = 8 秒),播放 1 秒钟,结束时间 = 0:0:9 (0.9 * 10 = 9)。
- 第四个关键帧在 500 和 600 之间进行动画处理。 它在第三个关键帧结束时开始(开始时间 = 9 秒),播放 1 秒钟,结束时间 = 0:0:10 (1 * 10 = 10)。
Uniform
当您Uniform希望每个关键帧花费相同的时间时,请使用计时。
Uniform关键时间将可用时间平均除以关键帧数,以确定每个关键帧的结束时间。 下面的示例显示持续时间为 10 秒的动画和四个关键帧,其关键时间指定为Uniform。
- 在前 2.5 秒钟内,第一个关键帧在基值和 100 之间进行动画处理,结束时间 = 0:0:2.5。
- 第二个关键帧在 100 和 200 之间进行动画处理。 它在第一个关键帧结束后开始(开始时间 = 2.5 秒),播放大约 2.5 秒钟,结束时间 = 0:0:5。
- 第三个关键帧在 200 和 500 之间进行动画处理。 它在第二个关键帧结束时开始(开始时间 = 5 秒),播放 2.5 秒钟,结束时间 = 0:0:7.5。
- 第四个关键帧在 500 和 600 之间进行动画处理。 它在第二个关键帧结束时开始(开始时间 = 7.5 秒),播放 2.5 秒钟,结束时间 = 0:0:1。
Paced
如果要Paced以恒定速率进行动画处理,请使用计时。
Paced关键时间根据每个关键帧的长度分配可用时间,以确定每个帧的持续时间。 这样,动画的速度或速率将保持不变。 下面的示例显示持续时间为 10 秒的动画和三个关键帧,其关键时间指定为Paced。
关键帧时间及顺序
可以在同一动画中使用具有不同KeyTime值类型的关键帧。 尽管建议以关键帧的实际播放顺序来添加关键帧,但此操作不是必需的。 动画和计时系统能够处理顺序紊乱的关键帧。 将忽略关键时间无效的关键帧。
下表描述了为关键帧动画的关键帧解析关键时间的过程。
- 1 解析TimeSpanKeyTime值。
- 2 确定动画的总内插时间,即关键帧动画完成向前迭代所需的全部时间。
如果动画的Duration不是Automatic或Forever,则总插值时间是动画Duration属性的值。
否则,总插值时间是其关键帧(TimeSpanKeyTime如果有)之间指定的最大值。
否则,总内插时间为 1 秒。 - 3 使用总插值时间值解析PercentKeyTime值。
- 4 如果最后一个关键帧尚未在之前步骤中解析,则将解析该关键帧。 如果最后KeyTime一个关键帧为Uniform或Paced,则其解析时间将等于总插值时间。
如果第KeyTime一个关键帧的,Paced并且此动画比关键帧多,则将其KeyTime值解析为零;如果只有一个关键帧,并且其KeyTime值为Paced,则解析为总插值时间,如上一步所述。 - 5 解析剩余UniformKeyTime值:每个值都给定可用时间的相等份额。 在此过程中PacedKeyTime,未解析的值将暂时视为UniformKeyTime值,并获得临时解析的时间。
- 6 使用声明KeyTime的最接近具有已解析KeyTime值的关键帧,解决未指定密钥时间的关键帧的值。
- 7 解析剩余PacedKeyTime值。 PacedKeyTime使用相邻KeyTime关键帧的值来确定其解析时间。 目的是确保动画速度在此关键帧的解析时间内保持固定不变。
- 8 按解析时间(主键)和声明顺序(辅助键)对关键帧进行排序,即根据已解决的关键帧KeyTime值使用稳定排序。
到此这篇关于WPF关键帧动画介绍与实现的文章就介绍到这了。希望对大家的学习有所帮助,也希望大家多多支持脚本之家。