前端页面性能优化指标

前端页面性能优化指标

一、有哪些指标

优化用户体验的质量一直都是是每个Web站点长期成功的关键,网页核心的性能指标应该是随着时间的推移而不断演变的,目前谷歌浏览器公布的核心Web健康指标——Core Web Vitals包括加载体验、交互性和页面内容的视觉稳定性;
1.Largest Contentful Paint (LCP): Web页主要内容的加载速度,衡量加载体验:为了提供良好的用户体验,LCP应该在页面首次开始加载后的2.5秒内发生。
2.First Input Delay (FID): 衡量可交互性,为了提供良好的用户体验,页面的FID应当小于100毫秒。
3.Cumulative Layout Shift (CLS): 衡量视觉稳定性,为了提供良好的用户体验,页面的CLS应保持小于 0.1。
4.Interaction to Next Paint (INP),用于衡量对页面上用户交互的整体响应能力

在这里插入图片描述
上面的表格就是各项指标的评判标准,其中期望覆盖率指的是至少有相应百分比的用户测试可以达到GOOD标准。

LCP(Largest Contentful Paint)

Largest Contentful Paint (LCP)用于衡量标准报告视口内可见的最大内容元素的渲染时间。为了提供良好的用户体验,网站应努力在开始加载页面的前2.5秒内进行最大内容渲染
在这里插入图片描述

FID( First Input Delay)

FID (First Input Delay即记录用户和页面进行首次交互操作所花费的时间。FID指标影响用户对页面交互性和响应性的第一印象。为了提供良好的用户体验,站点应努力使首次输入延迟小于100毫秒。
在这里插入图片描述

CLS(Cumulative Layout Shift)

通俗的说,叫作视觉稳定性

在这里插入图片描述
您是否曾经在访问一个Web页面时发生下面的情况?在阅读文章的同时文字突然移动了、你突然找不到你阅读的位置了、点按钮的时候按钮被移动到了其他地方,导致你点了其他东西?
页面内容的意外移动通常是由于异步加载资源或将DOM元素动态添加到现有内容上方的页面而发生的。罪魁祸首可能是尺寸未知的图像或视频,渲染后比其后备更大或更小的字体,或者是动态调整自身大小的第三方广告或小部件。
Cumulative Layout Shift CLS可通过测量实际用户发生的频率来帮助您解决此问题。
CLS会测量在页面的整个生命周期中发生的每个意外的样式移动的所有单独布局更改得分的总和。布局的移动可能发生在可见元素从一帧到下一帧改变位置的任何时候。为了提供良好的用户体验,网站应努力使CLS分数小于0.1
在这里插入图片描述

INP(Interaction to Next Paint)

2022年 Google新引入的标准,INP测量网页响应用户交互所花费的时间,从用户开始交互到在屏幕上绘制下一帧的那一刻.
低于或等于 200 毫秒的 INP 表示良好的响应能力。
INP 最终可能会取代首次输入延迟 (FID) 作为核心 Web 生命指标(Core Web Vitals)之一。
由于 INP 还包括处理时间和呈现延迟,因此它具有比首次输入延迟更高的值。它还查看最慢的页面交互,而不像 FID 只查看第一个
在这里插入图片描述

其他类指标

FP - First Paint - 首次渲染,就是说开始渐进式解析DOM结构并在页面上有所体现了
FCP - First Contentful Paint - 首次内容渲染,此时页面已经包含了一些文字,图标等
DCL - DOMContentLoaded - DOM完全加载及解析事件触发
FMP - First Meaningful Paint - 首次有效渲染,此时页面已经包含了更多文字,图标等
LCP - Large Content Paint - 革命就要胜利了
L - Load 页面加载完成

二、如何度量计算这些指标?

在这里插入图片描述

1、使用Chrome插件–web-vitals-extension来获取这些指标

1)首先下载插件并解压成文件夹
https://github.com/GoogleChrome/web-vitals-extension
在这里插入图片描述
(2)Chrome浏览器导入插件
在这里插入图片描述
在这里插入图片描述
(3)打开任意页面,点击插件图标,稍等几秒钟,即可看到指标计算结果
在这里插入图片描述

