android 动画-Tween Animation(一)动画体系简介,涉及到的核心类、核心接口讲解(下)

来源:互联网 发布:我与网络演讲稿2000字 编辑:程序博客网 时间:2024/06/08 03:34
三、核心接口
1、AnimationListener
/**
* <p>An animation listener receives notifications from an animation.
* Notifications indicate animation related events, such as the end or the
* repetition of the animation.</p>
*/
public static interface AnimationListener {
    void onAnimationStart(Animation animation);
    void onAnimationEnd(Animation animation);
    void onAnimationRepeat(Animation animation);
}
    为动画设置监听,看具体方法名称就可以知道;可以实现该监听接口,在动画开始时,动画结束时,动画重复时加入自己的逻辑实现。使用很简单,不再赘述。

2、Interpolator
    Interpolator 被用来修饰动画效果,定义动画的变化率,实现accelerated(加速),decelerated(减速),repeated(重复),bounced(弹跳)等效果。
    从API 11开始,所有的Interpolator都是从TimeInterpolator接口派生来的。TimeInterpolator只定义了一个方法:
public abstract float getInterpolation(float input);
输入值是0.0-1.0的浮点数,表示动画的进度。0.0表示开始,1.0表示结束。返回值是输入值的函数,值域也在0.0-1.0中。
Interpolator 接口实现了TimeInterpolator接口,但是并没有添加新的 方法。Interpolator接口在API11之前就有了,只是继承关系不同罢了。
从API 22开始,增加了BaseInterpolator抽象类的实现。
Andorid为我们实现了几种常用的差值器,包括:
    LinearInterpolator   以常量速率改变
    AccelerateInterpolator  在动画开始的地方速率改变比较慢,然后开始加速
    DecelerateInterpolator 在动画开始的地方快然后慢
     AccelerateDecelerateInterpolator 在动画开始与结束的地方速率改变比较慢,在中间的时候加速
    AnticipateInterpolator 开始的时候向后然后向前甩

    AnticipateOvershootInterpolator 开始的时候向后然后向前甩一定值后返回最后的值

    BounceInterpolator   动画结束的时候弹起

    CycleInterpolator 动画循环播放特定的次数,速率改变沿着正弦曲线

    OvershootInterpolator    向前甩一定值后再回到原来位置
下面从源码的角度来分析下这些常用的插值器:
(1)LinearInterpolator://这个最简单,是线性变化的,不再给出图示
public float getInterpolation(float input){
    return input;
}

(2)AccelerateInterpolator 
    构造时可以指定系数,当系数为1.0f时,效果为y=x^2的抛物线,非1.0f时,则为x的系数次方,可以为非整数。实现加速效果。
/**
 * An interpolator where the rate of change starts out slowly and 
 * and then accelerates.
 *
 */
public class AccelerateInterpolator implements Interpolator {
    private final float mFactor;
    private final double mDoubleFactor;

    public AccelerateInterpolator() {
        mFactor = 1.0f;
        mDoubleFactor = 2.0;
    }

    /**
     * Constructor
     * 
     * @param factor Degree to which the animation should be eased. Seting
     *        factor to 1.0f produces a y=x^2 parabola. Increasing factor above
     *        1.0f  exaggerates the ease-in effect (i.e., it starts even
     *        slower and ends evens faster)
     */
    public AccelerateInterpolator(float factor) {
        mFactor = factor;
        mDoubleFactor = 2 * mFactor;
    }

    public AccelerateInterpolator(Context context, AttributeSet attrs) {
        TypedArray a =
            context.obtainStyledAttributes(attrs, com.android.internal.R.styleable.AccelerateInterpolator);

        mFactor = a.getFloat(com.android.internal.R.styleable.AccelerateInterpolator_factor, 1.0f);
        mDoubleFactor = 2 * mFactor;

        a.recycle();
    }

    public float getInterpolation(float input) {
        if (mFactor == 1.0f) {
            return input * input;
        } else {
            return (float)Math.pow(input, mDoubleFactor);
        }
    }
}


(3)DecelerateInterpolator 1.0f时,产生倒过来的y=x^2抛物线。实现减速效果;
/**
 * An interpolator where the rate of change starts out quickly and 
 * and then decelerates.
 *
 */
public class DecelerateInterpolator implements Interpolator {
    public DecelerateInterpolator() {
    }

