AnimPropertyView
估值器(TypeEvaluator)
设置动画 如何从初始值 过渡到 结束值 的逻辑
- 插值器(
Interpolator
)决定 值 的变化模式(匀速、加速) - 估值器(
TypeEvaluator
)决定 值 的具体变化数值
ValueAnimator
实现原理 : 通过不断控制 值的变化, 再不断赋值给对象的属性,从而实现动画的效果。

从上面原理可以看出:ValueAnimator
类中有3个重要方法:
ValueAnimator.ofInt(int values)
ValueAnimator.ofFloat(float values)
ValueAnimator.ofObject(int values)
ValueAnimator.ofInt(int values)
将初始值 以整型数值的形式 过渡到结束值
即估值器是整型估值器 -
IntEvaluator
模板代码
实际开发中,建议使用Java代码实现属性动画:因为很多时候属性的起始值是无法提前确定的(无法使用XML设置),这就需要在Java
代码里动态获取。
1 | // 步骤1:设置动画属性的初始值 & 结束值 |
XML设置
1 | // ValueAnimator采用<animator> 标签 |
1 | Animator animator = AnimatorInflater.loadAnimator(context, R.animator.set_animation); |
实战
按钮的宽度从 200px
放大到 500px
1 | <Button |
?代码设置初始值
1 | // 步骤1:设置属性数值的初始值(此处在xml中200) & 结束值(600) |
浮点型:ValueAnimator.oFloat()
将初始值 以浮点型数值的形式 过渡到结束值
ValueAnimator.oFloat()
采用默认的浮点型估值器 (FloatEvaluator
)ValueAnimator.ofInt()
采用默认的整型估值器(IntEvaluator
)
在使用上完全没有区别
ValueAnimator.ofObject()
将初始值 以对象的形式 过渡到结束值
即通过操作 对象 实现动画效果
实战
可以看到 ValueAnimator.ofObject()
的本质还是操作 值,将多个值封装到一个对象里的方式,同时对多个值一起操作
PointEvaluator
1 | class PointEvaluator : TypeEvaluator<Point> { |
Point
1 | class Point(val x: Float, val y: Float) |
MyView
1 | class MyView : View { |
插值器
xml设置
当在XML文件设置插值器时,只需传入对应的插值器资源ID即可
主要是设置插值器属性android:interpolator
1 |
|
代码设置
当在Java代码设置插值器时,只需创建对应的插值器对象即可
1 | Button mButton = (Button) findViewById(R.id.Button); |
系统内置插值器

自定义插值器
根据动画的进度(0%-100%)计算出当前属性值改变的百分比
自定义插值器需要实现 Interpolator
/ TimeInterpolator
接口 & 复写getInterpolation()
- 补间动画 实现
Interpolator
接口;属性动画实现TimeInterpolator
接口 TimeInterpolator
接口是属性动画中新增的,用于兼容Interpolator
接口,这使得所有过去的Interpolator
实现类都可以直接在属性动画使用
1 | // Interpolator接口 tween动画 |
匀速插值器
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28// 匀速差值器:LinearInterpolator
public class LinearInterpolator extends BaseInterpolator implements NativeInterpolatorFactory {
// 仅贴出关键代码
...
public float getInterpolation(float input) {
return input;
// 没有对input值进行任何逻辑处理,直接返回
// 即input值 = fraction值
// 因为input值是匀速增加的,因此fraction值也是匀速增加的,所以动画的运动情况也是匀速的,所以是匀速插值器
}
// 先加速再减速 差值器:AccelerateDecelerateInterpolator
public class AccelerateDecelerateInterpolator implements Interpolator, NativeInterpolatorFactory {
// 仅贴出关键代码
...
public float getInterpolation(float input) {
return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;
// input的运算逻辑如下:
// 使用了余弦函数,因input的取值范围是0到1,那么cos函数中的取值范围就是π到2π。
// 而cos(π)的结果是-1,cos(2π)的结果是1
// 所以该值除以2加上0.5后,getInterpolation()方法最终返回的结果值还是在0到1之间。只不过经过了余弦运算之后,最终的结果不再是匀速增加的了,而是经历了一个先加速后减速的过程
// 所以最终,fraction值 = 运算后的值 = 先加速后减速
// 所以该差值器是先加速再减速的
}
}先加速再减速 插值器:
AccelerateDecelerateInterpolator
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15// 先加速再减速 差值器:AccelerateDecelerateInterpolator
public class AccelerateDecelerateInterpolator implements Interpolator, NativeInterpolatorFactory {
// 仅贴出关键代码
...
public float getInterpolation(float input) {
return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;
// input的运算逻辑如下:
// 使用了余弦函数,因input的取值范围是0到1,那么cos函数中的取值范围就是π到2π。
// 而cos(π)的结果是-1,cos(2π)的结果是1
// 所以该值除以2加上0.5后,getInterpolation()方法最终返回的结果值还是在0到1之间。只不过经过了余弦运算之后,最终的结果不再是匀速增加的了,而是经历了一个先加速后减速的过程
// 所以最终,fraction值 = 运算后的值 = 先加速后减速
// 所以该差值器是先加速再减速的
}
}
对input值 根据动画的进度(0%-100%)通过逻辑计算 计算出当前属性值改变的百分比
实战
DecelerateAccelerateInterpolator
1 | class DecelerateAccelerateInterpolator : TimeInterpolator { |
InterpolatorActivity
1 | val curTranslationX = bt_anim_interpolator.translationX |
ObjectAnimator
与 ValueAnimator
类的区别
ValueAnimator
类是先改变值,然后 手动赋值 给对象的属性从而实现动画;是 间接 对对象属性进行操作;ObjectAnimator
类是先改变值,然后 自动赋值 给对象的属性从而实现动画;是 直接 对对象属性进行操作
估值器(TypeEvaluator) 和插值器
- 插值器(
Interpolator
)决定 值 的变化模式(匀速、加速) - 估值器(
TypeEvaluator
)决定 值 的具体变化数值,设置动画从初始值过渡到结束值的逻辑。
https://blog.csdn.net/carson_ho/article/details/99619871
作者:Carson_Ho
链接:https://www.jianshu.com/p/7c95342f4bc2
https://www.jianshu.com/p/2f19fe1e3ca1
来源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。