2、Chrome DevTools

(1)Performance Insights 选项卡也显示了Core Web Vitals主要指标
在这里插入图片描述
(2)Performance标签可以显示其他类指标:

在这里插入图片描述
(3)Lighthouse会计算出核心指标LCP和CLS,以及对网站的整体性能进行评价,例:在谷歌浏览器调式模式下(F12),切换到Lighthouse 选项卡
在这里插入图片描述
在这里插入图片描述

3、Performance Timeline API

Performance Timeline API是对Performance API的扩展,可以狭义的理解为浏览器performance对象中以下三个主要方法:1.getEntries()
2.getEntriesByType()
3.getEntriesByName()

4、实例计算

在这里插入图片描述
在这里插入图片描述

三、如何优化页面

1、LCP(Largest Contentful Paint)优化

优化LCP主要考虑哪些元素?
1.<img>元素
2.<image>元素内的<svg>元素
3.<video>元素
4.通过**url()**函数加载背景图片的元素
5.包含文本节点或其他内联文本元素子级的块级元素。
LCP较差的最常见原因是:
1.服务器响应时间慢
2.阻断渲染的Javascript和CSS
3.资源加载时间慢
4.客户端渲染

如何改善 LCP?

优化服务器

缓存HTML离线页面,缓存页面资源,减少浏览器对资源的请求–尽量不要请求无用的资源。
尽量减小资源阻断渲染:CSSJavaScript压缩、合并等等
对图片进行优化:转化图片的格式为JPG或者WEBP等等的格式,降低图片的大小;将fetchpriority="high"属性添加给最重要的图像元素:

<img src="./flower.jpg" class="img-style" id="firstImg"fetchpriority="high">

这将告诉浏览器在加载低优先级资源之前发出此请求。默认情况下,图像请求的优先级较低,在呈现页面后,首屏图像的优先级会提高。添加fetchpriority=high意味着浏览器可以立即启动图像请求。
1.对HTML重写、压缩空格、去除注释等。减少HTML大小,加快速度。
2.使用CDN加快请求速度
3.使用preconnect尽快与服务器建立链接、使用dns-prefetch尽快进行DNS(把域名解析成对应的IP地址)查找。
preconnect:元素属性的关键字preconnect是对浏览器的提示,即用户可能需要来自目标资源的资源,因此浏览器可以通过抢先启动与该资源的连接来改善用户体验。

<link rel="preconnect" href="//the-domain-to-be-preconnect.com"crossorigin="anonymous" />

dns-prefetch: 即DNS预获取
Chrome 和 Firefox 3.5+ 内置了 DNS Prefetching 技术并对DNS预解析做了相应优化设置。所以即使不设置此属性,Chrome 和 Firefox 3.5+ 也能自动在后台进行预解析。目前很多大型站点也应用了这一优化,例如淘宝:
在这里插入图片描述

优化阻断渲染的资源

JavaScriptCSS都是会阻断页面渲染的资源,需要尽可能的对CSS和JavaScript文件进行压缩、延迟加载首屏无需使用的JavaScript、内联关键的CSS等来减小阻断时间。

优化资源加载时间

对图片进行优化。转化图片的格式为JPG或者WEBP等等的格式,降低图片的大小。对重要的资源进行预加载,比如为style标签添加rel="preload"属性使用GzipBrotli压缩页面资源,降低传输时间

实例

1)将大图片进行转码

直接将图片显示在页面上:图片大小为8,651.1 KiB,8兆左右
在这里插入图片描述

在这里插入图片描述
将图片转换为base64编码后再展示
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

(2)使用preconnect预加载

在这里插入图片描述
计算结果:
在这里插入图片描述

2、FID( First Input Delay)优化

FID考虑哪些元素?

