本文为稀土技术社区首发签约文章,14天内制止转载,14天后未获授权制止转载,侵权必究!

本篇文章是此专栏的第六篇文章,前几篇文章大约将 Compose 中的动画都简略过了一遍,假如想阅览前几篇文章的话能够点击下方链接:

  • Compose 动画艺术探究之瞅下 Compose 的动画
  • Compose 动画艺术探究之可见性动画
  • Compose 动画艺术探究之属性动画
  • Compose 动画艺术探究之动画标准
  • Compose 动画艺术探究之灵动岛
  • Compose 动画艺术探究之 AnimationVector

什么是 Easing?

根据时长的 AnimationSpec 操作(如 tweenkeyframes)运用 Easing 来调整动画的小数值。这样可让动画值加速和减速,而不是以恒定的速率移动。小数是介于 0(起始值)和 1.0(完毕值)之间的值,表明动画中的当前点。

Easing 实际上是一个函数,它取一个介于 0 和 1.0 之间的小数值并回来一个浮点数。回来的值可能位于边界之外,表明过冲或下冲。

上面这两段关于什么是 Easing 是官方文档中的描述,是不是看的云里雾里!哈哈哈,第一次看的时分都是,但在介绍 Easing 的最终加了一个留意,一起来看下:

留意:Easing 对象的运转办法与平台中 Interpolator 类的实例相同。不过,它采用的不是 getInterpolation() 办法,而是 transform() 办法。

奥,本来 Easing 就相当于我们之前运用的插值器(Interpolator)啊!这么说就好理解一些了。

怎么运用 Easing?

其实在之前文章 Compose 动画艺术探究之动画标准 中现已简略介绍过 Easing ,在里面大约介绍了常用的几种 Easing

  • FastOutSlowInEasing
  • LinearOutSlowInEasing
  • FastOutLinearEasing
  • LinearEasing
  • CubicBezierEasing

其间 CubicBezierEasing 是剩下四种的父类,这几种 Easing 的详细用法在 Compose 动画艺术探究之动画标准 中现已介绍过,这儿将就不再赘述,假如想看这几种 Easing 的动画作用能够先移步去看下。

下面来看下 Easing 的运用办法:

val value1 by animateFloatAsState(
  targetValue = 1f,
  animationSpec = tween(
    durationMillis = 300,
    delayMillis = 50,
    easing = LinearOutSlowInEasing // 运用 Easing
   )
)

运用办法其实很简略,关键是要选对 Easing 才干完成动画交互想要完成的作用。

还有哪些 Easing?

其实 Compose 中为我们提供的 Easing 远远不止上面说的这几种,还有许多,先来张图感受下有多少吧!

Compose 动画艺术探索之 Easing

小小提示,并没有截完。。。下面还有,这儿就不放那么多截图了。每一种 Easing 都对应着一种动画作用,我们能够去 看每一种 Easing 对应的动画作用样例。下面是官方文档地址:

developer.android.google.cn/reference/k…

怎么自界说 Easing?

方才的截图种能够看到,里面的 Easing 和最初说的那几种都承继的是 CubicBezierEasing ,那我们就来看下 CubicBezierEasing

@Immutable
class CubicBezierEasing(
  private val a: Float,
  private val b: Float,
  private val c: Float,
  private val d: Float
) : Easing {
    ......
  private fun evaluateCubic(a: Float, b: Float, m: Float): Float {
    return 3 * a * (1 - m) * (1 - m) * m +
      3 * b * (1 - m) * m * m +
      m * m * m
   }
​
  override fun transform(fraction: Float): Float {
    if (fraction > 0f && fraction < 1f) {
      var start = 0.0f
      var end = 1.0f
      while (true) {
        val midpoint = (start + end) / 2
        val estimate = evaluateCubic(a, c, midpoint)
        if ((fraction - estimate).absoluteValue < CubicErrorBound)
          return evaluateCubic(b, d, midpoint)
        if (estimate < fraction)
          start = midpoint
        else
          end = midpoint
       }
     } else {
      return fraction
     }
   }
    ......
}

嗯,CubicBezierEasing 完成了 Easing 接口,然后 Easing 中有一个办法 transformCubicBezierEasing 类完成了三阶贝塞尔曲线,这相当于原生的 PathInterpolator 。能够看到 CubicBezierEasing 结构办法中承受四个参数,类型都是 Float。

  • a:第一个控制点的x坐标。通过点(0,0)和第一个控制点的直线与点(0,0)处的缓动相切
  • b:第一个控制点的y坐标。通过点(0,0)和第一个控制点的直线与点(0,0)处的缓动相切
  • c:第二个控制点的x坐标。通过点(1,1)和第二个控制点的直线与点(1,1)处的缓动相切
  • d:第二个控制点的y坐标。通过点(1,1)和第二个控制点的直线与点(1,1)处的缓动相切。

CubicBezierEasing 是比较复杂的 Easing ,但也是一个通用的,所以有许多 Easing 都承继自它,我们自界说的时分也能够承继 CubicBezierEasing ,通过传入不同的控制点坐标来完成想要的动画作用。

当然,也能够直接完成 Easing 接口来完成动画作用,比方 LinearEasing

val LinearEasing: Easing = Easing { fraction -> fraction }

因为默许便是线性的,所以直接回来未修正的分数便是线性的动画作用。

接下来我们来自界说一个 Easing

val CustomLinearEasing: Easing = Easing { fraction -> fraction / 2 }

代码很简略,直接完成 Easing 接口,然后将分数除以二并回来,再来写个 Demo !

var small by remember { mutableStateOf(true) }
val size by animateDpAsState(
  targetValue = if (small) 50.dp else 100.dp,
  animationSpec = tween(
    durationMillis = 3000,
    delayMillis = 50,
    easing = CustomLinearEasing // 运用上面自界说的 Easing
   )
)
​
Column {
  Button(onClick = { small = !small }) {
    Text("修正巨细")
   }
  Box(
    modifier = Modifier.size(size)
   )
}

代码很简略,在之前的几篇文章中都运用过,这块也就不再赘述,唯一不同的便是这块运用了上面我们自界说的 Easing ,接下来运转看下作用!

Compose 动画艺术探索之 Easing

动画履行时间一共是三秒钟,但是三秒钟全部履行在了缩小的前半段,后半段在最终一瞬间完成。这是因为我们将 Easing 的分数回来值修正为了之前的一半而导致的。

方才的分数仅仅除以了二,这回我们直接改为负数看看!

val CustomLinearEasing: Easing = Easing { fraction -> -fraction / 2 }

别的都没动,仅仅加了个负号,来运转看下作用!

Compose 动画艺术探索之 Easing

能够看到动画作用正好和方才是相反的方向!

接下来再玩一下,方才是除以二,这回我们来乘二看下作用!

val CustomLinearEasing: Easing = Easing { fraction -> fraction * 2 }

运转看下作用!

Compose 动画艺术探索之 Easing

能够看到,动画作用履行到目标值还在办法或缩小,最终回来到既定值。

总结

假如想玩好 Compose 中的动画,Easing 是必不可少的一环,其实官方给完成的 Easing 根本都能满足我们的日程开发需求,假如完成需要自界说那就只能自界说搞一搞了,不过在自界说前能够思考下是直接完成 Easing 接口还是承继 CubicBezierEasing

本文至此完毕,有用的当地我们能够参考,当然假如能帮助到我们,哪怕是一点也足够了。就这样。