Interpolator,意译插值器,我理解为android中的变速器,依据数学中的函数公式比如计算获得想要的值,通常情况下,x为随时间固定变化的、取值0-1的小数,y为进度,取值0 - 1,a为任意参数。
以下是相关源码分析。
TimeInterpolator
顺着任意插值器可以找到最初的父接口,android.animation.TimeInterpolator,从名字就可看出:随时间变化的插值器。内部提供了 getInterpolation()方法,提供了最基本的需求。
// 入参input: 时间参数,取值0-1,0代表开始,1代表结束
// 返回值float: 进度
float getInterpolation(float input);
Interpolator
从文档中看到,android.view.animation.Interpolator 继承自TimeInterpolator接口,没有其他任何方法,仅仅是为了描述动画改变速率的抽象接口而已。其实直接去掉也没事,为什么要有这个中间接口呢?因为这个接口很古老,Android诞生的时候就引入了,而TimeInterpolator是在Android Api11的时候引入的,我猜想是为了兼容老版本,所以Interpolator没有直接删除,而是采用了继承,代代传了下来。如Interpolator的注释所写:
public interface Interpolator extends TimeInterpolator {
// A new interface, TimeInterpolator, was introduced for the new android.animation
// package. This older Interpolator interface extends TimeInterpolator so that users of
// the new Animator-based animations can use either the old Interpolator implementations or
// new classes that implement TimeInterpolator directly.
}
BaseIntorpolator
android.view.animation.BaseInterpolator,Interpolator的抽象类,添加了一个抽象参数:mChangingConfiguration。相当于我们上面数学公式中 y = ax中的a,不怎么常用,了解即可。
LinearInterpolator
线性插值器,输入即输出:
public float getInterpolation(float input) {
return input;
}
DecelerateInterpolator
减速插值器,速度越来越慢
private float mFactor = 1.0f;
public float getInterpolation(float input) {
float result;
if (mFactor == 1.0f) {
result = (float)(1.0f - (1.0f - input) * (1.0f - input));
} else {
result = (float)(1.0f - Math.pow((1.0f - input), 2 * mFactor));
}
return result;
}
AccelerateInterpolator
加速插值器,速度越来越快
private static float mFactor = 1.0f;
private static double mDoubleFactor = 2.0;
public static float getInterpolation(float input) {
if (mFactor == 1.0f) {
return input * input;
} else {
return (float)Math.pow(input, mDoubleFactor);
}
}
AccelerateDecelerateInterpolator
换挡插值器,先加速后减速
public float getInterpolation(float input) {
return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;
}
AnticipateInterpolator
回手抛插值器,先后抛,然后迅速前抛
int tension = 2
public float getInterpolation(float t) {
// a(t) = t * t * ((tension + 1) * t - tension)
return t * t * ((mTension + 1) * t - mTension);
}
BounceInterpolator
弹珠插值器,像掉落在地板装上的玻璃球,弹跳高度越来越小
private static float bounce(float t) {
return t * t * 8.0f;
}
public float getInterpolation(float t) {
// _b(t) = t * t * 8
// bs(t) = _b(t) for t < 0.3535
// bs(t) = _b(t - 0.54719) + 0.7 for t < 0.7408
// bs(t) = _b(t - 0.8526) + 0.9 for t < 0.9644
// bs(t) = _b(t - 1.0435) + 0.95 for t <= 1.0
// b(t) = bs(t * 1.1226)
t *= 1.1226f;
if (t < 0.3535f) return bounce(t);
else if (t < 0.7408f) return bounce(t - 0.54719f) + 0.7f;
else if (t < 0.9644f) return bounce(t - 0.8526f) + 0.9f;
else return bounce(t - 1.0435f) + 0.95f;
}
AnticipateOvershootInterpolator
回抛越界插值器
private static float mTension = 3.5f;
public static float getInterpolation(float t) {
if (t < 0.5f) return 0.5f * a(t * 2.0f, mTension);
else return 0.5f * (o(t * 2.0f - 2.0f, mTension) + 2.0f);
}
private static float a(float t, float s) {
return t * t * ((s + 1) * t - s);
}
private static float o(float t, float s) {
return t * t * ((s + 1) * t + s);
}
CycleInterpolator
周期插值器,内部有一个成员变量:mCycles,默认值1,是指x=1时,sin函数完整的走完了1个周期。举例,mCycles = 0.1时,x=1时,sin函数只能走完十分之一。mCycles=0.5时,x=1时,sin函数只能走完一半。
private float mCycles = 0.5f; // 以0.5举例
public float getInterpolation(float input) {
return (float)(Math.sin(2 * mCycles * Math.PI * input));
}
PathInterpolator
路径插值器。前面说的插值器都是根据函数一点一点计算出来的,路径插值器是根据我们自己提供的point来计算的,有兴趣的可以先去了解一下贝塞尔曲线,很有意思。
收集相关网址:
- 各种常见函数图表:easings.net
- 贝塞尔动态演示图表:cubic-bezier.com
- 高阶函数图表:www.wolframalpha.com
- 简易函数计算图表演示:www.desmos.com/calculator?…