浏览器接收到用户输入操作时,主线程正在忙于执行一个耗时比较长的任务,只有当这个任务执行完成后,浏览器才能响应用户的输入操作。它必须等待的时间就此页面上该用户的FID值。
例如,以下所有HTML元素都需要在响应用户交互之前等待主线程上正在进行的任务完成:
1. 文本输入框,复选框和单选按钮<input>,<textarea>
2. 选择下拉菜单<select>
3. 链接<a>

如何提高 FID

以下几个方面是提高FID的重要指标,同上面改善LCP的方法:
缩小并压缩JavaScript文件
延迟加载首屏不需要的JavaScript
尽量减少未使用的polyfill(polyfill:用于实现浏览器并不支持的原生API的代码)

3、CLS(Cumulative Layout Shift)优化

不要使用无尺寸元素

图像和视频等元素上始终需要包括widthheight尺寸属性,现代浏览器会根据图像的widthheight属性设置图像的默认长宽比,知道纵横比后,浏览器就可以为元素计算和保留足够的空间。
永远不要在现有内容之上插入内容,除非是响应用户交互。这确保了预期的布局变化。

提前给广告位预留空间

很多页面广告都是动态插入的,所以一定要提前为广告位预留一定空间。

警惕字体变化

字体通常是大文件,需要一段时间才能加载,一些浏览器直到下载完字体后才呈现文本font-display: swap告诉浏览器默认使用系统字体进行渲染,当自定义字体下载完成之后再进行替换,另外,你可以使用<link rel="preload">更早的加载字体文件。
在这里插入图片描述

4、INP(Interaction to Next Paint)优化

INP主要考虑哪些因素?

交互式元素的任何鼠标单击。
在包括触摸屏的任何设备上点击交互元素。
按物理键盘或屏幕键盘上的键。

如何提升优化INP

最好的方法是优化主线程工作

尽可能少的使用插件

这意味着确保将第三方字体等内容保持在最低限度(即,仅使用系统字体),并且您不会在页面加载时使用太多插件。

例如,假设你有一个WordPress网站,有15个广告插件,专门用于在你的页面上显示广告——也许你不必全部使用。

关闭90%的插件将有助于提高INP,并简化主线程工作——因为这会延迟页面加载。

减少http请求次数

80%的响应时间花在下载网页内容(images, stylesheets, javascripts, scripts, flash等)。减少请求次数是缩短响应时间的关键 css雪碧图(CSS Sprites): 就是把多个图片拼成一副图片,然后通过CSS来控制在什么地方具体显示这整张图片的什么位置,可减少请求图片的数量

#home {  
	width: 46px; 
	height: 44px;  
 	background: url(img_navsprites.gif) 0 0;
 }

Inline images: 通过编码的字符串将图片内嵌到网页文本中。例如下面的inline image的显示效果为一个勾选的checkbox。

.sample-inline-png {   
	 padding-left: 20px;    
	 background: white url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQAQMAAAAlPW0iAAAABlBMVEUAAAD///+l2Z/dAAAAM0lEQVR4nGP4/5/h/1+G/58ZDrAz3D/McH8yw83NDDeNGe4Ug9C9zwz3gVLMDA/A6P9/AFGGFyjOXZtQAAAAAElFTkSuQmCC') no-repeat scroll left top;
 }

5、其他类提升

HTML类

(1)减少DOM元素数量

网页中元素过多对网页的加载和脚本的执行都是沉重的负担,500个元素和5000个元素在加载速度上会有很大差别。
想知道你的网页中有多少元素,通过在浏览器中的一条简单命令就可以算出,

document.getElementsByTagName('*').length

(2)减少iframe数量

使用iframe要注意理解iframe的优缺点:
优点
1.可以用来加载速度较慢的内容,例如广告。
2.安全沙箱保护。浏览器会对iframe中的内容进行安全控制。
3.脚本可以并行下载
缺点
1.即使iframe内容为空也消耗加载时间
2.会阻止页面加载
3.没有语义

(3)避免404

404我们都不陌生,代表服务器没有找到资源,我们要特别要注意404的情况不要在我们提供的网页资源上,客户端发送一个请求但是服务器却返回一个无用的结果,时间浪费掉了。

