美文网首页
Android动画详解

Android动画详解

作者: 编程的猫 | 来源:发表于2020-03-09 16:08 被阅读0次

    Android动画分类

    Android动画分为传统动画和属性动画(Android3.0之后引入)

    传统动画
    • 帧动画

    帧动画是最容易实现的一种动画,这种动画更多的依赖于完善的UI资源,他的原理就是将一张张单独的图片连贯的进行播放,
    从而在视觉上产生一种动画的效果;有点类似于某些软件制作gif动画的方式。
    例如:京东App的加载动画
    代码实现:

    <?xml version="1.0" encoding="utf-8"?>
    <animation-list xmlns:android="http://schemas.android.com/apk/res/android">
        <item
            android:drawable="@drawable/a_0"
            android:duration="100" />
        <item
            android:drawable="@drawable/a_1"
            android:duration="100" />
        <item
            android:drawable="@drawable/a_2"
            android:duration="100" />
    </animation-list>
    
    protected void onCreate(@Nullable Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_frame_animation);
            ImageView animationImg1 = (ImageView) findViewById(R.id.animation1);
            animationImg1.setImageResource(R.drawable.frame_anim1);
            AnimationDrawable animationDrawable1 = (AnimationDrawable) animationImg1.getDrawable();
            animationDrawable1.start();
        }
    

    在有些代码中,我们还会看到android:oneshot="false" ,这个oneshot 的含义就是动画执行一次(true)还是循环执行多次。

    • 补间动画

    补间动画又又四种方式:
    1.alpha透明变化
    2.translate位移变化
    3.scale缩放变化
    4.rotate旋转变化
    补间动画一般采用XML的形式,优点是:方便复用
    下面列举四种方式的示例代码:
    translate:

    <?xml version="1.0" encoding="utf-8"?>
    <translate xmlns:android="http://schemas.android.com/apk/res/android"
        android:fromXDelta="30"
        android:fromYDelta="50"
        android:toXDelta="120"
        android:toYDelta="300">
    
    </translate>
    

    scale:

    <set xmlns:android="http://schemas.android.com/apk/res/android"
        android:duration="1000">
        <scale
            android:fromXScale="0.0"
            android:fromYScale="0.0"
            android:pivotX="30%"
            android:pivotY="30%"
            android:toXScale="1.0"
            android:toYScale="1.0" />
    </set>
    

    alpha:

    <?xml version="1.0" encoding="utf-8"?>
    <alpha xmlns:android="http://schemas.android.com/apk/res/android"
        android:duration="2000"
        android:fromAlpha="0.0"
        android:interpolator="@android:anim/accelerate_decelerate_interpolator"
        android:toAlpha="1.0">
    
    </alpha>
    

    rotate:

    <?xml version="1.0" encoding="utf-8"?>
    <set xmlns:android="http://schemas.android.com/apk/res/android"
        android:duration="2000"
        android:shareInterpolator="true">
        <rotate
            android:fromDegrees="0"
            android:pivotX="50"
            android:pivotY="30"
            android:toDegrees="270" />
    
    </set>
    

    四种方式也可以在set标签中节和使用。

    interpolator 和 pivot。
    Interpolator 主要作用是可以控制动画的变化速率 (差速器),就是动画进行的快慢节奏。也可以自定义实现自己的差速器

    Android 系统已经为我们提供了一些Interpolator ,比如 accelerate_decelerate_interpolator,accelerate_interpolator等。

    pivot 决定了当前动画执行的参考位置
    • pivotX取值
      10:表示距离动画所在view自身左边缘的10像素;
      10%:表示距离动画所在view自身左边缘为自身宽度的10%;
      10%p:表示距离动画所在view自身左边缘自身宽度的为其父View的宽度的10%;
      pivotY同理;
      补间动画也可以代码动态实现:
    private void RotateAnimation() {
    //旋转动画
            animation = new RotateAnimation(-deValue, deValue, Animation.RELATIVE_TO_SELF,
                    pxValue, Animation.RELATIVE_TO_SELF, pyValue);
            animation.setDuration(timeValue);
    
            if (keep.isChecked()) {
                animation.setFillAfter(true);
            } else {
                animation.setFillAfter(false);
            }
            if (loop.isChecked()) {
                animation.setRepeatCount(-1);
            } else {
                animation.setRepeatCount(0);
            }
    
            if (reverse.isChecked()) {
                animation.setRepeatMode(Animation.REVERSE);
            } else {
                animation.setRepeatMode(Animation.RESTART);
            }
            img.startAnimation(animation);
        }
    

    常用API:

    • setDuration:动画执行的时间
    • setFillAfter:保持动画执行后的状态
    • setFillBefore:保持动画执行前的状态
    • setRepeatCount:动画是否重复执行
    • setRepeatMode:动画重复执行的模式:
      Animation.REVERSE:逆向执行
      Animation.RESTART:从头开始执行
    传统动画暂时讲解到 这里

    属性动画

    属性动画,顾名思义它是对于对象属性的动画。因此,所有补间动画的内容,都可以通过属性动画实现。

        private void RotateAnimation() {
            ObjectAnimator anim = ObjectAnimator.ofFloat(myView, "rotation", 0f, 360f);
            anim.setDuration(1000);
            anim.start();
        }
    
        private void AlpahAnimation() {
            ObjectAnimator anim = ObjectAnimator.ofFloat(myView, "alpha", 1.0f, 0.8f, 0.6f, 0.4f, 0.2f, 0.0f);
            anim.setRepeatCount(-1);
            anim.setRepeatMode(ObjectAnimator.REVERSE);
            anim.setDuration(2000);
            anim.start();
        }
    
                    ObjectAnimator alphaAnim = ObjectAnimator.ofFloat(myView, "alpha", 1.0f, 0.5f, 0.8f, 1.0f);
                    ObjectAnimator scaleXAnim = ObjectAnimator.ofFloat(myView, "scaleX", 0.0f, 1.0f);
                    ObjectAnimator scaleYAnim = ObjectAnimator.ofFloat(myView, "scaleY", 0.0f, 2.0f);
                    ObjectAnimator rotateAnim = ObjectAnimator.ofFloat(myView, "rotation", 0, 360);
                    ObjectAnimator transXAnim = ObjectAnimator.ofFloat(myView, "translationX", 100, 400);
                    ObjectAnimator transYAnim = ObjectAnimator.ofFloat(myView, "tranlsationY", 100, 750);
                    AnimatorSet set = new AnimatorSet();
                    set.playTogether(alphaAnim, scaleXAnim, scaleYAnim, rotateAnim, transXAnim, transYAnim);
    //                set.playSequentially(alphaAnim, scaleXAnim, scaleYAnim, rotateAnim, transXAnim, transYAnim);
                    set.setDuration(3000);
                    set.start();
    
    

    可以看到,属性动画貌似强大了许多,实现很方便,同时动画可变化的值也有了更多的选择,并且也可以组合使用。可以看到这些动画可以同时播放,或者是按序播放。

    属性动画核心原理

    在上面实现属性动画的时候,我们反复的使用到了ObjectAnimator 这个类,这个类继承自ValueAnimator,使用这个类可以对任意对象的任意属性进行动画操作。ValueAnimator是整个属性动画机制当中最核心的一个类

    属性动画的运行机制是通过不断地对值进行操作来实现的,而初始值和结束值之间的动画过渡就是由ValueAnimator这个类来负责计算的。它的内部使用一种时间循环的机制来计算值与值之间的动画过渡,我们只需要将初始值和结束值提供给ValueAnimator,并且告诉它动画所需运行的时长,那么ValueAnimator就会自动帮我们完成从初始值平滑地过渡到结束值这样的效果。除此之外,ValueAnimator还负责管理动画的播放次数、播放模式、以及对动画设置监听器等

    通过duration、startPropertyValue和endPropertyValue 等值,我们就可以定义动画运行时长,初始值和结束值。然后通过start方法开始动画。
    那么ValueAnimator 到底是怎样实现从初始值平滑过渡到结束值的呢?这个就是由TypeEvaluator 和TimeInterpolator 共同决定的。

    • TypeEvaluator 决定了动画如何从初始值过渡到结束值
    • TimeInterpolator 决定了动画从初始值过渡到结束值的节奏

    参考博文:
    https://www.jianshu.com/p/420629118c10

    相关文章

      网友评论

          本文标题:Android动画详解

          本文链接:https://www.haomeiwen.com/subject/ffdpdhtx.html