当你在开发时涉及到一些或简单或繁琐的动画时,如何选择最合适性能最优的动画呢?
本文简明扼要的整理了几种常见的动画种类,截取重点实现部分,适合有一定Android动画基础的小伙伴们阅读。
首先我们要明确,Android动画由视图动画与属性动画两部分组成,接下来分别介绍这两个大类部分有代表性的使用方式。
本文组织结构如下图:
视图动画(ViewAnimation)
视图动画主要针对视图起作用,它只改变View的绘制效果,而没有改变View的真实属性。一个经典的问题就是一个Button从一个地方移动到另一个地方,点击事件还是在原来的地方。
逐帧动画(FrameAnimation/DrawableAnimation)
简而言之,将每帧图片依次播放形成的动画效果。
实现:
-
XML(res/drawable/frame.xml)
<?xml version="1.0" encoding="utf-8"?> <animation-list xmlns:android="http://schemas.android.com/apk/res/android" android:oneshot="true"> <item android:drawable="@drawable/a0" android:duration="100"/> <item android:drawable="@drawable/a1" android:duration="100"/> <item android:drawable="@drawable/a2" android:duration="100"/> <item android:drawable="@drawable/a3" android:duration="100"/> <item android:drawable="@drawable/a4" android:duration="100"/> </animation-list>
-
Java
mIvFrame.setBackgroundResource(R.drawable.frame); AnimationDrawable animationDrawable = (AnimationDrawable) mIvFrame.getDrawable(); animationDrawable.start();
补间动画(TweenAnimation)
提供位置、大小、旋转、透明度等一系列简单的变换。
实现:
-
XML
<?xml version="1.0" encoding="utf-8"?> <set xmlns:android="http://schemas.android.com/apk/res/android"> <alpha/> <scale/> <translate/> <rotate/> </set>
-
Java
Animation translateAnim = AnimationUtils.loadAnimation(context, R.anim.translate_animation); mImageView.startAnimation(translateAnim);
当然也可以使用AlphaAnimation/ScaleAnimation/TranslateAnimation/RotateAnimation
布局动画(LayoutAnimation)
补间动画只能对一个控件使用,如果要对某一组控件播放一样的动画的话,可以使用LayoutAnimation,在ViewGroup添加一个入场动画,这个ViewGroup的所有子元素都会按照你设计的顺序执行一遍动画。
实现:
-
XML
translate_layout_animation.xml: <?xml version="1.0" encoding="utf-8"?> <layoutAnimation xmlns:android="http://schemas.android.com/apk/res/android" android:animation="@anim/translate" android:animationOrder="normal" android:delay="0.3"/> translate.xml: <?xml version="1.0" encoding="utf-8"?> <translate xmlns:android="http://schemas.android.com/apk/res/android" android:duration="500" android:fromYDelta="100%p" android:toYDelta="0"/>
-
Java
Animation animation = AnimationUtils.loadAnimation(context, R.anim. translate); LayoutAnimationController layoutAnimationController = new LayoutAnimationController(animation); layoutAnimationController.setDelay(0.3f); layoutAnimationController.setOrder(LayoutAnimationController.ORDER_NORMAL); view.setLayoutAnimation(layoutAnimationController);
当然也可以在xml直接设置:
android:layoutAnimation ="@anim/translate_layout_animation"
属性动画(PropertyAnimation)
属性动画则是通过改变Object的属性进行动画实现,这样就不必限制在补间动画的4种效果,有更好的扩展性。
ObjectAnimator
ObjectAnimator.ofFloat(view, "translationY", 0f, 500f)
.setDuration(500)
.start();
ValueAnimator
ValueAnimator.ofFloat(0f, 1f)
.setDuration(500)
.start();
AnimatorSet
多个属性动画合集
ViewPropertyAnimator
ValueAnimator类和ObjectAnimator类基本都能满足我们对动画操作的需求,但ValueAnimator类和ObjectAnimator类本身并不是针对View对象的而设计的,而我们在大多数情况下主要都还是对View进行动画操作的,因此Google官方补充了ViewPropertyAnimator类,这个类便是专门为View动画而设计的。多个属性动画是一次同时变化,只执行一次UI刷新(也就是只调用一次invalidate,而n个ObjectAnimator就会进行n次属性变化,就有n次invalidate)。
实现:
mButton.animate().rotation(360).setDuration(200);
对,你没有看错,就是没有start()
其他动画
转场动画
我们只说共享元素。
效果:
图片来源: Activity 共享元素转场动画实践
实现:
在当前页和目标页XML中设置共享View属性
android:transitionName="mark"
-
在当前页启动共享元素动画:
Intent intent = new Intent(activity, TargetActivity.class); ActivityOptionsCompat options = ActivityOptionsCompat. makeSceneTransitionAnimation(activity, view, "mark"); activity.startActivity(intent, options.toBundle());
关闭目标页时使用
supportFinishAfterTransition()
触摸反馈(Ripple)
效果:
图片来源: Android UI效果篇-(1)Ripple
实现:
-
使用系统提供的颜色
在background中配置属性,
android:background="?attr/selectableItemBackground"
selectableItemBackground波纹被限制在控件的边界中/selectableItemBackgroundBorderless波纹会呈圆形发散出去
-
自定义扩散颜色
在background中配置属性,
android:background="@drawable/ripple"
R.drawable.ripple:
<?xml version="1.0" encoding="utf-8"?> <ripple xmlns:android="http://schemas.android.com/apk/res/android" android:color="@color/gray"> <item android:drawable="@color/white"/> </ripple>
弹性动画
反弹动画,Android Support Library 25.3.0引入了Dynamic-animation增强动画,里面提供了几个类用于使动画呈现实现真实的物理效果,你可以设置弹簧硬度和阻尼等。
效果:
实现:
-
导入
dependencies { compile 'com.android.support:support-dynamic-animation:25.3.0' }
-
定义弹性特质
SpringForce spring = new SpringForce(finalPosition); spring.setStiffness(stiffness); spring.setDampingRatio(dampingRatio);
-
定义SpringAnimation,并关联SpringForce对象
SpringAnimation animation = new SpringAnimation(view, property); animation.setSpring(spring); animation.start();
Lottie
非常强大的库,解析从AE导出的动画json文件并播放,将所有动画的设计全推给了设计师哈哈哈哈!!而且跨平台的哈哈哈!!用过的都说好!!别忘了自己把图片拖进去哦!
效果:
我是Github链接: Lottie