更糟糕的是我们网页中需要加载一个外部脚本,结果返回一个404,不仅阻塞了其他脚本下载,下载回来的内容(404)客户端还会将其当成Javascript去解析。

(4)避免空的图片src

**straight HTML**
<img src="">

JavaScript**var img = new Image();
img.src = "";

(5)其他

CSS类

(1)将样式表置顶

经样式表(css)放在网页的HEAD中会让网页显得加载速度更快,因为这样做可以使浏览器逐步加载已将下载的网页内容。这对内容比较多的网页尤其重要,用户不用一直等待在一个白屏上,而是可以先看已经下载的内容。

如果将样式表放在底部,浏览器会拒绝渲染已经下载的网页,因为大多数浏览器在实现时都努力避免重绘,样式表中的内容是绘制网页的关键信息,没有下载下来之前只好对不起观众了

(2)避免css表达式

CSS表达式可以动态的设置CSS属性,在IE5-IE8中支持,其他浏览器中表达式会被忽略。例如下面表达式在不同时间设置不同的背景颜色。

background-color: expression( (new Date()).getHours()%2 ? "#B8D4FF" : "#F08A00");

CSS表达式的问题在于它被重新计算的次数远比我们想象的要多,不仅在网页绘制或大小改变时计算,即使我们滚动屏幕或者移动鼠标的时候也在计算,因此我们还是尽量避免使用它来防止使用不当而造成的性能损耗。

如果想达到类似的效果我们可以通过简单的js脚本做到。

<html>
	<head></head>
	<body>
		<script type="text/javascript">
			var currentTime = new Date().getHours();
			if (currentTime%2) {    
				if (document.body) {        
					document.body.style.background = "#B8D4FF";    
					}
				}else {    
					if (document.body) {        
						document.body.style.background = "#F08A00";    
						}
					}
			</script>
		</body>
</html>

(3)用代替@import

避免使用@import的原因很简单,因为它相当于将css放在网页内容底部。

(4)资源压缩

利用webpackgulp/gruntrollup等模块化工具,将css代码进行压缩,使文件变小,大大降低了浏览器的加载时间。

(5)合理使用选择器

css匹配的规则是从右往左开始匹配,例如**#markdown .content h3**匹配规则如下:
1.先找到h3标签元素
2.然后去除祖先不是.content的元素
3.最后去除祖先不是#markdown的元素

如果嵌套的层级更多,页面中的元素更多,那么匹配所要花费的时间代价自然更高
所以我们在编写选择器的时候,可以遵循以下规则:

1.不要嵌套使用过多复杂选择器,最好不要三层以上
2.使用id选择器就没必要再进行嵌套
3.通配符和属性选择器效率最低,避免使用

总结:

css实现性能的方式可以从选择器嵌套、属性特性、减少http请求这三面考虑,同时还要注意css代码的加载顺序

JS类

(1)将脚本置底

1.把脚本置底,这样可以让网页渲染所需要的内容尽快加载显示给用户。
2.现在主流浏览器都支持defer关键字,可以指定脚本在文档加载后执行。
3.HTML5中新加了async关键字,可以让脚本异步执行。

(2)使用外部Javascirpt和CSS文件

1.使用外部Javascript和CSS文件可以使这些文件被浏览器缓存,从而在不同的请求内容之间重用,也减小了网页内容的大小。
2.使用外部Javascript和CSS文件的决定因素在于这些外部文件的重用率,如果用户在浏览我们的页面时会访问多次相同页面或者可以重用脚本的不同页面,那么外部文件形式可以为你带来很大的好处。但对于用户通常只会访问一次的页面,例如microsoft.com首页,那inline的javascript和css相对来说可以提供更高的效率。

(3)精简Javascript和CSS

将Javascript或CSS中的空格和注释全去掉?个人感觉不太合理,代码没有格式了

body {   
	 line-height: 1;
 }
 ol,  ul {   
 	 list-style: none;
 }
 blockquote, q {   
 	 quotes: none;
 }

精简后版本

body{line-height:1}ol,ul{list-style:none}blockquote,q{quotes:none}

