Android Tween and Property Animation的本质区别

来源:互联网 发布:mysql 查询某一年数据 编辑:程序博客网 时间:2024/06/05 20:33

之前只知道这两种动画是有区别的,区别是属性动画会修改View的属性。但是具体怎么回事一直没弄明白。

在阅读了网上的各种博客和源码后,大致搞懂了区别。

Tween动画通过view的matrix和alpha变量对view进行修改,但是并不会修改view自身属性。

而Property动画会修改view的自身属性,动画结束后的效果会实实在在的反应在view上。

例子如下:

MainActivity

package com.none.objectanimatordemo;import android.animation.Animator;import android.animation.AnimatorSet;import android.animation.ObjectAnimator;import android.os.Bundle;import android.support.v7.app.ActionBarActivity;import android.util.Log;import android.view.View;import android.view.animation.Animation;import android.view.animation.ScaleAnimation;import android.widget.Button;import android.widget.ImageView;import android.widget.Toast;public class MainActivity extends ActionBarActivity {    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        final ImageView img = (ImageView) findViewById(R.id.id_img);        img.setImageResource(R.mipmap.ic_launcher);        img.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View v) {                Toast.makeText(MainActivity.this, "Image", Toast.LENGTH_SHORT).show();            }        });        Button btn = (Button) findViewById(R.id.id_btn);        btn.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View v) {                ViewWrapper view = new ViewWrapper(img);                AnimatorSet set = new AnimatorSet();                ObjectAnimator width = ObjectAnimator.ofInt(view, "width", 200, 500).setDuration(3000);                ObjectAnimator height = ObjectAnimator.ofInt(view, "height", 200, 500).setDuration(3000);                set.playTogether(width, height);                set.setDuration(3000).start();                set.addListener(new Animator.AnimatorListener() {                    @Override                    public void onAnimationStart(Animator animation) {                    }                    @Override                    public void onAnimationEnd(Animator animation) {                        Log.d("TAG", "width: " + img.getWidth() + ", height: " + img.getHeight());                    }                    @Override                    public void onAnimationCancel(Animator animation) {                    }                    @Override                    public void onAnimationRepeat(Animator animation) {                    }                });//                ScaleAnimation scale = new ScaleAnimation(1.0f, 4.0f, 1.0f, 4.0f, Animation.RELATIVE_TO_PARENT, 0, Animation.RELATIVE_TO_PARENT, 0);//                scale.setFillAfter(true);//                scale.setDuration(3000);//                img.startAnimation(scale);//                scale.setAnimationListener(new Animation.AnimationListener() {//                    @Override//                    public void onAnimationStart(Animation animation) {////                    }////                    @Override//                    public void onAnimationEnd(Animation animation) {//                        Log.d("TAG", "width: " + img.getWidth() + ", height: " + img.getHeight());//                    }////                    @Override//                    public void onAnimationRepeat(Animation animation) {////                    }//                });            }        });    }    private static class ViewWrapper {        public ViewWrapper(View mTarget) {            this.mTarget = mTarget;        }        private View mTarget;        private int getWidth() {            return mTarget.getLayoutParams().width;        }        private void setWidth(int width) {            mTarget.getLayoutParams().width = width;            mTarget.requestLayout();        }        private int getHeight() {            return mTarget.getLayoutParams().height;        }        private void setHeight(int height) {            mTarget.getLayoutParams().height = height;            mTarget.requestLayout();        }    }}

xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    xmlns:tools="http://schemas.android.com/tools"    android:layout_width="match_parent"    android:layout_height="match_parent"    android:orientation="vertical">    <Button        android:id="@+id/id_btn"        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:background="@drawable/shape_circle"        android:text="@string/hello_world" />    <ImageView        android:id="@+id/id_img"        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:scaleType="centerCrop"/></LinearLayout>

可以对比打印出来的img的宽高。scale动画后img的位置并没有改变,它的宽高也没有发生变化。

property动画则渐变的修改了img的宽高,最终达到了设定值。

例子中的属性动画在修改view的宽高时,会不断的requestlayout,该函数会导致view的measure,layout,draw重复调用。


属性动画会通过反射调用预设的setter和getter函数。


0 0