Web Animations


什么是Web Animations?

Web Animations defines a model for supporting animation and synchronization on the Web platform. It is intended that other specifications will build on this model and expose its features through declarative means. W3C

以上W3C对 Web Animations的定义,目前处于草稿阶段,Web Animations定义了一种同步或者异步在Web平台上,支持动画的模型。目前已有Chrome和Firefox开始实现Web Animations.以下是各浏览器对WAAP(Web Animations API)的支持情况。
图片描述
随着css的发展和一些技js新特性的加入,动画在过去五年里发展的比较好。但是每一种解决方案都有他的优点和缺点:

  • CSS 具有硬件加速,表现更为平滑,而且浏览器内置支持,但是需要JS辅助动态变化。

  • requestAnimationFrame 有很好的支持并且可以让浏览器进行优化,但是当有很多其他JS程序运行时,动画可能会被阻塞,并且还需要更多的数学函数进行计时。

  • setInterval 不准确而且很容易卡顿。

  • jQuery.animate() ,性能问题。

  • 第三方库 ,其他JS库 Velocity.js Greensock ,需要增加第三方的库。

而Web Animations的目标就是带来和CCS一样的强劲表现,并且增加灵活性,让浏览器更好的工作。

Web Animations用法事例

Web Animations希望为 CSS Transitions CSS Animations ,和 SVG 提供一些特性。因此,Web Animations是这三个规范的总称。

监测正在运行的动画

Web程序经常需要等到动画结束后去更新状态,此规范的编程接口运用程序等到所有的运行动画结束,无论是CSS Transitions, CSS Animations, SVG animations中的哪一个定义的,或者是此编程接口直接创建的。


 // Wait until all animations have finished before removing the element
Promise.all(
  elem.getAnimations().map(animation => animation.finished)
).then(() => elem.remove());

或者选择正在运行的动画:


 var isAnimating = elem.getAnimations().some(
  animation => animation.playState == 'running'
);

控制动画

也可以用Js的requestAnimationFrame控制动画,但是存在表现不一致和性能问题。而Web Animations不会产生此问题。


 // Fade out quickly
elem.animate({ transform: 'scale(0)', opacity: 0 }, 300);

调试动画

在复杂的应用中,动画是很难调试的,但可以Web Animations的接口进行辅助调试。


 // Print the id of any opacity animations on elem
elem.getAnimations().filter(
  animation =>
    animation.effect instanceof KeyframeEffectReadOnly &&
    animation.effect.getFrames().some(
      frame => frame.hasOwnProperty('opacity')
    )
).forEach(animation => console.log(animation.id));

也可以减慢动画的速率:


 // Slow down and replay any transform animations
elem.getAnimations().filter(
  animation =>
    animation.effect instanceof KeyframeEffectReadOnly &&
    animation.effect.getFrames().some(
      frame => frame.hasOwnProperty('transform')
    )
).forEach(animation => {
  animation.currentTime = 0;
  animation.playbackRate = 0.5;
});

测试动画

为了测试动画而等待动画完成是不现实的,可以写一些描述快速找出特定动画。


 // Seek to the half-way point of an animation and check that the opacity is 50%
elem.getAnimations().forEach(
  animation =>
    animation.currentTime =
      animation.effect.getComputedTiming().delay +
      animation.effect.getComputedTiming().activeDuration / 2;
);
assert_equals(getComputedStyle(elem).opacity, 0.5);

// Check that the loading screen is hidden after the animations finish
elem.getAnimations().forEach(
  animation => animation.finish()
);
// Wait one frame so that event handlers have a chance to run
requestAnimationFrame(() => {
  assert_equals(
    getComputedStyle(document.querySelector('#loading')).display, 'none');
});

Web Animations模型概述

这一部分是还未规范的标准。动画模型包含时间模型和动画模型:

  • 时间模型:在单次动画中,将时间称比列的转化为空间距离被称作迭代进度,迭代数(动画重复的次数)也将会被记录下来。

  • 动画模型:将迭代进程和迭代数通过时间模型转换成一系列的值并应用到对象的属性上。

简单的说就是:

  • 3秒之后开始。

  • 运行两次。

  • 每次运行两秒。

  • 改变一个矩形的宽度在50像素到100像素之间。

前三点被用到时间模型上,动画会被计算,在六秒之后动画运行到第二次迭代的一半。动画模型将根据这些信息计算出矩形宽度。

时间模型

这一部分是还未规范的标准。时间模型具有两大特性:无状态和分等级。

  • 无状态:Web Animations的时间模型根据一个输入时间产生迭代进程。

  • 分等级: Web Animations的时间模型的的另一特性是时间是被继承的。

全局时间(global clock)

Web Animations时间体系的根源是全局时间,全局时间没有对外暴露接口,只是用于测量时间。

时间轴(Timelines)

时间轴为同步或者异步提供了一些了的时间值。

  • 文档时间轴(Document timelines):文档时间轴是一种类型的时间轴(Timelines),这种类型的时间轴和文档相关联,文档时间轴的时间值根据全局时间的偏移量计算出来。

  • 默认文档时间轴(The default document timeline):每一个文档都有唯一的默认文档时间轴,它的持续时间是文档的生命周期。默认文档时间轴的初始值为0.

动画

包含一系列的概念。

动画模型

动画模型根据迭代进程和当前进程去计算相应的输出。包含:Keyframe effects,Keyframe,Combining effects.

编程接口

具体的接口可参考: W3C programming-interface

栗子来了

一个基本的Keyframe动画


 @keyframes translation {
    0% { transform: rotate(0deg) }
    8% { transform: rotate(-12deg) }
    30% { transform: rotate(270deg) }
    55% { transform: rotate(-40deg) }
    80% { transform: rotate(70deg) }
    92% { transform: rotate(-13deg) }
    100% { transform: rotate(0deg) }
}
#div {
    background: #d05f5e;
    animation: translation 3s 0s infinite linear;
}

以上CSS创建的一个动画,可以使用Web Animations创建一个类似的动画:


 var player = document.getElementById('toAnimate').animate([
    { transform: 'rotate(0deg)', offset: 0 },
    { transform: 'rotate(-12deg)', offset: .08 },
    { transform: 'rotate(270deg)', offset: .3 },
    { transform: 'rotate(-40deg)', offset: .55 },
    { transform: 'rotate(70deg)', offset: .8 },
    { transform: 'rotate(-13deg)', offset: .92 },
    { transform: 'rotate(0deg)', offset: 1 }
], {
    duration: 3000,
    iterations: Infinity,
    easing: 'linear',
    delay: 0
});

Demo演示 (灰色方块用js实现,红色方块用css实现)

控制动画状态

Web Animations开放出了playState,playbackRate等接口供调用。
Demo演示 (暂停和加速)

参考资源

Web Animations .
Web Animations API .

web-animations 动画 Animation css3动画

陈之空空少年桑 8 years, 7 months ago

Your Answer