Android 属性动画探究(二)——TypeEvaluator解析与自定义
来源:互联网 发布:c语言点滴 epub 编辑:程序博客网 时间:2024/05/01 16:13
1、TypeEvaluator
这里将主要阐述一下上图的第三步,关于TypeEvaluator的一些解析。上一篇中已经知道Interpolator的作用是控制动画的完成进度变化快慢的,那TypeEvaluator的作用又是什么?
简言之,TypeEvaluator是直接改变动画的属性值的,比如要改变颜色属性,可以直接改变其值为"#FFFFFF",而Interpolator改变的是进度,如可以直接指定瞬间完成动画整体的80%。但是两者不是孤立存在的,不是各自改变各自的东西,他们之间又有着什么样的爱恨纠葛?
2、系统实现的TypeEvaluator
先看一下上一篇用到的 ValueAnimator.ofFloat的默认实现
/** * Internal function, called by ValueAnimator, to set up the TypeEvaluator that will be used * to calculate animated values. */ void init() { if (mEvaluator == null) { // We already handle int and float automatically, but not their Object // equivalents mEvaluator = (mValueType == Integer.class) ? sIntEvaluator : (mValueType == Float.class) ? sFloatEvaluator : null; } if (mEvaluator != null) { // KeyframeSet knows how to evaluate the common types - only give it a custom // evaluator if one has been set on this class mKeyframeSet.setEvaluator(mEvaluator); } }
可见默认设置为sFloatEvaluator
private static final TypeEvaluator sFloatEvaluator = new FloatEvaluator();
** * This evaluator can be used to perform type interpolation between <code>float</code> values. */public class FloatEvaluator implements TypeEvaluator<Number> { /** * This function returns the result of linearly interpolating the start and end values, with * <code>fraction</code> representing the proportion between the start and end values. The * calculation is a simple parametric calculation: <code>result = x0 + t * (v1 - v0)</code>, * where <code>x0</code> is <code>startValue</code>, <code>x1</code> is <code>endValue</code>, * and <code>t</code> is <code>fraction</code>. * * @param fraction The fraction from the starting to the ending values * @param startValue The start value; should be of type <code>float</code> or * <code>Float</code> * @param endValue The end value; should be of type <code>float</code> or <code>Float</code> * @return A linear interpolation between the start and end values, given the * <code>fraction</code> parameter. */ public Float evaluate(float fraction, Number startValue, Number endValue) { float startFloat = startValue.floatValue(); return startFloat + fraction * (endValue.floatValue() - startFloat); }}分析FloatEvaluator ,主要是实现了evaluate方法,其中的参数fraction这个至关重要,它便是开始提到问题的答案,是Interpolator中返回的动画进度。把Interpolator和TypeEvaluator联系起来。故此参数是动画的进度完成百分比。startValue 我们设置的动画初始值,endValue 我们设置的动画结束值。这里返回值是:开始值+动画完成百分比*(结束值-开始值)。显然这是线性变化关系返回此刻动画的属性值变化到哪个具体数值了。这个值我们在动画监听中获取到。
public void onAnimationUpdate(ValueAnimator animation) { cy = (Float) animation.getAnimatedValue(); // ... }这里就明白了整个流程,通过ofFloat方法传人要设置的动画变化范围值,Interpolator中返回动画当前进度百分比传人到TypeEvaluator中,TypeEvaluator根据这个百分比来计算当前的动画属性值具体应该是多少。如果需要获取当前这个属性的具体值则在onAnimationUpdate中获取。
3、自己实现TypeEvaluator
ValueAnimator与ObjectAnimator中都有ofObject(TypeEvaluator evaluator, Object... values) 这个方法,其中第一个参数便可使用自己实现的TypeEvaluator。在定义Interpolator时只能使动画进度变化按特定函数关系执行,在这里便可以使得动画的属性值按特定的函数关系变化。下面描述一个使小球沿着等幅周期振荡函数进行运动的例子。定义一个类封装坐标值(系统也有实现-- android.graphics.Point;):
/** * 坐标点 */public class Point { private float x; private float y; public Point(float x, float y) { this.x = x; this.y = y; } public float getX() { return x; } public void setX(float x) { this.x = x; } public float getY() { return y; } public void setY(float y) { this.y = y; }}定义OscillationEvaluator:
/** * 等幅振荡 */ class OscillationEvaluator implements TypeEvaluator { @Override public Object evaluate(float fraction, Object startValue, Object endValue) { Point startPoint = (Point) startValue; Point endPoint = (Point) endValue; float x = startPoint.getX() + fraction * (endPoint.getX() - startPoint.getX());//x坐标线性变化 float y = 120 * (float) (Math.sin(0.01 * Math.PI * x)) + getHeight() / 2;//y坐标取相对应函数值 return new Point(x, y); } }
函数图像:
/** * 小球动画 */ private void startAnimationMotion() { Point startPoint = new Point(mRadius, getHeight() / 2); Point endPoint = new Point(getWidth() - mRadius, 0); ValueAnimator animator = ValueAnimator.ofObject(new OscillationEvaluator(), startPoint, endPoint); animator.setDuration(7000).setRepeatCount(3); animator.addUpdateListener(new AnimatorUpdateListener() { @Override public void onAnimationUpdate(ValueAnimator animation) { currentPoint = (Point) animation.getAnimatedValue(); invalidate(); } }); animator.setInterpolator(new LinearInterpolator());//设置插值器 animator.start(); }
这里需要设置为LinearInterpolator保证x坐标线性变化。
绘制图像:
@Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); width = getWidth(); height = getHeight(); mPaint.setStyle(Style.FILL); mPaint.setAntiAlias(true); if (currentPoint == null) { startAnimationMotion();// 执行动画 } mPaint.setColor(Color.WHITE); canvas.drawLine(0, getHeight() / 2, getWidth(), getHeight() / 2, mPaint); mPaint.setColor(Color.MAGENTA); canvas.drawCircle(currentPoint.getX(), currentPoint.getY(), mRadius, mPaint); }效果:
4、总结
以上便是对Interpolator、TypeEvaluator的一些见解。Interpolator负责调节动画进度变化快慢,TypeEvaluator负责改变动画最终的属性值,它们之间以Interpolator返回的当前进度值相联系。文中多以路径变化举例,当然属性动画是可以根据需要作用于其他属性的,通过对Interpolator、TypeEvaluator的自定义,写出丰富效果。当然,一般不需要同时自己实现两者。
下载源码
0 0
- Android 属性动画探究(二)——TypeEvaluator解析与自定义
- Android 属性动画探究(一)——Interpolator解析与自定义
- Android属性动画--TypeEvaluator
- 浅析 Android 动画:自定义 Interpolator 与 TypeEvaluator
- Android属性动画(二) ValueAnimator的实际应用 & 自定义TypeEvaluator
- Android 属性动画 多动画执行 与 估值器 TypeEvaluator
- Android开发 之 属性动画(自定义ValueAnimator的TypeEvaluator)
- Android-Property 动画自定义TypeEvaluator
- Android属性动画(三)——TypeEvaluator(估值器)和Interpolator(插值器)
- 属性动画-TypeEvaluator
- 模拟自然动画的精髓——TimeInterpolator与TypeEvaluator
- Android动画解析(二)-----属性动画
- 属性动画资料文件如何编写?property-animation资源文件 属性动画如何自定义TypeEvaluator
- Android 动画-Interpolator和TypeEvaluator
- 属性动画Animator玩法/自定义估值器TypeEvaluator实现抛物线曲线动画
- Android动画解析 View动画,帧动画与属性动画
- Android 属性动画——自定义Drawable
- Android属性动画完全解析(二)
- 31.Next Permutation
- 毕业论文出炉记录(纯纯的菜鸟文)
- 针对魔兽争霸3“萝莉”病毒的扫描工具开发
- linux 环境变量设置(临时 + 永久)
- recycleView基本知识
- Android 属性动画探究(二)——TypeEvaluator解析与自定义
- 润乾报表使用Frame实现初始参数 报表为空效果
- MYSQL 百万条记录全文检索中文解决方案
- Hadoop Yarn的工作流程
- 编写开源库并发布到JitPack.io
- UNIX下利用OpenSSL对大文件进行AES加解密
- 第13篇研究webrtc官网(二)ninja安装(一)及安卓一对一测试问题
- 用AOP自动管理Session数据
- CSS选择器