    /**
     * Constructor
     * 
     * @param factor Degree to which the animation should be eased. Setting factor to 1.0f produces
     *        an upside-down y=x^2 parabola. Increasing factor above 1.0f makes exaggerates the
     *        ease-out effect (i.e., it starts even faster and ends evens slower)
     */
    public DecelerateInterpolator(float factor) {
        mFactor = factor;
    }

    public DecelerateInterpolator(Context context, AttributeSet attrs) {
        TypedArray a =
            context.obtainStyledAttributes(attrs, com.android.internal.R.styleable.DecelerateInterpolator);

        mFactor = a.getFloat(com.android.internal.R.styleable.DecelerateInterpolator_factor, 1.0f);

        a.recycle();
    }

    public float getInterpolation(float input) {
        float result;
        if (mFactor == 1.0f) {
            result = (float)(1.0f - (1.0f - input) * (1.0f - input));
        } else {
            result = (float)(1.0f - Math.pow((1.0f - input), 2 * mFactor));
        }
        return result;
    }

    private float mFactor = 1.0f;
}


(4)AccelerateDecelerateInterpolator  
    以0.5为界,先快后慢。
/**
 * An interpolator where the rate of change starts and ends slowly but
 * accelerates through the middle.
 * 
 */
public class AccelerateDecelerateInterpolator implements Interpolator {
    public AccelerateDecelerateInterpolator() {
    }

    @SuppressWarnings({"UnusedDeclaration"})
    public AccelerateDecelerateInterpolator(Context context, AttributeSet attrs) {
    }

    public float getInterpolation(float input) {
        return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;
    }
}


(5)AnticipateInterpolator  
    张力的效果。这个是开始的时候向后,然后向前甩的效果。公式:a(t) = t * t * ((tension + 1) * t - tension)。
/**
 * An interpolator where the change starts backward then flings forward.
 */
public class AnticipateInterpolator implements Interpolator {
    private final float mTension;

    public AnticipateInterpolator() {
        mTension = 2.0f;
    }

    /**
     * @param tension Amount of anticipation. When tension equals 0.0f, there is
     *                no anticipation and the interpolator becomes a simple
     *                acceleration interpolator.
     */
    public AnticipateInterpolator(float tension) {
        mTension = tension;
    }

    public AnticipateInterpolator(Context context, AttributeSet attrs) {
        TypedArray a = context.obtainStyledAttributes(attrs,
                com.android.internal.R.styleable.AnticipateInterpolator);

        mTension =
                a.getFloat(com.android.internal.R.styleable.AnticipateInterpolator_tension, 2.0f);

        a.recycle();
    }

    public float getInterpolation(float t) {
        // a(t) = t * t * ((tension + 1) * t - tension)
        return t * t * ((mTension + 1) * t - mTension);
    }
}


(6)AnticipateOvershootInterpolator 开始的时候向后然后向前甩一定值后返回最后的值
/**
 * An interpolator where the change starts backward then flings forward and overshoots
 * the target value and finally goes back to the final value.
 */
public class AnticipateOvershootInterpolator implements Interpolator {
    private final float mTension;

    public AnticipateOvershootInterpolator() {
        mTension = 2.0f * 1.5f;
    }

    /**
     * @param tension Amount of anticipation/overshoot. When tension equals 0.0f,
     *                there is no anticipation/overshoot and the interpolator becomes
     *                a simple acceleration/deceleration interpolator.
     */
    public AnticipateOvershootInterpolator(float tension) {
        mTension = tension * 1.5f;
    }

    /**
     * @param tension Amount of anticipation/overshoot. When tension equals 0.0f,
     *                there is no anticipation/overshoot and the interpolator becomes
     *                a simple acceleration/deceleration interpolator.
     * @param extraTension Amount by which to multiply the tension. For instance,
     *                     to get the same overshoot as an OvershootInterpolator with
     *                     a tension of 2.0f, you would use an extraTension of 1.5f.
     */
    public AnticipateOvershootInterpolator(float tension, float extraTension) {
        mTension = tension * extraTension;
    }

    public AnticipateOvershootInterpolator(Context context, AttributeSet attrs) {
        TypedArray a = context.obtainStyledAttributes(attrs, AnticipateOvershootInterpolator);

        mTension = a.getFloat(AnticipateOvershootInterpolator_tension, 2.0f) *
                a.getFloat(AnticipateOvershootInterpolator_extraTension, 1.5f);

        a.recycle();
    }

    private static float a(float t, float s) {
        return t * t * ((s + 1) * t - s);
    }

    private static float o(float t, float s) {
        return t * t * ((s + 1) * t + s);
    }

