AnimationCloning 这activity也很简单, 是为了表面 animator可以复制, animatorSet也可以复制, 并且animator可以设置动画的播放顺序,等
public class AnimationCloning extends Activity {
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.animation_cloning);
LinearLayout container = (LinearLayout) findViewById(R.id.container);
final MyAnimationView animView = new MyAnimationView(this);
container.addView(animView);
Button starter = (Button) findViewById(R.id.startButton);
starter.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
animView.startAnimation();
}
});
}
public class MyAnimationView extends View implements ValueAnimator.AnimatorUpdateListener {
public final ArrayList<ShapeHolder> balls = new ArrayList<ShapeHolder>();
AnimatorSet animation = null;
private float mDensity;
public MyAnimationView(Context context) {
super(context);
mDensity = getContext().getResources().getDisplayMetrics().density;//获取像素单位
ShapeHolder ball0 = addBall(50f, 25f);
ShapeHolder ball1 = addBall(150f, 25f);
ShapeHolder ball2 = addBall(250f, 25f);
ShapeHolder ball3 = addBall(350f, 25f);
}
private void createAnimation() {
if (animation == null) {
ObjectAnimator anim1 = ObjectAnimator.ofFloat(balls.get(0), "y",
0f, getHeight() - balls.get(0).getHeight()).setDuration(500);
//0 - 屏幕底部的high 的 y动画 ,改变的是ShapeAnimator的中属性y的值
ObjectAnimator anim2 = anim1.clone();//第二个小球和第一个小球的动作完全一样
anim2.setTarget(balls.get(1));
anim1.addUpdateListener(this);
ShapeHolder ball2 = balls.get(2);
ObjectAnimator animDown = ObjectAnimator.ofFloat(ball2, "y",
0f, getHeight() - ball2.getHeight()).setDuration(500);
animDown.setInterpolator(new AccelerateInterpolator());//向下加速
ObjectAnimator animUp = ObjectAnimator.ofFloat(ball2, "y",
getHeight() - ball2.getHeight(), 0f).setDuration(500);
animUp.setInterpolator(new DecelerateInterpolator());//向上移动的时候减速
AnimatorSet s1 = new AnimatorSet();
s1.playSequentially(animDown, animUp);//动画播放的顺序
/*如果注释掉这两句代码会导致第三个球只有向下的动画 没有向上的动画
第四个球不会有动画,这是因为第一第二个球只在500ms内调用了onDraw,遍历每个球并将其画出来.
500ms之后 anim1和anim2都执行完了没有人回调 onAnimationUpdate 进而回调onDraw了.
*/
animDown.addUpdateListener(this);
animUp.addUpdateListener(this);
AnimatorSet s2 = (AnimatorSet) s1.clone();//和第三个球一样的动画 ,AnimatorSet 也可以clone
s2.setTarget(balls.get(3));
animation = new AnimatorSet();
animation.playTogether(anim1, anim2, s1); //三个动画以前播放
animation.playSequentially(s1, s2);//设置s1播放之后再让s2播放
}
}
private ShapeHolder addBall(float x, float y) {
OvalShape circle = new OvalShape();//android中的画圆球的类
circle.resize(50f * mDensity, 50f * mDensity);
ShapeDrawable drawable = new ShapeDrawable(circle);//把这圆转为时间的drawable
ShapeHolder shapeHolder = new ShapeHolder(drawable);//保存一些怎么画这个球的参数
shapeHolder.setX(x - 25f);
shapeHolder.setY(y - 25f);
int red = (int)(100 + Math.random() * 155);
int green = (int)(100 + Math.random() * 155);
int blue = (int)(100 + Math.random() * 155);
int color = 0xff000000 | red << 16 | green << 8 | blue;
Paint paint = drawable.getPaint(); //new Paint(Paint.ANTI_ALIAS_FLAG);
int darkColor = 0xff000000 | red/4 << 16 | green/4 << 8 | blue/4; //绘制阴影
RadialGradient gradient = new RadialGradient(37.5f, 12.5f,
50f, color, darkColor, Shader.TileMode.CLAMP); //径向的影音效果
paint.setShader(gradient);
shapeHolder.setPaint(paint);
balls.add(shapeHolder);
return shapeHolder;
}
@Override
protected void onDraw(Canvas canvas) {//遍历
for (int i = 0; i < balls.size(); ++i) {
ShapeHolder shapeHolder = balls.get(i);
canvas.save();
//原来在(100,100),然后translate(1,1)新的坐标原点在(101,101)而不是(1,1)
canvas.translate(shapeHolder.getX(), shapeHolder.getY());
shapeHolder.getShape().draw(canvas);
canvas.restore();
}
}
public void startAnimation() {
createAnimation();
animation.start();
}
public void onAnimationUpdate(ValueAnimator animation) {
invalidate();
}
}
}
这些动画可以从xml中load 注意 xml中的属性值必须 是Target (也就是我们的小球)必须有的!
private void createAnimation() {
Context appContext = AnimationLoading.this;
if (animation == null) {
ObjectAnimator anim = (ObjectAnimator) AnimatorInflater.
loadAnimator(appContext, R.anim.object_animator); //从xml中load animator 里面指定了改变那个属性的值
anim.addUpdateListener(this);
anim.setTarget(balls.get(0));
ValueAnimator fader = (ValueAnimator) AnimatorInflater.
loadAnimator(appContext, R.anim.animator);//也是从xml中设置
fader.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
public void onAnimationUpdate(ValueAnimator animation) {//动画帧变化的时候根据ValueAnimator设置其alpha
balls.get(1).setAlpha((Float) animation.getAnimatedValue());
}
});
AnimatorSet seq =
(AnimatorSet) AnimatorInflater.loadAnimator(appContext,
R.anim.animator_set);
seq.setTarget(balls.get(2));
ObjectAnimator colorizer = (ObjectAnimator) AnimatorInflater.
loadAnimator(appContext, R.anim.color_animator);//可以改变颜色改变的属性是color
colorizer.setTarget(balls.get(3));
animation = new AnimatorSet();
((AnimatorSet) animation).playTogether(anim, fader, seq, colorizer);
}
}
<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="1000"
android:valueTo="200"
android:valueType="floatType"
android:propertyName="y"
android:repeatCount="1"
android:repeatMode="reverse"/>
<animator xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="1000"
android:valueFrom="1"
android:valueTo="0"
android:valueType="floatType"
android:repeatCount="1"
android:repeatMode="reverse"/>
<set>
<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="1000"
android:valueTo="200"
android:valueType="floatType"
android:propertyName="x"
android:repeatCount="1"
android:repeatMode="reverse"/>
<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="1000"
android:valueTo="400"
android:valueType="floatType"
android:propertyName="y"
android:repeatCount="1"
android:repeatMode="reverse"/>
</set>
<objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="1000"
android:valueFrom="#0f0"
android:valueTo="#00ffff"
android:propertyName="color"
android:repeatCount="1"
android:repeatMode="reverse"/>
本文介绍如何在Android中实现动画克隆,利用Animator、AnimatorSet和ObjectAnimator进行动画的复制与播放顺序的控制,展示动画加载与关键属性设置的方法。
803

被折叠的 条评论
为什么被折叠?