统计表明精简后的文件大小平均减少了21%,即使在应用Gzip的文件也会减少5%

(4)去除重复脚本

重复的脚本不仅浪费浏览器的下载时间,而且浪费解析和执行时间。一般用来避免引入重复脚本的做法是使用统一的脚本管理模块,这样不仅可以避免重复脚本引入,还可以兼顾脚本依赖管理和版本管理。

(5)减少DOM访问

通过Javascript访问DOM元素没有我们想象中快,元素多的网页尤其慢,对于Javascript对DOM的访问我们要注意

1.缓存已经访问过的元素
2.避免通过Javascript修复layout

优化总结

主要分为加载性能优化渲染性能优化

加载性能优化

1、减少请求次数;
2、减少请求资源的大小;
3、网络优化;

(1)减少请求次数

为什么减少请求次数?
以chrome为例:
同一域名下,同一GET请求的并发数是1,也就是说上一个请求结束,才会执行下一个请求,否则置入队列等待发送;
同一域名下,不同GET/POST请求的并发数量是6。
所以资源请求数过多肯定比请求数少更耗时,直接影响网页的加载速度;

减少请求次数方式
(1)图片资源
CSS雪碧图 技术把一些常用、重复使用的小图合并成一张大图,使用的时候通过背景图片定位(background-position),定位到具体的某一张小图上;
字体图标 一个图标字体比一系列图像要小,一旦图标字体加载了,图标就会马上渲染出来,不需要下载一个图像,可以减少HTTP请求。
base64编码
(2)合理利用缓存
(3)合并CSS和JS文件

(2)减少请求资源大小

1.图片压缩:转码、使用字体图标等
2.文件压缩:gzip压缩、Tree Shaking技术等

(3)网络优化

1.CDN
2.第三方组件按需加载

渲染性能优化

浏览器渲染过程

  1. 解析HTML生成DOM树。
  2. 解析CSS生成CSSOM规则树。
  3. 解析JS,操作 DOM 树和 CSSOM 规则树。
  4. 将DOM树与CSSOM规则树合并在一起生成渲染树。
  5. 遍历渲染树开始布局,计算每个节点的位置大小信息。
  6. 浏览器将所有图层的数据发送给GPU,GPU将图层合成并显示在屏幕上
    在这里插入图片描述
    重排
    当改变 DOM 元素位置或大小时,会导致浏览器重新生成渲染树,这个过程叫重排。
    重绘
    当重新生成渲染树后,就要将渲染树每个节点绘制到屏幕,这个过程叫重绘。不是所有的动作都会导致重排,例如改变字体颜色,只会导致重绘。
    重排和重绘这两个操作代价非常大,因为 JavaScript 引擎线程与 GUI 渲染线程是互斥,它们同时只能一个在工作,因此重排和重绘会阻塞主线程。

渲染性能优化方式

(1)资源加载优先级控制

1.css引入放在head标签尾部,script脚本放在body标签尾部;
2.脚本与DOM/其它脚本的依赖关系很强:对<script>设置defer
3.脚本与DOM/其它脚本的依赖关系不强:对<script>设置async
4.preload 加载当前路由必需资源,优先级高,一般对于 Bundle资源(静态资源文件包,不包含可执行文件)使用preload;
5.refetch 优先级低,在浏览器空闲状态时加载资源,一般用以加载非首页资源;
6.preload/prefetch preload/prefetch可控制 HTTP 请求优先级,从而达到关键请求更快响应的目的;dns-prefetch,可对主机地址的 DNS 进行预解析。

(2)减少重排重绘

1.减少页面DOM操作;
2.对 DOM 元素执行一系列操作,可以将 DOM 元素脱离文档流,修改完成后,再将它带回文档。例如:隐藏元素(display:none);
3.用 JavaScript 修改样式时,最好不要直接修改单个样式属性,而是替换 class 来改变样式;
4.合理使用防抖和节流;

(3)利用缓存

页面缓存(keep-alive),接口缓存(减少数据更新导致的页面刷新)

猜你喜欢

转载自blog.csdn.net/A__men/article/details/129146018