android动画系列(一):property属性动画
2016-08-27 20:54
281 查看
Property 动画
与view动画的区别
view动画只能作用于view,而property动画的作用范围更广view动画只能作用于缩放,平移,淡化,旋转这几个特性,对于别的比如背景颜色的改变不能作用
view动画只是改变了view的绘制,并没有改变view的实际属性,所以“只是看上去好看而已”,而property动画解决了这个问题
由官网上的介绍来说,就是 任何属性,任何对象(看得到或者看不到),任何时候。
属性
下列属性可以更改duration,Time interpolation,Repeat count and behavior,Animator sets,Frame refresh delay
监听原理
1.计算已完成动画分数首先,new 一个ValueAnimator,然后为要修改的属性指定开始,结束的值,这样的话,ValueAnimator会一直计算随着时间的减少value的值变化的百分率,
2.计算插值分数
当valueAnimator计算完之后,他会去调用TimeInterpolator,去计算得到一个插值分数,当然传入的是当前的已完成动画分数
/** * Maps a value representing the elapsed fraction of an animation to a value that represents * the interpolated fraction. This interpolated value is then multiplied by the change in * value of an animation to derive the animated value at the current elapsed animation time. * * @param input A value between 0 and 1.0 indicating our current point * in the animation where 0 represents the start and 1.0 represents * the end * @return The interpolation value. This value can be more than 1.0 for * interpolators which overshoot their targets, or less than 0 for * interpolators that undershoot their targets. */ float getInterpolation(float input);
3.计算属性值
当插值分数计算完成后,valueAnimator会调用合适的TypeEvaluator来计算运动中的函数值,这是TypeEvaluator的返回值,我们以floatEvaluator为例
@Override public float[] evaluate(float fraction, float[] startValue, float[] endValue) { float[] array = mArray; if (array == null) { array = new float[startValue.length]; } for (int i = 0; i < array.length; i++) { float start = startValue[i]; float end = endValue[i]; array[i] = start + (fraction * (end - start)); } return array; }
这里传进去的就是fraction:插值分数,startValue:初始值,endValue:结束值。从而我们可以计算出来并返回对象属性现在的值
总结一下就是:ValueAnimator以时间为基准获得elapsed fraction,然后插值器通过时间的流失率获得动画的变化率,这个变化率就是作用于我们的属性的。最后typeEvaluator通过动画变化率得到属性的当前值
使用方法
ValueAnimator
整个property 动画有两个步骤:1.首先是计算出属性的值
2.然后是为对象属性设置这些值,即应用和刷新动画
我们通过ValueAnimator完成了第一个步骤,如果要完成第二个步骤需要监听由ValueAnimator计算得到的属性值,并修改目标对象。需要实现ValueAnimator .onUpdateListener 接口,自己去处理对象的动画逻辑
如
ValueAnimator animation = ValueAnimator.ofFloat(0f, 1f); animation.setDuration(1000); animation.addUpdateListener(new AnimatorUpdateListener() { @Override public void onAnimationUpdate(ValueAnimator animation) { Log.i("update", ((Float) animation.getAnimatedValue()).toString()); } }); animation.setInterpolator(new CycleInterpolator(3)); animation.start();
ObjectAnimator
objectAnimator是valueAnimator的子类,它比valueAnimator好的地方就是它不用自己去写对象属性的处理逻辑,只需要我们将对象和对象的一个属性传入就行了。但是有如下限制:
The object property that you are animating must have a setter function (in camel case) in the form of set().
如果没有的话,有三个方法来解决它:1.Add the setter method to the class if you have the rights to do so. 2.Use a wrapper class that you have rights to change and have that wrapper receive the value with a valid setter method and forward it to the original object. 3.Use ValueAnimator instead.
the object property that you are animating must have a getter function that is used to obtain the starting value of the animation. The getter function must be in the form of get()。之所以需要一个get方法,是因为当我们只传入了一个value时,他会作为endvalue,所以为了获取startValue,必须有这个方法,不然没有办法实现效果。
属性值要对应一致
Depending on what property or object you are animating, you might need to call the invalidate() method on a View to force the screen to redraw itself with the updated animated values. 也就是为了更新界面,必须调用这个方法。我们在onAnimationUpdate中调用。
TimeInterplotar与TypeEvaluator的区别
通过系统给出来的例子,很多都是在timeInterplotor中获取到变化率,然后在TypeEvaluator中进行简单的数学运算。其实他们两个中都可以进行变化率的计算,并且TypeEvaluator还可以进行返回。最主要的区别是TypeEvaluator中可以获取三个参数而TimeInterpolator只能获得一个参数。所以如果有些时候需要用到startValue和endValue,我们就需要使用TypeEvaluator来定义变换方法。ViewpropertyAnimator
可以方便的为某个View的多个属性添加并行的动画,只使用一个ViewPropertyAnimator对象就可以完成。它的行为更像一个ObjectAnimator,因为它修改的是对象的实际属性值。但它为一次性给多个属性添加动画提供了方便,而且使用ViewPropertyAnimator的代码更连贯更易读。下面是使用多个Objectanimator,一个Objectanimator,一个ViewPropertyanimator的区别
bjectAnimator animX = ObjectAnimator.ofFloat(myView, "x", 50f); ObjectAnimator animY = ObjectAnimator.ofFloat(myView, "y", 100f); AnimatorSet animSetXY = new AnimatorSet(); animSetXY.playTogether(animX, animY); animSetXY.start();
一个ObjectAnimator和多个PropertyValuesHolder相结合
PropertyValuesHolder pvhX = PropertyValuesHolder.ofFloat("x", 50f); PropertyValuesHolder pvhY = PropertyValuesHolder.ofFloat("y", 100f); ObjectAnimator.ofPropertyValuesHolder(myView, pvhX, pvyY).start();
viewpropertyAnimator只用一行代码
myView.animate().x(50f).y(100f);//myView.animate()直接返回一个ViewPropertyAnimator对象
补充:propertyValuesHolder的属性设置
PropertyValuesHolder pvsX = PropertyValuesHolder.ofFloat(“scaleX”, 1f, 0.7f);
PropertyValuesHolder tlSWY = PropertyValuesHolder.ofFloat(“translationY”, -50f, 0f);
PropertyValuesHolder apSWY = PropertyValuesHolder.ofFloat(“alpha”, 0.25f, 1f);
PropertyValuesHolder roSWXY = PropertyValuesHolder.ofFloat(“rotation”, -25f, 0f);
第一个是初始值,第二个是end值(并且是以你的初始设置或者在xml中的位置或大小作为参考值0或1),translation以下右为正,rotation以顺时针为正,逆时针为负。
keyFrame
keyframe是由一个键值对组成,可以定制动画在某一特定时间点的特定状态。可以有自己的插值器,用于控制自己前一帧和后一帧的动画keyframe.ofFloat(0.5f,300f)
第一个参数是时间参数,第二个参数是属性值。这个keyframe可以很好解决ObjectAnimator等无法精确控制时间点的动画的情况。
当我们给animator设置插值器时,我们是给整体进行的设置,但是我们仍然可以为这个时间点即keyframe对象设置插值器。
使用方法:
Keyframe kf0 = Keyframe.ofFloat(0f, 0f); Keyframe kf1 = Keyframe.ofFloat(.5f, 360f); Keyframe kf2 = Keyframe.ofFloat(1f, 0f); PropertyValuesHolder pvhRotation = PropertyValuesHolder.ofKeyframe("rotation", kf0, kf1, kf2);//动画属性名,可变参数 ObjectAnimator rotationAnim = ObjectAnimator.ofPropertyValuesHolder(target, pvhRotation) rotationAnim.setDuration(5000);
XML中定义Animator
xml文件中支持这三者:- valueAnimator:
- objectAnimator:
- AnimatorSet:
<set android:ordering="sequentially"> <set> <objectAnimator android:propertyName="x" android:duration="500" android:valueTo="400" android:valueType="intType"/> <objectAnimator android:propertyName="y" android:duration="500" android:valueTo="300" android:valueType="intType"/> </set> <objectAnimator android:propertyName="alpha" android:duration="500" android:valueTo="1f"/> </set> // 然后可以这样使用 AnimatorSet set = (AnimatorSet) AnimatorInflater.loadAnimator(myContext, R.anim.property_animator); set.setTarget(myObject); set.start();
相关文章推荐
- Android 动画系列之属性(Property)动画详解
- Android中属性动画Property Animation使用示例(三)
- Android 动画详解之属性动画(Property Animation)
- Android-Property_Animation介绍及基本实现(属性动画)
- Android属性动画完全解析(下),Interpolator和ViewPropertyAnimator的用法
- Android中属性动画Property Animation使用示例(二)
- Android属性动画完全解析(下),Interpolator和ViewPropertyAnimator的用法
- Android属性动画完全解析(下),Interpolator和ViewPropertyAnimator的用法
- Android属性动画PropertyAnimation系列三之LayoutTransition(布局容器动画)
- Android使用属性动画property animation,实现分散式弹出菜单
- Android中属性动画Property Animation使用示例(一)
- android的属性动画的propertyName--------Property Animation
- Android属性动画完全解析(下),Interpolator和ViewPropertyAnimator的用法
- Android中属性动画Property Animation使用示例(四)
- Android中属性动画Property Animation使用示例(一)
- Android属性动画Property Animation系列二之ObjectAnimator
- Android属性动画Property Animation系列三之LayoutTransition(布局容器动画)
- Android 动画之三 Property Animation—— 属性(Property)动画 【Animator提供基类】
- Android属性动画完全解析(下),Interpolator和ViewPropertyAnimator的用法
- Android属性动画完全解析(下),Interpolator和ViewPropertyAnimator的用法