目录
????????Android属性动画是一种强大的动画系统,它可以用于在Android应用程序中创建平滑的动画效果。属性动画的作用效果就是:在一个指定的时间段内将对象的一个属性的属性值动态地变化到另一个属性值。
????????属性动画的核心概念是值动画器(ValueAnimator)和对象动画器(ObjectAnimator)。值动画器可以通过指定起始值和结束值来创建动画,然后可以通过监听动画的更新事件来更新视图的属性。对象动画器则更加灵活,可以直接对对象的属性进行动画处理。
Android属性动画的使用步骤如下:
ValueAnimator:值动画器,用于对一个属性的值进行动画处理。它可以通过指定起始值和结束值,以及动画的时长、插值器等属性来创建动画。
ObjectAnimator:对象动画器,用于对一个对象的属性进行动画处理。与值动画器不同,对象动画器可以直接对对象的属性进行动画操作,而不需要通过监听器手动更新属性值。
AnimatorSet:动画集合,用于组合多个动画,并设置动画之间的顺序、延迟和并发等。通过AnimatorSet,可以实现复杂的动画效果,例如同时播放多个动画、按顺序播放动画或者设置动画的循环等。
ObjectAnimator.PropertyValuesHolder:属性值持有者,用于同时对多个属性进行动画处理。可以通过PropertyValuesHolder同时对多个属性指定起始值和结束值,并将它们传递给ObjectAnimator来创建动画。
????????这些类都属于Android动画框架的一部分,我们可以通过它们来创建各种动画效果,并提供丰富的方法和属性来控制动画的行为和特性。
? ? ? ??ObjectAnimator类是属性动画中非常重要的一个类,可以通过该类对View不仅可以实现一些基本的移、旋转、缩放和透明度四种基本变换动画,还能实现一些其他属性值的变换动画。
????????实现方式既可以通过Java代码,也可以通过XML方式来实现,下面我们来分别介绍下两种方式基本用法。
? ? ? ? 首先我们先来看一下ObjectAnimator 类最基本的方法
public static ObjectAnimator ofFloat(Object target, String propertyName, float... values) {
ObjectAnimator anim = new ObjectAnimator(target, propertyName);
anim.setFloatValues(values);
return anim;
}
????????方法中第一个参数Object target 的作用对象通常是View,也就是Android中的控件或布局。
????????方法中第二个参数String propertyName 通常是需要执行动画的属性,具体值如下表所示
? ? ? ? ??属性?? ?????????????????????????????????????????????????值的用法
????????rotation?? ?????????????????????????????????以屏幕方向为轴的旋转度数
????????alpha?? ?????????????????????????????????????????????????透明度
translationX / translationY?? ?????????????????X/Y方向的位移
?????scaleX /scaleY?? ?????????????????????????X/Y方向的缩放倍数
rotationX / rotationY?? ???????????????????以X/Y轴为轴的旋转度数
????????
????????方法中第三个参数float... values 表示属性的变换范围,该参数可以传多个值。
ImageView imageView = findViewById(R.id.imageView);
ObjectAnimator animator = ObjectAnimator.ofFloat(imageView,"rotationY",0f,360f)
.setDuration(2000);
animator.star();
//动画延迟500ms执行
animator.setStartDelay(500);
//执行重复次数 +1
animator.setRepeatCount(3);
// 设置动画重复播放模式 RESTART -执行完一遍后重新执行
// REVERSE -执行完一遍后 从末位置往前执行
animator.setRepeatMode(ValueAnimator.RESTART);
//监听值变换
animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
Log.i("MainActivity","value:" +animation.getAnimatedValue());
}
});
animator.start();
用XML
实现对象动画
1、在res
目录下新建animator
文件夹
2、animator
文件夹下创建动画XML文件,如rotatey_property.xml
往该xml文件中输入如下代码?
<?xml version="1.0" encoding="utf-8"?>
<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="2000"
android:propertyName="rotationY"
android:valueFrom="0"
android:valueTo="360"
android:valueType="floatType"
>
</objectAnimator>
Java代码中通过加载该xml启动动画
animator11 = AnimatorInflater.loadAnimator(getApplicationContext(),R.animator.rotatey_property);
animation11.setTarget(imageView);
animator11.start();
????????值动画通过控制值的变化,之后 手动赋值给对象的属性,从而实现动画。
? ?ValueAnimator
的核心方法如下:
ValueAnimator ofFloat(float... values) -- 浮点型数值
ValueAnimator ofInt(int... values) -- 整型数值
ValueAnimator ofObject(TypeEvaluator evaluator, Object... values) -- 自定义对象类型
????????下面我们来添加值动画,在值动画的监听函数里 来获取值得变化,根据值的变化对控件设置相应的属性。这里的属性可以是控件的任意属性。
ImageView imageView = findViewById(R.id.imageView);
ValueAnimator anim = ValueAnimator.ofInInt0, 360);
anim.setDuration(5000);
anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
int currentValue = (int) animation.getAnimatedValue();
Log.d("MainActivity", "cuurent value is " + currentValue);
imageView.setRotationY(currentValue);
}
});
anim.start();
效果如上图,这里就不再展示
PropertyValueHolder?
可以让前面的一些动画同时执行。
PropertyValuesHolder alpha1 = PropertyValuesHolder.ofFloat("alpha",0.5f,1f);
PropertyValuesHolder scaleX1 = PropertyValuesHolder.ofFloat("scaleX", 0f, 1f);
PropertyValuesHolder scaleY1 = PropertyValuesHolder.ofFloat("scaleY", 0f, 1f);
PropertyValuesHolder translateX1 = PropertyValuesHolder.ofFloat("alpha",0.5f,1f);
PropertyValuesHolder translateY1 = PropertyValuesHolder.ofFloat("alpha",0.5f,1f);
PropertyValuesHolder rotate1 = PropertyValuesHolder.ofFloat("rotation", 0, 360);
ValueAnimator animator = ObjectAnimator.ofPropertyValuesHolder(imageView, alpha1,
scaleX1, scaleY1,translateX1,translateY1,rotate1);
animator.setDuration(2000);
animator.start();
????????前面的PropertyValueHolder 类能实现将多个动画同时执行,AnimatorSet类不仅能让多个动画同时执行,还能让多个动画按一定的顺序执行,同时也能穿插多个动画同时执行。
主要的方法如下:
after(Animator anim) 将现有动画插入到传入的动画之后执行
after(long delay) 将现有动画延迟指定毫秒后执行
before(Animator anim) 将现有动画插入到传入的动画之前执行
with(Animator anim) 将现有动画和传入的动画同时执行
ObjectAnimator rotate2 = ObjectAnimator.ofFloat(imageView, "rotation", 0f, 360f);
ObjectAnimator translateX2 = ObjectAnimator.ofFloat(imageView, "translationX", -100, 100f);
ObjectAnimator translateY2 = ObjectAnimator.ofFloat(imageView, "translationY", -100, 100f);
ObjectAnimator scaleX2 = ObjectAnimator.ofFloat(imageView, "scaleX", 0, 1f);
ObjectAnimator scaleY2 = ObjectAnimator.ofFloat(imageView, "scaleY", 0, 1f);
ObjectAnimator alpha2 = ObjectAnimator.ofFloat(imageView, "alpha", 1f, 0f, 1f);
AnimatorSet animSet = new AnimatorSet();
animSet.play(rotate2) // 首先播放 rotate2 动画
.with(alpha2) // 与 rotate2 动画同时播放 alpha2 动画
.after(scaleX2) // 在 rotate2 动画之后播放 scaleX2 动画
.before(translateX2) // 在 scaleX2 动画之前播放 translateX2 动画
.after(1000) // 在 translateX2 动画之后延迟1000毫秒
.before(translateY2) // 在延迟后播放 translateY2 动画
.with(scaleY2); // 与 translateY2 动画同时播放 scaleY2 动画
animSet.setDuration(5000);
animSet.start();