官方页面:动画简介
官方页面:属性动画概览
官方页面:使用动画显示或隐藏视图
一、概念
属性动画 PeopertyAnimation |
view的属性根据执行的动画发生真实的改变,通过不断设置View的属性实现。 |
视图动画(补间动画) ViewAnimation(Tween) |
视图动画的作用对象是View。不改变view的位置和属性。基于 Framework的绘制转变。 |
帧动画 DrawableAnimation(Frame) |
依次播放动画过程中每帧对应的静态图片。 |
二、插值器 Interpolator
即数度模型,算法对应不同时间点动画完成度的百分比,使一些基础的动画如(平移,缩放,旋转,透明)可以被加速,减速,重复等。
LinearInterpolator | 匀速。 |
AccelerateInterpolator | 持续加速(构造中可调节变速系数)。主要用在出场效果中。 |
AccelerateDecelerateInterpolator | 先加速再减速。默认效果,最符合现实物理模型。 |
DecelerateInterpolator | 持续减速到0。主要用于入场效果。 |
AnticipateInterpolator | 先反效果一点点(平移就是先回拉,放大就是先缩小),再进行正常动画轨迹。 |
OvershottInterpolator | 超过目标值一些再弹回来。 |
AnticipateOvershootInterpolator | 两种效果的结合体,先反效果一点点,最后超过目标值一些再回弹。 |
BounceInterpolator | 在目标值处弹跳几下。 |
CycleInterpolator | 自定义动画循环播放特定次数。 |
PathInterpolator | 自定义任何想要的速度模型(动画完成度 ÷ 时间完成度)。使用一个 Path 对象来绘制出想要的曲线(y 为动画完成度,x 为时间完成度)。 |
FastOutLinearInInterpolator |
持续加速(贝塞尔曲线,初始加速更快,肉眼并不明显)。 |
FastOutSlowInInterpolator | 先加速再减速(贝塞尔曲线,加速减速更快)。 |
LinearOutSlowInInterpolator | 持续减速(初始速度更快)。 |
三、属性动画 PeopertyAnimation
3.1 ViewPropertyAnimator
通过 view.animate() 返回一个 ViewPropertyAnimator 对象并自动执行,局限性在于只能调用以下方法设置属性动画。
public ViewPropertyAnimator animate() |
3.1.1 动画模式
- 这些方法调用就会执行动画,在播放中途再次调用会先停留在原处,等进度赶上了再继续播放。当动画播放完毕后,不带by的方法再次调用不会执行,任何时候调用 start( ) 都无效果,调用 cancel() 会打断动画并会停留在原处,再次这些方法等进度赶上了再继续播放。
- 默认动画时长0.3s,通过 setDuration() 自定义。
- 默认速度模型开始加速结束减速(AccelerateDecelerateInterpolator),通过 setInterpolator() 自定义。
3.1.2 动画监听
设置监听 | public @NonNull ViewPropertyAnimator setListener(@Nullable Animator.AnimatorListener listener) 重写onAnimationStart动画开始、onAnimationEnd动画结束、onAnimationCancel动画取消(对应调用了cancel时)、onAnimationRepeat动画重复(对应通过repeat播放时)。 |
更新监听 | public @NonNull ViewPropertyAnimator setUpdateListener(@Nullable ValueAnimator.AnimatorUpdateListener listener) 重写onAnimationUpdate每当属性值更新时,参数ValueAnimator可以获取当前动画完成度、属性值等。 |
一次性监听 | public @NonNull ViewPropertyAnimator withStartAction(Runnable runnable) public @NonNull ViewPropertyAnimator withEndAction(Runnable runnable) 重用ViewPropertyAnimator 执行别的动画也不会再执行,动画被调用cancel取消时不会再执行。 |
3.2 ObjectAnimator
ofFloat(Object target, String propertyName, float... values) 通过 ObjectAnimator.ofXXX() 创建对象,XXX具体选什么类型根据该属性设置方法的参数类型决定。target是目标View,propertyName是View的哪个属性(不是找同名变量修改值,是拼接出setter方法并调用,找不到IDE会提示。若是自定义View该属性需要提供setter方法,并在最后一行调用 invalidate() 触发重绘),values是目标值(填一个就是目标值,填两个就是起始值和目标值,填多个就是增加中间转接点值。若是自定义View,只填一个值的情况就需要该属性提供getter方法,会获取当前值当作起始值)。调用 start() 才会执行动画。 |
class MyView2 : View {
var progress = 0F
set(value) {
field = value
invalidate() //重写getter触发重绘即调用onDraw()
}
override fun onDraw(canvas: Canvas?) {
super.onDraw(canvas)
canvas?.drawArc(...)
}
}
UI {
val animator = ObjectAnimator.ofFloat(myView, "progress", 0, 65)
animator.start()
}
3.2.1 动画监听
设置监听 | public void addListener(AnimatorListener listener) 重写onAnimationStart动画开始、onAnimationEnd动画结束、onAnimationCancel动画取消(对应调用了cancel时)、onAnimationRepeat动画重复(对应通过repeat播放时)。 |
更新监听 |
public void addUpdateListener(AnimatorUpdateListener listener) 重写onAnimationUpdate每当属性值更新时,参数ValueAnimator可以获取当前动画完成度、属性值等。 |
暂停监听 | public void addPauseListener(AnimatorPauseListener listener) |
var boolean = false
onCreate {
//对View启用动画
val animate = imagineView.animate().apply {
//动画类型不能写在里面因为调用就会执行
duration = 2000 //设置动画时长
interpolator = AccelerateDecelerateInterpolator() //设置速度模型
startDelay = 2000 //延迟播放
setListener(object : Animator.AnimatorListener{
override fun onAnimationStart(animation: Animator) { } //动画开始
override fun onAnimationEnd(animation: Animator) { } //动画结束
override fun onAnimationCancel(animation: Animator) { } //动画取消
override fun onAnimationRepeat(animation: Animator) { } //动画重复
})
setUpdateListener { valueAnimator -> } //动画更新
withStartAction { Runnable { } } //动画开始
withEndAction { Runnable { } } //动画结束
}
button1.setOnClickListener {
//中途再次点击会停留在原地等进度赶上了继续播放
animate.translationXBy(200F) //每次点击都有位移效果
animate.rotation(180F) //只执行一次,播放完后再次点击无旋转效果
}
button2.setOnClickListener {
//每次点击在strat和cancel切换,测试结果:start()任何时候都无效,cancel()打断动画停在原地
if (boolean) animate.start() else animate.cancel()
boolean = !boolean
}
}
3.3 DynamicAnimation
四、切换界面动画 Transition
官方页面
五、视图动画 ViewAnimation
视图动画的作用对象是View,又叫补间动画,仅仅是呈现呈现效果,便不会改变控件任何的真实情况(例如Button即便动画移到了下边也不能点击,其实还停留在原处可点击)。可以通过 xml 或代码动态创建(建议使用 xml 因为具有更高的可读性和重用性)。
- 数值、百分数、百分数p,譬如50表示以当前View左上角坐标加50px为初始点、50%表示以当前View的左上角加上当前View宽高的50%做为初始点、50%p表示以当前View的左上角加上父控件宽高的50%做为初始点
5.1 动画模式
透明度 | AlphaAnimation( float fromAlpha, //动画开始的透明度 float toAlpha //动画结束的透明度 ) 透明度取值范围范围 0~1。 |
缩放 | public ScaleAnimation( pivotX/pivotY:缩放的中轴点坐标,即距离自身左边缘的位置,比如50%就是以图像的中心为中轴点。 |
平移 | public TranslateAnimation( |
旋转 | public RotateAnimation( float pivotY //缩放起点Y坐标 旋转角度:正代表顺时针度数,负代表逆时针度数。 |
动画集合 | AnimationSet(boolean shareInterpolator) 可同时播放以上动画。shareInterpolator:true都用一样的插值器,false用各自的插值器。通过调用addAnimation(Animation a) 将动画添加进集合。 |
5.2 动画配置
持续时间 | public void setDuration(long durationMillis) |
重复次数 | public void setRepeatCount(int repeatCount) 值为-1或者infinite时,表示动画永不停止。 |
重复模式 | public void setRepeatMode(int repeatMode) 默认restart,但只有当repeatCount大于0或者infinite或-1时 才有效。还可以设置成reverse,表示偶数次显示动画时会做方向相反的运动。 |
设置速度模型 | public void setInterpolator(Interpolator i) |
停留结果 | public void setFillAfter(boolean fillAfter) 设为 true 则动画结束后 view 会停留在当前效果。 |
开始动画 | public void startAnimation(Animation animation) 由 view 调用,传入要播放的动画。 |
5.3 动画监听
public void setAnimationListener(AnimationListener listener) 用动画对象调用,重写三个方法:onAnimationStart动画开始时、onAnimationEnd动画结束时、onAnimationRepeat动画重复时。 |
5.4 使用方式
5.4.1 xml配置动画
res目录下新建anim文件夹,创建xml文件,可选节点有alpha、rotate、scale、translate、set。
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="@android:anim/accelerate_decelerate_interpolator"
android:fromXDelta="0"
android:toXDelta="320"
android:fromYDelta="0"
android:toYDelta="0"
android:duration="2000"/>
AnimationUtils.loadAnimation(this, R.anim.translate) //加载Xml文件中的动画
imagineView.startAnimation(translate) //将动画设置到指定的View上
5.4.2 代码配置动画
val imagineView = binding.imagineView
val button = binding.button
//透明
val alphaAnimation = AlphaAnimation(1.0F, 0.2F)
//旋转
val rotateAnimation = RotateAnimation(0F, 360F, Animation.RELATIVE_TO_SELF, 0.5F, Animation.RELATIVE_TO_SELF, 0.5F)
//缩放
val scaleAnimation = ScaleAnimation(1.0F, 5.0F, 1.0F, 5.0F, Animation.RELATIVE_TO_SELF, 0.5F, Animation.RELATIVE_TO_SELF, 0.5F)
//平移
val translateAnimation = TranslateAnimation(Animation.RELATIVE_TO_PARENT, 0F, Animation.RELATIVE_TO_PARENT, 0F,Animation.RELATIVE_TO_PARENT, 0F, Animation.RELATIVE_TO_PARENT, 0.4F)
//动画集合
val set = AnimationSet(true).apply {
addAnimation(alphaAnimation)
addAnimation(rotateAnimation)
addAnimation(scaleAnimation)
addAnimation(translateAnimation)
duration = 1 //持续时间
repeatCount = 10 //重复次数
repeatMode = Animation.RESTART //重复方式
interpolator = AccelerateDecelerateInterpolator() //速度模型
fillAfter = true //播放完毕后停留在原地
}
//动画监听
set.setAnimationListener(object : AnimationListener {
override fun onAnimationStart(animation: Animation?) { } //动画开始
override fun onAnimationEnd(animation: Animation?) { } //动画结束
override fun onAnimationRepeat(animation: Animation?) { } //动画重复
})
button.setOnClickListener {
imagineView.startAnimation(set) //开始动画
}
六、帧动画 DrawableAnimation(Frame)
容易引起OOM。文章来源:https://www.toymoban.com/news/detail-434481.html
6.1 xml配置
res/drawable目录下创建animation-list文件文章来源地址https://www.toymoban.com/news/detail-434481.html
<animation-list xmlns:android="http://schemas.android.com/apk/res/android"
android:oneshot="false"> //true表示只播放一边,默认就是false可不写
<item android:drawable="@drawable/girl_1" android:duration="100" />
<item android:drawable="@drawable/girl_2" android:duration="100" />
<item android:drawable="@drawable/girl_3" android:duration="100" />
</animation-list>
6.2 代码调用
imagineView.setBackgroundResource(R.drawable.anim_frame)
val animationDrawable = imagineView.background as AnimationDrawable
animationDrawable.start()
到了这里,关于Android - 动画的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!