Interpolator简介
Interpolator属性是Animation类的一个XML属性,所以alpha、scale、rotate、translate、set都会继承得到这个属性。它指定动画如何变化,跟PS里的动作有点类似:随便拿来一张图片,应用一个动作,图片就会指定变化。
被用来修饰动画效果,定义动画的变化率,可以使存在的动画效果accelerated(加速),decelerated(减速),repeated(重复),bounced(弹跳)等。
Interpolator属性
Interpolator Class | Resource ID |
---|---|
AccelerateDecelerateInterpolator | @android:anim/accelerate_decelerate_interpolator |
AccelerateInterpolator | @android:anim/accelerate_interpolator |
AnticipateInterpolator | @android:anim/anticipate_interpolator |
AnticipateOvershootInterpolator | @android:anim/anticipate_overshoot_interpolator |
BounceInterpolator | @android:anim/bounce_interpolator |
CycleInterpolator | @android:anim/cycle_interpolator |
DecelerateInterpolator | @android:anim/decelerate_interpolator |
LinearInterpolator | @android:anim/linear_interpolator |
OvershootInterpolator | @android:anim/overshoot_interpolator |
各种属性的效果如下:
- AccelerateDecelerateInterpolator 动画从开始到结束,变化率是先加速后减速的过程。
- AccelerateInterpolator 动画从开始到结束,变化率是一个加速的过程。
- AnticipateInterpolator 开始的时候向后,然后向前甩
- AnticipateOvershootInterpolator 开始的时候向后,然后向前甩一定值后返回最后的值
- BounceInterpolator 动画结束的时候弹起
- CycleInterpolator 动画从开始到结束,变化率是循环给定次数的正弦曲线。
- DecelerateInterpolator 动画从开始到结束,变化率是一个减速的过程。
- LinearInterpolator 以常量速率改变
- OvershootInterpolator 向前甩一定值后再回到原来位置
Interpolator使用方法
在Java中(定义一个TextView tv):
LinearInterpolator li = new LinearInterpolator();
ObjectAnimator animator = ObjectAnimator.ofFloat(tv, "rotation", 0f, 360f);
animator.setInterpolator(li);
animator.setDuration(5000);
animator.start();
在xml中:
<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="@android:anim/linear_interpolator"
/>
当你没有为动画设置插值器是,系统默认会帮你设置加减速插值器AccelerateDecelerateInterpolator。
自定义Interpolator
既然要自定义Interpolator,我们自然要明白官方给我们的Interpolator是怎么实现的,我们就拿AccelerateDecelerateInterpolator和LinearInterpolator 作比较吧。
AccelerateDecelerateInterpolator的实现代码为:
@HasNativeInterpolator
public class AccelerateDecelerateInterpolator extends BaseInterpolator implements NativeInterpolatorFactory {
public AccelerateDecelerateInterpolator() {
}
@SuppressWarnings({"UnusedDeclaration"})
public AccelerateDecelerateInterpolator(Context context, AttributeSet attrs) {
}
public float getInterpolation(float input) {
return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;
}
/** @hide */
@Override
public long createNativeInterpolator() {
return NativeInterpolatorFactoryHelper.createAccelerateDecelerateInterpolator();
}
}
可以看出只重写了getInterpolation(float input)方法,所以加减速插值器的实现就在这个方法里。getInterpolation()方法接收一个input参数,input参数是系统根据设置的动画持续时间计算出来的,取值范围是[0,1],从0匀速增加到1。
(float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f
翻译成数学表达式就是:{0.5*cos[(input + 1)π] + 0.5}。
一个最基本的余弦函数变换,它的图像为[0,1]范围内的曲线,曲线的斜率先增大后减小,相应的,小球运动先加速后减速。
而线性插值器的实现代码为:
@HasNativeInterpolator
public class LinearInterpolator extends BaseInterpolator implements NativeInterpolatorFactory {
public LinearInterpolator() {
}
public LinearInterpolator(Context context, AttributeSet attrs) {
}
public float getInterpolation(float input) {
return input;
}
/** @hide */
@Override
public long createNativeInterpolator() {
return NativeInterpolatorFactoryHelper.createLinearInterpolator();
}
}
LinearInterpolator的getInterpolation(float input)方法果然是直接把input参数作为返回值返回了。由于input参数是从0匀速增加到1的,所以自然就是匀速啦。
清楚Interpolator是怎么实现的,我们就可以自定义一个先减速后加速的DeceAcceInterpolator了:
public class DeceAcceInterpolator implements Interpolator {
@Override
public float getInterpolation(float input) {
return ((4*input-2)*(4*input-2)*(4*input-2))/16f + 0.5f;
}
}
翻译成数学表达式如下:[(4*input-2)^3]/16 + 0.5。
由图可知是先减速后加速。
然后把我们的DeceAcceInterpolator加到属性动画:
DeceAcceInterpolator di = new DeceAcceInterpolator();
ObjectAnimator animator = ObjectAnimator.ofFloat(mImageView, "rotation", 0f, 360f);
animator.setInterpolator(di);
animator.setDuration(5000);
animator.start();
可以看到笑脸确实是先做减速旋转,速度减为0后又继续加速旋转。
如此,我们简单的自定义Interpolator就完成了。
结束语:本文仅用来学习记录,参考查阅。