• android 补间动画和Animation


    介绍:

    补间动画是一种设定动画开始状态、结束状态,其中间的变化由系统计算补充。这也是他叫做补间动画的原因。

    补间动画由Animation类来实现具体效果,包括平移(TranslateAnimation)、缩放(ScaleAnimation)、旋转(RotateAnimation)、透明度(AlphaAnimation)四个子类,四种变化。

    实现:

    补间动画的四种变化效果(四个类)允许通过xml设置,也可以通过初始化类来设置。xml比较简单,java比较灵活。

    1、通过xml设置补间动画

    <?xml version="1.0" encoding="utf-8"?>
    <set xmlns:android="http://schemas.android.com/apk/res/android"
        android:interpolator="@[package:]anim/interpolator_resource"
        android:shareInterpolator=["true" | "false"] >
        <alpha
            android:fromAlpha="float"
            android:toAlpha="float" />
        <scale
            android:fromXScale="float"
            android:toXScale="float"
            android:fromYScale="float"
            android:toYScale="float"
            android:pivotX="float"
            android:pivotY="float" />
        <translate
            android:fromXDelta="float"
            android:toXDelta="float"
            android:fromYDelta="float"
            android:toYDelta="float" />
        <rotate
            android:fromDegrees="float"
            android:toDegrees="float"
            android:pivotX="float"
            android:pivotY="float" />
        <set>
            ...
        </set>
    </set>
    android:interpolator为动画的变化速度【可以单独设置,可以直接放在set里面】
      可以设置多种速度变化方式,这里只列出匀速、加速、减速
      匀速 @android:anim/linear_interpolator
      加速 @android:anim/accelerate_interppolator
      减速 @android:anim/decelerate_interpolator

    android:shareInterpolator为是否给所有子元素共享动画变化速度【放在set里面设置是否共享】


    android:fillAfter动画显示结束保持最后一帧【true:最后一帧】
    android:fillBefore动画显示结束保持第一帧【true:第一帧】


    android:duration动画播放时间【单位毫秒,每个动画都需要设置,否则没有效果】


    android:startOffset动画装载完成后需要等待多少时间才能启动【单位毫秒】


    透明度
    android:fromAlpha为动画开始的透明度【0:完全透明,1:完全不透明】
    android:toAlpha为动画结束的透明度

    缩放
    android:fromXScale、android:fromYScale为动画开始X,Y方向上的缩放比例【0:小的没有,1:原本大小】
    android:toXScale、android:toYScale为动画开始X,Y方向上的缩放比例
    android:pivotX、android:pivotY为动画在X,Y方向上的缩放中心点(比如设置为0,0那么就是宽和高向左上角缩小)【例如:50%是距左边界图片一半的距离】


    平移
    android:fromXDelta、android:fromYDelta为动画平移的起始点
    android:toXDelta、android:toYDelta为动画平移的结束点

    旋转
    android:fromDegrees为动画旋转的起始角度【0:不动,180:转半圈,360:转一圈,3600:转10圈,-180逆时针转半圈】
    android:toDegrees为动画旋转的结束角度
    android:pivotX、android:pivotY为动画旋转的中心点【例如:50%是距左边界图片一半的距离】


    以上每一个都可以在java代码中通过setXXX来设置。

    通过xml新建完动画资源还需要使用AnimationUtils进行装载。
    final Animation anim = AnimationUtils
                .loadAnimation(this, R.anim.anim);

    上面的R.anim.anim就是上面用xml写出来的动画文件。

    其实补间动画是一种View Animation,是专门作用在View上的。

    所以在我们使用的时候,直接调用View的startAnimation方法就好了。

    flower.startAnimation(reverse);

    代码中的flower是一个ImageView。



    2、除了使用xml定义动画以外,还可以直接新建一个相应的对象。

    新建对象时构造函数的参数和上面的xml是一样的,就不详细介绍了~

    平移(TranslateAnimation)
    构造函数
    public TranslateAnimation(int fromXType, float fromXValue, int toXType, float toXValue,
                int fromYType, float fromYValue, int toYType, float toYValue)
    fromXType、toXType、fromYType、toYType指的是坐标类型,默认为ABSOLUTE,如果使用绝对坐标的话可以省去type这个参数。基本上使用这个参数都是为了设置为RELATIVE_TO_SELF,意思是相对有自己的距离。
    剩下的那些值就好xml里一样,自己就能看懂啦~

    下面是具体的使用:
    TranslateAnimation translateAnimation = 
                        new TranslateAnimation(
                                Animation.RELATIVE_TO_SELF, 0f,
                                Animation.RELATIVE_TO_SELF, 0.5f,
                                Animation.RELATIVE_TO_SELF, 0f,
                                Animation.RELATIVE_TO_SELF, 0.5f
                        );
                translateAnimation.setDuration(5000);
                image.startAnimation(translateAnimation);

    缩放(ScaleAnimation)
    构造函数:
    public ScaleAnimation(float fromX, float toX, float fromY, float toY,
                int pivotXType, float pivotXValue, int pivotYType, float pivotYValue)
    pivotXType、pivotYType指的是坐标类型,默认为ABSOLUTE,如果使用绝对坐标的话可以省去type这个参数。基本上使用这个参数都是为了设置为RELATIVE_TO_SELF,意思是相对有自己的距离。
    下面是具体的使用:
    ScaleAnimation scaleAnimation = new ScaleAnimation( 0, 1f, 0, 1f, Animation.RELATIVE_TO_SELF,0.5f);
                scaleAnimation.setDuration(5000);
                image.startAnimation(scaleAnimation);

    旋转(RotateAnimation)
    构造函数:
    public RotateAnimation(float fromDegrees, float toDegrees, int pivotXType, float pivotXValue,
                int pivotYType, float pivotYValue)
    pivotXType、pivotYType指的是坐标类型,默认为ABSOLUTE,如果使用绝对坐标的话可以省去type这个参数。基本上使用这个参数都是为了设置为RELATIVE_TO_SELF,意思是相对有自己的距离。
    具体使用:
    RotateAnimation rotateAnimation = new RotateAnimation( 0, 180, Animation.RELATIVE_TO_SELF, 0.5f, Animation.RELATIVE_TO_SELF, 0.5F);
                rotateAnimation.setDuration(1000);
                image.startAnimation(rotateAnimation);

    透明度(AlphaAnimation)
    构造函数:
    public AlphaAnimation(float fromAlpha, float toAlpha)

    具体使用:
    AlphaAnimation alphaAnimation = new AlphaAnimation(1, 0);
                alphaAnimation.setDuration(5000);
                image.startAnimation(alphaAnimation);

    Animation类介绍

    既然补间动画的四种变化都是基于Animation写的,那么我们是不是也可以自定义一个补间动画呢。

    当然可以。

    其实Animation类最主要的函数是applyTransformation,重写这个函数就可以实现自己的动画啦~

    protected void applyTransformation(float interpolatedTime, Transformation t)
    interpolatedTime:代表动画的时间进行比,不管实际持续时间是多少,当动画播放时,该参数总是从0到1
    Transformation :这个参数是补间动画在不同时刻的变化,具体的变化都是通过这个参数实现。这个对象里面封装了一个Matrix,所以可以直接使用Matrix的函数实现对View的各种操作。
    干说也不明白,我们直接看一下RotateAnimation的代码吧~
    @Override
        protected void applyTransformation(float interpolatedTime, Transformation t) {
            float degrees = mFromDegrees + ((mToDegrees - mFromDegrees) * interpolatedTime);
            float scale = getScaleFactor();
            
            if (mPivotX == 0.0f && mPivotY == 0.0f) {
                t.getMatrix().setRotate(degrees);
            } else {
                t.getMatrix().setRotate(degrees, mPivotX * scale, mPivotY * scale);
            }
        }

    这个函数可能是能够不断的装载吧(这他妈做么做到的,谁知道的话在评论里告诉我!!),在不同的时间通过运算就能够得到不同的角度,然后设置相应的旋转角度。

    由于Matrix提供倾斜函数,我们可以写一个倾斜的动画。虽然可能没有什么实际用处。

    代码贴在下面,我就这么随便一写,更多玩法等待你的开发哦~

    package activity;
    
    import android.view.animation.Animation;
    import android.view.animation.Transformation;
    
    public class MyAnimation extends Animation{
        
        private float mkx;
        private float mky;
        
        
        public MyAnimation(float kx, float ky)
        {
            this.mkx = kx;
            this.mky = ky;
        }
        
        @Override
        protected void applyTransformation(float interpolatedTime, Transformation t) {
            float kx = mkx * interpolatedTime;
            float ky = mky * interpolatedTime;
            
            t.getMatrix().setSkew(kx, ky);
            
        }
    
    }

    我在学习安卓时的教材用的是《安卓疯狂讲义》,他在这里讲了控制三维变换的类Camera,也可以使用这个类来实现动画三维变换。

    关于这个类的具体信息大家可以看一下官网:http://developer.android.com/reference/android/graphics/Camera.html

    常用的几个函数列一下:

    getMatrix(Matrix matrix):将Camera所做的变换用用到matrix上

    rotate(float x, float y, float z):三个方向上的变换

    rotateX(float deg):将目标组件沿X轴旋转

    rotateY(float deg):将目标组件沿Y轴旋转

    rotateZ(float deg):将目标组件沿Z轴旋转

    translate(float x,float y,float z):把目标组件在三维空间内进行位移变换

    applyToCanvas(Canvas canvas):把Camera所做变幻应用到Canvas上

    save():保存Camera的状态

    。。。

    然后大家就看一下我这本书上他们自定义的动画吧~

    public class MyAnimation extends Animation
    {
        private float centerX;
        private float centerY;
        // 定义动画的持续事件
        private int duration;
        private Camera camera = new Camera();
    
        public MyAnimation(float x, float y, int duration)
        {
            this.centerX = x;
            this.centerY = y;
            this.duration = duration;
        }
    
        @Override
        public void initialize(int width, int height
            , int parentWidth, int parentHeight)
        {
            super.initialize(width, height, parentWidth, parentHeight);
            // 设置动画的持续时间
            setDuration(duration);
            // 设置动画结束后效果保留
            setFillAfter(true);
            setInterpolator(new LinearInterpolator());
        }
    
        /*
         * 该方法的interpolatedTime代表了抽象的动画持续时间,不管动画实际持续时间多长,
         * interpolatedTime参数总是从0(动画开始时)~1(动画结束时) 
         * Transformation参数代表了对目标组件所做的变.
         */
        @Override
        protected void applyTransformation(float interpolatedTime
            , Transformation t)
        {
            camera.save();
            // 根据interpolatedTime时间来控制X、Y、Z上的偏移
            camera.translate(100.0f - 100.0f * interpolatedTime,
                    150.0f * interpolatedTime - 150,
                    80.0f - 80.0f * interpolatedTime);
            // 设置根据interpolatedTime时间在Y柚上旋转不同角度。
            camera.rotateY(360 * (interpolatedTime));
            // 设置根据interpolatedTime时间在X柚上旋转不同角度
            camera.rotateX((360 * interpolatedTime));
            // 获取Transformation参数的Matrix对象
            Matrix matrix = t.getMatrix();
            camera.getMatrix(matrix);
            matrix.preTranslate(-centerX, -centerY);
            matrix.postTranslate(centerX, centerY);
            camera.restore();
        }
    }
  • 相关阅读:
    CSS Grid网格布局全攻略
    正则表达式不要背
    前端模块化的前世今生
    关于React Hooks,你不得不知的事
    精简版LINUX系统---wdOS
    TypeScript_泛型
    typescript_类
    ES5_对象 与 继承
    TypeScript_基础数据类型
    vue-route+webpack部署单页路由项目,访问刷新出现404问题
  • 原文地址:https://www.cnblogs.com/glimpse/p/5256182.html
Copyright © 2020-2023  润新知