前端入门之网页性能优化(三)

时间:2022-01-05 来源:未知网络 作者:996建站网

好,其实网页性能优化讲到上一篇,对于入门的同学来讲就已经差不多了。现在做一下小结。

对于HTML、CSS和JavaScript都通用的一个优化策略就是Minify,Compress,和Cache(缩小,压缩和缓存)。对于CSS来讲就是添加媒体查询和内嵌CSS。对于JavaScript来讲就是延缓加载(用onload事件)和在<script>字段里添加async关键字。总结起来就是需要优化CRP(关键呈现路径)的三个指标:1. 关键资源数 2. 关键字节大小 3.关键路径长度。

前端入门之网页性能优化(三)插图

看这个例子,我们可以看到关键资源数量是5个,分别是1个HTML,1个CSS和3个JS文件,关键字节量就是这个五个文件大小的加和,而关键路径长度就是5,即5次请求才能加载完。

到这里我们就弄明白如何对一个网页做一个基础的性能优化了。实际上,一般设备的刷新频率是60次每秒,也就是60hz,那我们的网页也要做到60FPS才算是比较合格的,也就是每1秒需要展示60帧的内容,那么对于每一帧的渲染其实只有16ms。如果浏览器花费较长的时间才能渲染一帧,帧速度下降就出出现卡顿,这会造成很差的用户体验。其实可以把一帧的渲染流程看做一个pipline

前端入门之网页性能优化(三)插图1

一般情况下,都是会通过JavaScript来修改样式的,不过也有其他方式比如CSS Animations,tansitions或者是新的web animations API等等。也就是做出修改-渲染样式-计算布局-像素着色-图层合成。但并不是每一次修改都需要经历完这几个步骤。第一种情况,如果通过JS或者CSS修改了网页的样式和元素的几何结构,那么浏览器就需要重新计算样式,计算布局,染色,合成多个图层。第二种情况,如果通过JS或者CSS只修改了网页的样式,并没有修改几个结构,比如换了一张照片,或者只是添加了一个阴影,这样的话浏览器就不需要重新计算布局,只需要计算样式,染色,合成图层。点这里可以详细了解css的哪些操作会出发哪些步骤。

前端入门之网页性能优化(三)插图2

下面就要从更高的层面去分析可优化的地方了。一个网络应用的生命周期一般分为四个部分,即加载,闲置,动画,响应。而一般情况下加载的时间在1s内完成就不会影响用户体验。加载完成后,一般用户是会有50ms的闲置时间,那这50ms对于我们完成一些耗时的计算或者处理是非常有帮助的。利用这个时间做一些不太重要的工作来确保此后的所有操作都能够及时响应。对于交互来说,当用户点击了一个按钮,在100ms内做出响应的话就不会有卡顿的表现。对于动画来说依然是要做到60fps,即每一帧的渲染时间要在16ms以内。比如用户滚动屏幕或者其它的一些动画。

现在我们看上面的pipline。对于开始的JavaScript,我们首先要弄清楚你写代码的步骤并不是浏览器执行的步骤,因为JavaScript的引擎很复杂,因此你就没有必要在这上面去做微优化。微优化就是说你没有必要纠结于选择for循环还是while循环,因为你也不知道引擎是怎么处理这两个循环的,并且优化的效果小到可以忽略不计。因此我们要把优化思路放到其他方向。如果能在网页加载的1000ms内,或者闲置的50ms内,响应的100ms,动画的16毫秒内完成JavaScript的处理不就不影响用户体验了吗?也就是说要在每一帧最开始的时候就去执行JavaScript。requestAnimationFrame( )就能够实现让JavaScript尽早在每一帧的开始去执行。要想达到60fps的动画效果,每一帧的渲染时间最多只能1000ms/60 = 16ms。但是实际情况是浏览器还有其他的工作要做,留给渲染的时间只有10ms。JavaScript的执行也最多只能占3-4ms,因为后面还有样式,布局,染色和合成图层的工作要去做。在旧时代,实现这个功能的是setTimeOut( )和setInterval( )这两个函数。这里再介绍一个工具Web Workers(详细介绍戳这里)。它能够开辟出来一条独立于操作系统之外的新线程,可以用来处理执行时间比较长的JavaScript。

前端入门之网页性能优化(三)插图3

但是要注意主线程与Web Works线程无法相互通信。

在pipline里面JavaScript的下一步就是样式(style)。要知道修改样式所耗费的成本和需要修改样式的元素的个数是成线性增长的。因此在这里要根据实际情况注意控制需要修改样式的元素的数量。那除了这一点,还有一点就是要注意选择器匹配的问题。选择器匹配是指确定某些样式是否应该应用到任何给定DOM元素的过程。复杂的选择器会给浏览器带来更多的工作量。比如.box:nth.title就比.box-three要复杂,当有大量的复杂选择器的时候,对于浏览器就会产生比较大的性能消耗。修改样式的下一步是聚酸布局,在这一步里,要注意避免强制同步布局。因为在写代码的时候,一不小心就会犯这个错误。

前端入门之网页性能优化(三)插图4

看着三段代码,上面两段都触发了强制同步布局。因为访问.scrollY和访问.offsetHeight都会导致浏览器运行布局(会触发layout的事件看这里)。因此每次都是先布局,然后修改样式,根据pipline,然后又布局。这样不好。而最下面的那段程序就不会导致强制同步布局,因为它在循环体外面只访问了一次.offsetWidth,这就是个很好的策略,布局运行一次,然后批量更新样式。那么修改前两段代码的方式就是要在这一帧最开始的时候读取一次布局属性,然后在这一帧快结束的时候批量修改样式,这是一步小小的修改,但是却大大的优化了性能。修改如下图

前端入门之网页性能优化(三)插图5

最后就是paint和composite,即染色和渲染层的合成。对于paint,要避免不要每次都对整个页面进行染色,只对需要重新染色的元素进行染色就可以了。类似于PS的多个图层,网页在处理的时候也是有很多图层,因为如果只有一个图层,那么在染色的时候整个页面都需要重新染色,每一帧都这么做的话是很耗费性能的。因此可以分成多个图层,染色这个过程就可以在相应的图层上去做,最后再合成展示。对于每一个元素,可以加上这个属性{will-change:transform}就可以把当前元素变成一个新的图层。但是如果创建了很多新的图层也是对性能很不好的,所以需要权衡。对于10ms完成渲染一帧来讲,更新图层和合成图层都不应该超过2ms。关键在于为自己的项目创建合适的图层数量。

收尾之前再来说一点技术名词的发音哈,对于咱们经常读的JavaScript[dʒɑːvə skrɪpt],注意音标[dʒɑːvə],不要读成“假娃”,这样很难听!要注意前面一个音要舌尖顶着上颚,第二个音要上牙咬着下嘴唇,来,试着发一下音!还有Composite,[kəm'pɑːzət],不要读成com'pou'sit.美音有很多o都发[ɑː]音,这个要注意一下。

好了,网页性能优化的方法很多很多。因为本文讲的是入门,所以大概就先介绍到这里,希望对于新入门的同学会有所帮助。他日等我也掌握更多技能,更有经验之后再来做补充。

前端入门之网页性能优化(二)

前端入门之网页性能优化(一)

前端入门之网页性能优化(三)插图6

微信扫一扫 关注公众号

微信扫一扫 使用小程序

百度扫一扫 使用小程序