Android属性动画(第一话)
帧动画,补间动画
Android动画能给界面带来很炫的效果,如果我们要实现这些效果,在android3.0版本前实现动画主要有2种方式,帧动画和补间动画。
帧动画加载大量图片,对性能有很大要求效率不高,补间动画是对view进行包括缩放,移动,旋转,透明度的绘制。因为补间动画实现不了动画操作后的view的点击等操作,只是简单在操作后的地方显示一个,并不会加上view原来的属性,比如一个button从父容器左上角移动到右下角,他的点击事件还在左上角。
介绍属性动画
为了解决上述问题,新推出了View的属性动画,原理是改变view的属性,所以我们可以操作缩放移动透明度旋转后的view,原理是在一段时间内不断设置View.setRotation(),下面我们来介绍一下ValueAnimator。
ValueAnimator
//动画是200毫秒内view由0过渡到1
ValueAnimator valueAnimator = ValueAnimator.ofFloat(0f, 1f);
valueAnimator.setDuration(200);
valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
//监听输出动画移动的值
float value = (float) animation.getAnimatedValue();
}
});
valueAnimator.start();
生成ValueAnimator的方法除了ValueAnimator.ofFloat(float);参数要精确到小数点后几位,还有ValueAnimator.ofInt(int);参数是整型比如1,100。
ValueAnimator还有其他属性,比如设置延迟时间ValueAnimator.setStartDelay(200);设置延时200毫秒,还有循环次数
ValueAnimator.setRepeatCount(5);动画循环5次,又或者是动画播放模式正常ValueAnimator.RESTART还是反向播放的
ValueAnimator.setRepeatMode(ValueAnimator.REVERSE);发向播放动画。
ObjectAnimator
ObjectAnimator继承了ValueAnimator,所以ValueAnimator有的方法ObjectAnimator都有。ObjectAnimator是操作具体的控件比如button,imageview的动画,举几个例子:
图片从x轴的-500的位置移动到100的位置
ObjectAnimator objectAnimator=ObjectAnimator.ofFloat(mImageView,"translationX",-500f,100f);
objectAnimator.setDuration(500);
objectAnimator.start();
透明度由1变成0再变成1的动画
ObjectAnimator objectAnimator=ObjectAnimator.ofFloat(mImageView,"alpha",1f,0f,1f);
objectAnimator.setDuration(500);
objectAnimator.start();
旋转360度的动画
ObjectAnimator objectAnimator=ObjectAnimator.ofFloat(mImageView,"rotation",0f,360f);
objectAnimator.setDuration(500);
objectAnimator.start();
y轴上缩放3倍的动画
ObjectAnimator objectAnimator=ObjectAnimator.ofFloat(mImageView,"scaleY",1f,3f);
objectAnimator.setDuration(500);
objectAnimator.start();
如果你觉得单单实现一种动画还不够炫,如果你想同时实现多个动画,你要用到动画组合AnimatorSet
AnimatorSet
把多个ObjectAnimator按顺序连接起来,比如把上面的缩放,移动,设置透明度组合起来
ObjectAnimator scaleYAnimator=ObjectAnimator.ofFloat(mImageView,"scaleY",1f,3f);
ObjectAnimator translationXAnimator=ObjectAnimator.ofFloat(mImageView,"translationX",0f,100f);
ObjectAnimator alphaAnimator=ObjectAnimator.ofFloat(mImageView,"alpha",1f,0f,1f);
AnimatorSet animatorSet=new AnimatorSet();
animatorSet.play(scaleYAnimator).with(translationXAnimator).with(alphaAnimator);
animatorSet.setDuration(500);
animatorSet.start();
这里Animator.after将其他动画加到这个动画之后,还可以传入动画设置两个动画的间隔,Animator.with两个动画一起播放,Animator.before插入动画放在这个动画之前。
动画监听器
ObjectAnimator objectAnimator=ObjectAnimator.ofFloat(mImageView,"scaleY",1f,3f);
objectAnimator.addListener(new Animator.AnimatorListener() {
@Override
public void onAnimationStart(Animator animation) {
//动画的时候
}
@Override
public void onAnimationEnd(Animator animation) {
//动画结束的时候
}
@Override
public void onAnimationCancel(Animator animation) {
//动画取消时
}
@Override
public void onAnimationRepeat(Animator animation) {
//动画循环时
}
});
objectAnimator.setDuration(500);
objectAnimator.start();
你也可以单独实现一个监听方法,这里的AnimatorListener改为AnimatorListenerAdapter就可以了
objectAnimator.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
super.onAnimationEnd(animation);
}
});
设置XML动画
如果有多个界面的控件要实现相同的动画效果,我们可以通过xml更加有效率来设置动画。
在res/animator文件夹下新建animator.xml
(注意,res/anim这个文件夹是放补间动画的)
根标签是一个
xml代码写好了,然后实现可以在类中调用
Animator animator = AnimatorInflater.loadAnimator(mContext, R.animator.animator);
animator.setTarget(mImageView);
animator.start();
最后通过够用AnimatorInflate.loadAnimator,参数分别是Context和R.animator.animator
总结
上述分别讲述了帧动画,补间动画,属性动画的ValueAnimator,ObejectAnimator 和AnimatorSet,还有属性动画的xml写法。
从性能效率上来看,优先考虑使用属性动画。