3.属性动画
文章目录
3.1 ValueAnimator的基本使用
3.1.1 概述
- 视图动画:对指定的控件做动画。
- 属性动画:通过改变控件的某一属性值来做动画的。
3.1.2 ValueAnimator 的简单使用
初步使用ValueAnimator:
ValueAnimator animator = ValueAnimator.ofInt(0,400); animator.setDuration(1000); animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @Override public void onAnimationUpdate(ValueAnimator animation){ int curValue = (Integer)animation.getAnimatedValue(); Log.d("ValueAnimator","curValue:"+curValue); } }); animator.start();
ValueAnimator 只负责对指定值区间进行动画运算。
需要对运算过程进行监听,然后对控件执行动画操作。
注意:
- 补间动画的单击区域:原区域。
- 属性动画的点击区域:新区域。
补充:
- 可以通过layout()函数来改变控件的位置。
- layout()函数在改变控件位置时是永久性的,即通过更改控件left、top, right 、bottom 这4 个点的坐标来更改坐标位置。
3.1.3 常用函数
**oflnt()与ofFloat()**函数:
public static ValueAnimatorofInt(int...values) public static ValueAnimatorofFloat(float...values)
- 参数类型都是可变长参数。
- 传进去的值列表表示动画时的变化范围。
ValueAnimator setDuration(long duration):设置动画时长,单位ms。
Object getAnimatedValue ():获取ValueAnimator在运动时当前运动点的值。
void start():开始动画。
void setRepeatCount(int value):设置循环次数,设置为ValueAnimation.INFINITE 表示无限循环,设置为0表示不循环。
void setRepeatMode(int value):设置循环模式,value取值:ValueAnimation.RESTART和ValueAnimation.REVERSE。
void cancel():取消动画。
注意:重复次数为INFINITE(无限循环)的动画,当Activity结束的时候,必须调用cancel()函数取消动画, 否则动画将无限循环,从而导致View无法释放,进一步导致整个Activity无法释放,最终引起内存泄漏。
添加与移除监听器:
添加方法:
public void addUpdateListener(AnimatorUpdateListener listener)//监听器一 public void addListener(AnimatorListener listener)//监听器二
监听器一: 监听动画过程中值的实时变化
public static interface AnimatorUpdateListener { void onAnimationUpdate(ValueAnimator animation); }
监听器二: 监听动画变化时的4个状态
public static interface AnimatorListener { void onAnimationStart(Animator animation); void onAnimationEnd(Animator animation); void onAnimationCancel(Animator animation); void onAnimationRepeat(Animator animation); }
移除监听器:
//移除AnimatorUpdate Listener void removeUpdateListener(AnimatorUpdateListener listener); void removeAllUpdateListeners(); //移除AnimatorListener void removeListener(AnimatorListener listener); void removeAllListeners();
其他不常用函数:
public void setStartDelay(long startDelay)//延迟多久开始,单位ms public ValueAnimator clone()//完全克隆一个ValueAnimator实例,包括它所有的设置以及所有对监听器代码的处理
3.2 自定义插值器与Evaluator
- View Animation中,仅允许通过setlnterpolator()函数来设置插值器。
- View Animator中,不仅可以设置插值器,还可以设置Evaluator。
3.2.1 自定义插值器
Linearlnterpolator举例:
public class Linearinterpolator implements Interpolator{ public Linearinterpolator(){} public Linearinterpolator(Context context , AttributeSet attrs) { public float getinterpolation(float input) { return input; } } ... } public interface Interpolator extends Timeinterpolator {} public interface Timeinterpolator{ float getInterpolation(float input); }
- input: Float 类型,取值范围是0~1。表示当前动画的进度,取0 时表示动画刚开始,取1时表示动画结束,取0.5 时表示动画中间的位置。
- 返回值:表示当前实际想要显示的进度。取值可以超过1 ,也可以小于0 。超过1表示己经超过目标值,小于0 表示小于开始位置。
使用方式:
animator.setinterpolator(new MyInterpolator());
3.2.2 Evaluator
从定义动画的数值区间到在AnimatorUpdateListener中得到当前动画所对应数值的过程:
- 1.定义动画数值区间:ofInt(400)
- 差值器:返回当前数值进度
- Evaluator:根据数值进度计算当前值
- 监听器返回:在AnimatorUpdateListener中返回
Evaluator 其实就是一个转换器,它能把小数进度转换成对应的数值位置。
对于Evaluator而言, oflnt()函数的默认Evaluator 是IntEvaluator,而ofFloat()函数的默认Evaluator则是FloatEvaluator 。
使用方式:
animator.setEvaluator(new MyEvaluator());
ArgbEvaluator:
用来实现颜色值过渡转换的。
animator.setEvaluator(new ArgbEvaluator());
定义颜色的取值范围要使用**ValueAnimator.oflnt()**函数,且颜色必须包括A 、R 、G 、B四个值。
ValueAnimator animator = ValueAnimator.ofInt(0xffffff00,0xff0000ff);
3.3 ofObject
3.3.1 概述
ValueAnimator有一个函数ofObject(), 可以传入任何类型的变量。
函数定义:
public static ValueAnimator ofObject(TypeEvaluator evaluator, Object...values)
- 参数一:自定义的Evaluator。
- 参数二:可变长参数,属于Object类型。
3.4 ObjectAnimator
3.4.1 概述
Google的开发人员在ValueAnimator 的基础上派生了一个类ObjectAnimator。
ValueAnimator中所能使用的函数在ObjectAnimator中都可以正常使用。
ObjectAnimator函数:
public static ObjectAnimator ofFloat(Object target,String propertyName,float...values) //example ObjectAnimator animator= ObjectAnimator.ofFloat(tv,"rotation",0,180,0); animator.setDuration(2000); animator.start();
- 参数一:用于指定这个动画操作的控件。
- 参数二:用于指定这个动画操作的属性。
- 参数三:可变长参数,指定属性值如何变化。
set函数:
ObjectAnimator的ofFloat函数的第二个参数不是根据控件XML 中的属性来改变的,而是通过指定属性所对应的set函数来改变的。
View中有关动画的几组set:
//1.透明度:alpha public void setAlpha(float alpha) //2.旋转度数:rotation、rotationX、rotationY public void setRotation(float rotation) public void setRotationX(float rotationX) public void setRotationY(float rotationY) //3.平移:translationX 、translationY public void setTranslationX(float translationX) public void setTranslationY(float translationY) //4.缩放:scaleX 、scaleY public void setScaleX(float scaleX) public void setScaleY(float scaleY)
3.4.2 自定义ObjectAnimator属性
ObjectAnimator的三个构造函数:
public static ObjectAnimator ofFloat(Object target,String propertyName,float...values) public static ObjectAnimator ofInt(Object target,String propertyName,int...values) public static ObjectAnimator ofObject(Object target,String propertyName,TypeEvaluator evaluator,Object...values)
注意:当且仅当动画只有一个过渡值时,系统才会调用对应属性的get函数来得到动画的初始值。当不存在get 函数时,则会取动画参数类型的默认值作为初始值; 当无法取得动画参数类型的默认值时,则会直接崩渍。
3.4.3 常用函数
监听器一:监听动画变化时的实时值
public static interface AnimatorUpdateListener{ void onAnimationUpdate(ValueAnimator animation); } //添加方法为: public void addUpdateListener(AnimatorUpdateListener listener)
监听器二:监听动画变化时的4种状态
public static interface AnimatorListener{ void onAnimationStart(Animator animation); void onAnimationEnd(Animator animation); void onAnimationCancel(Animator animation); void onAnimationRepeat(Animator animation); } //添加方法为: public void addListener(AnimatorListener listener)
与插值器和Evaluator相关的函数:
//设置插值器 public void setinterpolator(Timeinterpolator value) //设置Evaluator public void setEvaluator(TypeEvaluator value)
3.5 AnimatorSet
- 用于组合动画。
3.5.1 playSequentially()与playTogether()函数
AnimatorSet 对ValueAnimator和ObjectAnimator都是适用的,但一般不会用到ValueAnimator 的组合动画。
playSequentially()表示所有动画依次播放, playTogether()表示所有动画一起开始。
playSequentially()函数:
public void playSequentially(Animator...items); public void playSequentially(List<Animator> items);
playTogether()函数:
public void playTogether(Animator...items); public void playTogether(Collection<Animator> items);
playTogether()和playSequentially()函数在开始动画时,只是把每个控件的动画激活,至于每个控件自身的动画是否延时、是否无限循环, 只与控件自身的动画设定有关,与playTogether()和playSequentially()函数无关,它们只负责到时间后激活动画。playSequentially()函数只有在上一个控件做完动画以后,才会激活下一个控件的动画。
3.5.2 AnimatorSet.Builde
AnimatorSet.Builde的函数:
public Builder play(Animator anim)//表示要播放哪个动画 public Builder with(Animator anim)//和前面的动画一起执行 public Builder before(Animator anim)//先执行这个动画,再执行前面的动画 public Builder after(Animator anim)//在执行前面的动画后才执行该动画 public Builder after(long delay)//延迟n毫秒之后执行动画
3.5.3 AnimatorSet 监听器
添加监听器:
public static interface AnimatorListener{ //当AnimatorSet开始时调用 void onAnimationStart(Animator animation); //当AnimatorSet结束时调用 void onAnimationEnd(Animator animation); //当AnimatorSet被取消时调用 void onAnimationCancel(Animator animation); //当AnimatorSet重复时调用。由于AnimatorSet没有设置重复的函数,所以这个函数永远不会被调用 void onAnimationRepeat(Animator animation); //添加方法 public void addListener(AnimatorListener listener);
3.5.4 常用函数
//设置单次动画时长 public AnimatorSet setDuration(long duration) //设置插值器 public void setinterpolator(TimeInterpolator interpolator) //设置ObjectAnimator动画目标控件 public void setTarget(Object target)
在AnimatorSet中没有设置,那么以ObjecAnimator中的设置为准。
在AnimatorSet中设置以后,ObjectAnimator中的设置就会无效。
setStartDelay(long startDelay)函数:
//设置延时开始动画时长 public void setStartDelay(long startDelay)
- setStartDelay()函数不会覆盖单个动画的延时,而且仅针对性地延长AnimatorSet 的激活时间,单个动画所设置的setStartDelay()函数仍对单个动画起作用。
3.6 Animator 动画的XML实现
3.6.1 animator标签
<animator android:duration="int" android:valueFrom="float | int | color " android:valueTo="float | int | color " android:startOffset="int" android:repeatCount="int" android:repeatMode=["repeat" | "reverse"] android:valueType=["intType" | "floatType"] android:interpolator=["@android:interpolator/XXX"] />
将文件加入程序中的方法:
ValueAnimator valueAnimator = (ValueAnimator)Animatorinflater.loadAnimator(MyActivity.this,R.animator.animator); valueAnimator.start();
3.6.2 objectAnimator标签
<objectAnimator android:duration="string" android:duration="int" android:valueFrom="float | int | color " android:valueTo="float | int | color " android:startOffset="int" android:repeatCount="int" android:repeatMode=["repeat" | "reverse"] android:valueType=["intType" | "floatType"] android:interpolator=["@android:interpolator/XXX"] />
参考资料
- 《Android自定义控件开发入门与实战》