Android开发 之 属性动画(自定义ValueAnimator的TypeEvaluator)

自定义ValueAnimator的TypeEvaluator

翻译过来就是类型计算器,对,就是一个计算器,只不过这计算器的计算规则由你设定,也就是你要继承重写喽。

对于valueAnimator类中的其他ofXXx方法,其实都是有计算器,默认好像是FloatEvaluator的。

本文这次改变属性是一个点的x,y跟随要给曲线运动动画效果:
Android开发 之 属性动画(自定义ValueAnimator的TypeEvaluator)_第1张图片

妈的,这 gif录制工具太差了,变成绿低了。但是还是能看出小蝌蚪在动。

下面看代码:
activity的布局文件就一个imageview,等会这个就是存放你的运动点的容器。


    

activity代码
这里是根据imageview的尺寸 去设置起点和终点的。
有个iamgeview尺寸的获取,利用视图树,当iamgeview绘制好了,再去获取其宽高。
自定义了一个pointDrawable,和myself类下面有代码
package com.example.zxq.bsquxian;

import android.animation.ValueAnimator;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.view.View;
import android.view.ViewTreeObserver;
import android.view.animation.LinearInterpolator;
import android.widget.ImageView;

import com.example.zxq.bsquxian.zidiyizhidonghua.MySelf;
import com.example.zxq.bsquxian.zidiyizhidonghua.Point;
import com.example.zxq.bsquxian.zidiyizhidonghua.PointDrawable;

/**
 * Created by Administrator on 2017/7/26 0026.
 */

public class ShuxingAnmationActivity extends AppCompatActivity {
    private ImageView iv;
    private int width;
    private int height;
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_shuxingdonghua);
        iv= (ImageView) findViewById(R.id.iv);
        int intw=View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
        int inth=View.MeasureSpec.makeMeasureSpec(0,View.MeasureSpec.UNSPECIFIED);
        iv.measure(intw, inth);
        iv.getViewTreeObserver().addOnGlobalLayoutListener(
                new ViewTreeObserver.OnGlobalLayoutListener() {
                    @Override
                    public void onGlobalLayout() {

                        height = iv.getHeight();
                        width = iv.getWidth();
                        iv.getViewTreeObserver().removeGlobalOnLayoutListener(this);

                        final PointDrawable pointDrawable=new PointDrawable(width,height);
                        iv.setBackground(pointDrawable);
                        ValueAnimator valueAnimator = ValueAnimator.ofObject(new MySelf(), pointDrawable.getStartPoint(), pointDrawable.getEndPoint());
                        valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
                            @Override
                            public void onAnimationUpdate(ValueAnimator valueAnimator) {
                                Point animatedValue = (Point) valueAnimator.getAnimatedValue();
                                pointDrawable.setCurrentPoint(animatedValue);
                                pointDrawable.invalidateSelf();
                            }
                        });
                        valueAnimator.setDuration(5000);
                        valueAnimator.setInterpolator(new LinearInterpolator());//设置插值器
                        valueAnimator.start();
                    }
                });
    }
}

pointDrawable的代码:
创建这个对象的时候,创建了两个点,起点和终点,还有画笔
在draw()方法中去绘制图形
在setcurrentpoint()方法中,当前运动点的位置传进来。这个方法是在activity中动画运行监听中调用的。在上面
package com.example.zxq.bsquxian.zidiyizhidonghua;

import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.ColorFilter;
import android.graphics.Paint;
import android.graphics.drawable.Drawable;
import android.graphics.drawable.PictureDrawable;
import android.support.annotation.IntRange;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.util.Log;

import java.util.ArrayList;
import java.util.List;

/**
 * Created by Administrator on 2017/7/26 0026.
 */

public class PointDrawable extends Drawable {
    private  Point startPoint;
    private  Point endPoint;
    private Point currentPoint;
    private final Paint paint;
    private List list=new ArrayList();

    public void setCurrentPoint(Point currentPoint) {
        this.currentPoint = currentPoint;
    }
    public void setStartPoint(Point startPoint) {
        this.startPoint = startPoint;
    }

    public void setEndPoint(Point endPoint) {
        this.endPoint = endPoint;
    }
    public Point getStartPoint() {
        return startPoint;
    }

    public Point getEndPoint() {
        return endPoint;
    }
    public PointDrawable(int width,int height){
        startPoint = new Point(0,height/2);
        endPoint = new Point(width,height/2);
        paint = new Paint();
        paint.setStyle(Paint.Style.FILL);
        paint.setAntiAlias(true);
        paint.setColor(Color.GREEN);
    }
    @Override
    public void draw(@NonNull Canvas canvas) {
        canvas.drawColor(Color.BLACK);
        if(currentPoint!=null)
        {
            Log.e("jinlai",currentPoint.getX()+"???"+currentPoint.getY());
            if(list.size()<20)
            {
                list.add(currentPoint);
            }else{
                list.remove(0);
                list.add(currentPoint);
            }
            for (int i=0;i

MySelf类就是真个点运动位置的计算方法
实现TypeEvaluator接口
方法中的那两个点就是activity代码中的创建动画传进来的开始和结束点,x成线性变化,y成正玄曲线变化。
package com.example.zxq.bsquxian.zidiyizhidonghua;

import android.animation.TypeEvaluator;
import android.widget.Button;

/**
 * Created by Administrator on 2017/7/26 0026.
 */

public class MySelf implements TypeEvaluator {
    @Override
    public Point evaluate(float v, Point point, Point t1) {
        int x = (int) (v*(t1.getX()-point.getX()));
        int y = (int) (50 * (float) (Math.sin(0.01 * Math.PI * x)) +200);
        return new Point(x,y);
    }
}

这就是整个过程。主要用途就是根据自己的计算规则实现动态计算,获取要的数据,然后在 

你可能感兴趣的:(Android,特效,TypeEvaluator,ValueAnimator,动画,值动画)