常见动画的缓动函数

大多时候,我们的动画都是线性变化的。例如,一个点从0运动到1,假如中间有8个点,那就应该是0.1,0.2,0.3,0.4,0.5,0.6,0.7,0.8。但有的时候,我们需要一种非线性的变化。例如我们做一架飞机起飞,它的变化应该是从慢到快的。又比如一个小球落地,它的轨迹应该是抛物线,而且还会弹起。

要做到这些,就需要用到缓动函数(EasingFunction)。很多语言都提供了缓动函数库,但如我们想(或者说需要)自己实现时,就需要知道这些缓动函数的函数形式。

我们让时间为t,值为y,那么缓动函数就是y=f(t)。我们假设t的取值范围是[0,1],同样y的值域也是[0,1],这个规定对我们后面的计算有极大的帮助。怎么把时间变成[0,1]里的数,又怎么把[0,1]范围的值转为实际的值,相信并不难。举个例子,我们的时间是[0,1000ms],那么把时间除以1000,就是[0,1]的数组了。我们的值是[15,100],那么我们把结果x作以下运算即可转化:15+(100-15)*x。

我们知道,很多缓动函数都有EaseIn,EaseOut,EaseInOut的选项。其实EaseIn就是EaseOut旋转180度得到的,而EaseInOut是把值分为[0,0.5],(0,5,1]两段,前面用EaseIn,后面用EaseOut得到的。假如我们已经得到EaseIn的函数形式是y=f(t),那么EaseOut的函数形式就是y=1-f(1-t)。所以我们只需要求出每种缓动函数的EaseIn即可。

一、线性变化

不使用缓动函数默认就是线性变化。它的函数形式很明显:

y=t

没错,这就是线性动画的缓动函数。

二、端点略有收回(BackEase)

表现出来就是一辆车开得太快,过了终点又往回倒一点点。

函数形式是:

y=t^3-0.3*t*sin(t*π)

C#代码:

case EasingMethod.BackEaseIn:
    t = x[i];
    MidValues[i] = Math.Pow(t, 3) - 0.3 * t * Math.Sin(t * Math.PI);
    break;
case EasingMethod.BackEaseOut:
    t = 1 - x[i];
    MidValues[i] = 1 - (Math.Pow(t, 3) - 0.3 * t * Math.Sin(t * Math.PI));
    break;

三、加速/减速(SineEase)(较缓)

表现出来是慢慢加速。

函数形式是:

y=sin(t*π/2)

C#代码:

case EasingMethod.SineEaseIn:
    t = 1 - x[i];
    MidValues[i] = 1 - (Math.Sin(t * Math.PI / 2));
    break;
case EasingMethod.SineEaseOut:
    t = x[i];
    MidValues[i] = Math.Sin(t * Math.PI / 2);
    break;

四、加速/减速(CircleEase)(较迅速)

同样是加速,这个表现出来就是加油加得很猛那种。

函数形式:

y=sqrt(1-t^2)

其实加减数函数还有很多,可以用幂不同的指数函数去做,例如是t^2、t^3、t^4,指数越大,变化越迅速。

C#代码:

case EasingMethod.CircleEaseIn:
    t = x[i];
    MidValues[i] = 1 - Math.Sqrt(1 - t * t);
    break;
case EasingMethod.CircleEaseOut:
    t = 1 - x[i];
    MidValues[i] = Math.Sqrt(1 - t * t);
    break;

五、振荡(ElasticEase)

这个一般做弹簧的那种运动。

函数形式:

y=100^t*sin(8.5π*t)/100

C#代码:

case EasingMethod.ElasticEaseIn:
    t = x[i];
    MidValues[i] = Math.Pow(100, t) * Math.Sin(8.5 * Math.PI * t) / 100;
    break;
case EasingMethod.ElasticEaseOut:
    t = 1 - x[i];
    MidValues[i] = 1 - (Math.Pow(100, t) * Math.Sin(8.5 * Math.PI * t) / 100);
    break;

六、弹跳(BounceEase)

这个表现出来就是有弹力的小球落地的那种运动了。

这种运行没办法有一个统一的函数去做,我们只能把它切成若干段,每一段都是抛物线:

[0,0.1]  y=-(t-0.05)^2+0.0025

(0.1,0.3]  y=-(t-0.2)^2+0.01

(0.3,0.7]  y=-(t-0.5)^2+0.04

(0.7,1]  y=-(t-1)^2+0.09

C#代码:

case EasingMethod.BounceEaseIn:
    t = x[i];
    MidValues[i] = (
        (t <= 0.1 ? (-Math.Pow(t - 0.05, 2) + 0.0025) : 0) +
        ((t > 0.1 && t <= 0.3) ? (-Math.Pow(t - 0.2, 2) + 0.01) : 0) +
        ((t > 0.3 && t <= 0.7) ? (-Math.Pow(t - 0.5, 2) + 0.04) : 0) +
        (t > 0.7 ? (-Math.Pow(t - 1, 2) + 0.09) : 0)
        ) / 0.09;
    break;
case EasingMethod.BounceEaseOut:
    t = 1 - x[i];
    MidValues[i] = 1 - (
        (t <= 0.1 ? (-Math.Pow(t - 0.05, 2) + 0.0025) : 0) +
        ((t > 0.1 && t <= 0.3) ? (-Math.Pow(t - 0.2, 2) + 0.01) : 0) +
        ((t > 0.3 && t <= 0.7) ? (-Math.Pow(t - 0.5, 2) + 0.04) : 0) +
        (t > 0.7 ? (-Math.Pow(t - 1, 2) + 0.09) : 0)
        ) / 0.09;
    break;

 

  • 7
    点赞
  • 29
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值