    public float getInterpolation(float t) {
        // a(t, s) = t * t * ((s + 1) * t - s)
        // o(t, s) = t * t * ((s + 1) * t + s)
        // f(t) = 0.5 * a(t * 2, tension * extraTension), when t < 0.5
        // f(t) = 0.5 * (o(t * 2 - 2, tension * extraTension) + 2), when t <= 1.0
        if (t < 0.5f) return 0.5f * a(t * 2.0f, mTension);
        else return 0.5f * (o(t * 2.0f - 2.0f, mTension) + 2.0f);
    }
}


(7)OvershootInterpolator    
    向前甩一定值后再回到原来位置
/**
 * An interpolator where the change flings forward and overshoots the last value
 * then comes back.
 */
public class OvershootInterpolator implements Interpolator {
    private final float mTension;

    public OvershootInterpolator() {
        mTension = 2.0f;
    }

    /**
     * @param tension Amount of overshoot. When tension equals 0.0f, there is
     *                no overshoot and the interpolator becomes a simple
     *                deceleration interpolator.
     */
    public OvershootInterpolator(float tension) {
        mTension = tension;
    }

    public OvershootInterpolator(Context context, AttributeSet attrs) {
        TypedArray a = context.obtainStyledAttributes(attrs,
                com.android.internal.R.styleable.OvershootInterpolator);

        mTension =
                a.getFloat(com.android.internal.R.styleable.OvershootInterpolator_tension, 2.0f);

        a.recycle();
    }

    public float getInterpolation(float t) {
        // _o(t) = t * t * ((tension + 1) * t + tension)
        // o(t) = _o(t - 1) + 1
        t -= 1.0f;
        return t * t * ((mTension + 1) * t + mTension) + 1.0f;
    }
}



(8)BounceInterpolator   
    动画结束的时候弹起,有点玻璃球落地时的感觉

/**
 * An interpolator where the change bounces at the end.
 */
public class BounceInterpolator implements Interpolator {
    public BounceInterpolator() {
    }

    @SuppressWarnings({"UnusedDeclaration"})
    public BounceInterpolator(Context context, AttributeSet attrs) {
    }

    private static float bounce(float t) {
        return t * t * 8.0f;
    }

    public float getInterpolation(float t) {
        // _b(t) = t * t * 8
        // bs(t) = _b(t) for t < 0.3535
        // bs(t) = _b(t - 0.54719) + 0.7 for t < 0.7408
        // bs(t) = _b(t - 0.8526) + 0.9 for t < 0.9644
        // bs(t) = _b(t - 1.0435) + 0.95 for t <= 1.0
        // b(t) = bs(t * 1.1226)
        t *= 1.1226f;
        if (t < 0.3535f) return bounce(t);
        else if (t < 0.7408f) return bounce(t - 0.54719f) + 0.7f;
        else if (t < 0.9644f) return bounce(t - 0.8526f) + 0.9f;
        else return bounce(t - 1.0435f) + 0.95f;
    }
}



(9)CycleInterpolator 
    动画循环播放特定的次数,速率改变沿着正弦曲线

    /**

 * Repeats the animation for a specified number of cycles. The
 * rate of change follows a sinusoidal pattern.
 *
 */
public class CycleInterpolator implements Interpolator {
    public CycleInterpolator(float cycles) {
        mCycles = cycles;
    }

    public CycleInterpolator(Context context, AttributeSet attrs) {
        TypedArray a =
            context.obtainStyledAttributes(attrs, com.android.internal.R.styleable.CycleInterpolator);

        mCycles = a.getFloat(com.android.internal.R.styleable.CycleInterpolator_cycles, 1.0f);

        a.recycle();
    }

    public float getInterpolation(float input) {
        return (float)(Math.sin(2 * mCycles * Math.PI * input));
    }

    private float mCycles;
}



好了,到此为止,android 动画-Tween Animation(一)动画体系简介,涉及到的核心类、核心接口讲解的内容华商一个完美的句号,以上内容纯属理论内容,没有一个例子,具体的demo在下一节会看到。同时,郑重声明,以上内容绝大多数非本人原创,本人本着整理的原则,取精华,去糟粕,重归纳,加上自己的理解,组成这个第一讲,主要参考资料如下:

参考资料:
http://blog.csdn.net/yanbober/article/details/46481171
http://www.cnblogs.com/mengdd/p/3346003.html
http://yq.aliyun.com/articles/3016?spm=5176.100240.searchblog.13.mCyqhU

0 0