前端实现动画效果的几种方式 - 九种
原文链接:
一. Js实现
代码如下
存在的问题
javascript 实现动画通常会导致页面频繁性重排重绘,消耗性能,一般应该在桌面端浏览器,在移动端上使用会有明显的卡顿。
为什么是16ms
上面例子中,我们设置的setInterval
时间间隔是16ms
一般认为人眼能辨识的流畅动画为每秒60帧,这里16ms比(1000ms/60)帧略小一些,但是一般可仍为该动画是流畅的。
如果大于16ms, 比如设置成500ms, 会明显感觉的卡顿。
在很多移动端动画性能优化时,一般使用16ms来进行节流处理连续触发的浏览器事件。
例如对touchmove、scroll事件进行节流等, 通过这种方式减少持续事件的触发频率,可以大大提升动画的流畅性。
二. CSS3 transition
代码如下
菜鸟教程(runoob.com)
注意:该实例无法在 Internet Explorer 9 及更早 IE 版本上工作。
鼠标移动到 div 元素上,1秒后 开始过渡效果。
transition是过度动画
但是transition并不能实现独立的动画,只能在某个标签元素样式或状态改变时进行平滑的动画效果过渡,而不是马上改变
三. CSS3 animation
代码如下
菜鸟教程(runoob.com)
注意: 该实例在 Internet Explorer 9 及更早 IE 版本是无效的。
animation 算是真正意义上的CSS3动画。通过对关键帧和循环次数的控制,页面标签元素会根据设定好的样式改变进行平滑过渡
而且关键帧状态的控制是通过百分比来控制的
四. SVG
代码如下
Note: This example only works in Firefox and Google Chrome.
SVG的教程看这里:https://www.runoob.com/svg/svg-tutorial.html
SVG的一大优势是含有较为丰富的动画功能,原生绘制各种图形、滤镜和动画,并且能被js调用。html是对dom的渲染,那么svg就是对图形的渲染。
但是,另一方面元素较多且复杂的动画使用svg渲染会比较慢,而且SVG格式的动画绘制方式必须让内容嵌入到HTML中使用
CSS3的出现让svg的应用变得相对少了。
五. Canvas
代码如下
Canvas 相关教程看这里: https://www.runoob.com/html/html5-canvas.html
Canvas主要优势是可以应对页面中多个动画元素渲染较慢的情况,完全通过javascript来渲染控制动画的执行。可用于实现较复杂动画。
六. requestAnimationFrame
代码如下
requestAnimationFrame 相关资料看这里: https://developer.mozilla.org/zh-CN/docs/Web/API/Window/requestAnimationFrame
requestAnimationFrame是另一种Web API,原理与setTimeout和setInterval类似,都是通过javascript持续循环的方法调用来触发动画动作。
但是requestAnimationFrame是浏览器针对动画专门优化形成的APi,在性能上比另两者要好。
前面提到,大多数显示器的刷新频率是60Hz,大概相当于每秒钟重绘60次。大多数浏览器都会对重绘操作加以限制,不超过显示器的重绘频率,因为即使超过这个频率用户体验也不会提升。
因此,最平滑动画的最佳循环间隔是 1000ms/60 ,约16ms。这个循环间隔重绘的动画是最平滑的,因为这个速度最接近浏览器的最高限速。
通常,我们将执行动画的每一步传到requestAnimationFrame中,在每次执行完后进行异步回调来连续触发动画效果。
requestAnimationFrame只是将回调的方法传入到自身的参数中执行,而不是通过setInterval调用
要知道,无论是setInterval()还是setTimeout()都不十分精确,
因为它们传入的第二个参数,实际上只是指定了把动画代码添加到浏览器UI线程队列中以等待执行时间。
如果队列前面已经加入其他任务,那动画代码就要等前面的任务完成后再执行。
七.GIF
对于一些特别动画,代码如果不好实现,完全可以制作成GIF图的形式, 可以看下阿里云官网, 上面好几个动画都是gif制作的,效果也挺好的。
比如下面这个GIF图
八. 雪碧图
类似下面这种图片,作为背景图片,改变图片位置,实现动画效果
代码如下
九. Video
这个已经有点超越动画范畴了,可以说几乎任何效果都可以用video实现,根据实际需求,酌情使用,因为视频的加载还是有点慢的~
性能优化
上述是动画的几种实现方式,但是有时候还需要对动画的性能进行优化,找了一些不错的文章,可以参考
前端动画性能优化
无线性能优化
前端性能优化系列 | 加载优化