关于前端:现代图片性能优化及体验优化指南-懒加载及异步图像解码方案

10次阅读

共计 4268 个字符,预计需要花费 11 分钟才能阅读完成。

本文是系列第四篇。系列文章:

  1. 古代图片性能优化及体验优化指南 – 图片类型及 Picture 标签的应用
  2. 古代图片性能优化及体验优化指南 – 响应式图片计划
  3. 古代图片性能优化及体验优化指南 – # 缩放精细化展现及防止布局偏移、拉伸

图片资源,在咱们的业务中堪称是占据了十分大头的一环,尤其是其对带宽的耗费是非常微小的。

对图片的性能优化及体验优化在明天就显得尤为重要。本文,就将从各个方面论述,在各种新个性满头飞的明天,咱们能够如何尽可能的对咱们的图片资源,进行性能优化及体验优化。

懒加载 / 异步图像解码计划

持续下一个章节。本章节,咱们来探讨下图片的懒加载与异步图像解码计划。

图片的懒加载

懒加载是一种网页性能优化的常见形式,它能极大的晋升用户体验。到明天,当初一张图片超过几 M 曾经是常见事了。如果每次进入页面都须要申请页面上的所有的图片资源,会较大的影响用户体验,对用户的带宽也是一种极大的损耗。

所以,图片懒加载的意义即是,当页面未滚动到相应区域,该区域内的图片资源(网络申请)不会被加载。反之,当页面滚动到相应区域,相干图片资源的申请才会被发动。

在过来,咱们通常都是应用 JavaScript 计划进行图片的懒加载。而明天,咱们再图片的懒加载实现上,有了更多不一样的抉择。

JavaScript 计划实现图片的懒加载

首先,回顾一下过往最常见的,应用 JavaScript 计划实现图片的懒加载。

这里,通过 JavaScript 实现的懒加载,次要是两种形式:

  1. 监听 onscroll 事件,通过 getBoundingClientRect API 获取元素图片间隔视口顶部的间隔,配合以后可视区域的地位实现图片的懒加载
  2. 通过 HTML5 新的 IntersectionObserver API,Intersection Observer(穿插观察器)配合监听元素的 isIntersecting 属性,判断元素是否在可视区内,可能实现比监听 onscroll 性能更佳的图片懒加载计划

然而,JavaScript 计划的一个劣势在于,不论如何,须要引入一定量的 JavaScript 代码,进行一定量的运算。

到明天,其实咱们有更多的其余便捷的形式去实现图片的懒加载。

应用 content-visibility: auto 实现图片内容的提早渲染

首先,介绍一个十分有用,然而绝对较为冷门的属性 — content-visibility

content-visibility:属性管制一个元素是否渲染其内容,它容许用户代理(浏览器)潜在地省略大量布局和渲染工作,直到须要它为止。

利用 content-visibility 的个性,咱们能够实现 如果该元素以后不在屏幕上,则不会渲染其后辈元素

假如咱们有这样一个 DEMO:

<div class="g-wrap">
    // 模块 1
    <div class="paragraph">
        <p>Lorem Start!</p>   
        <img src="https://s1.ax1x.com/2023/02/20/pSX1xMV.png" alt="" />
        <p>Lorem End!</p>  
    </div>
    // 模块 2
    <div class="paragraph">
        <p>Lorem Start!</p>   
        <img src="https://s1.ax1x.com/2023/02/20/pSX1xMV.png" alt="" />
        <p>Lorem End!</p>  
    </div>
    // ... 间断几十个上述相似的构造
</div>

只须要给须要提早(实时)渲染的元素,设置简略的 CSS 款式:

.paragraph {content-visibility: auto;}

咱们来看一下,设置了 content-visibility: auto 与没设置的区别。

如果,不增加上述的 content-visibility: auto 代码,页面的滚动条及滚动成果如下:

那么,在增加了 content-visibility: auto 之后,留神察看页面的滚动条及滚动成果:

能够看到滚动条在向下滚动在 一直的抽搐,这是因为上面不在可视区域内的内容,一开始是没有被渲染的,在每次滚动的过程中,才逐步渲染,以此来晋升性能。

Codepen Deom — content-visibility: auto Image Load Demo

content-visibility: auto VS 图片懒加载

当然,其实应用 content-visibility: auto 并不能真正意义上实现图片的懒加载。

这是因为,即使以后页面可视区域外的内容未被渲染,然而图片资源的 HTTP/HTTPS 申请,仍然会在页面一开始被触发!

因而,这也失去了一个十分重要的论断:

content-visibility: auto 无奈间接代替图片懒加载,设置了 content-visibility: auto 的元素在可视区外只是未被渲染,然而其中的动态资源仍旧会在页面初始化的时候被全副加载。因而,它更像是一个虚构列表的代替计划。

对于 content-visibility 本文限于篇幅,没有齐全开展,然而它是一个十分有意思且对渲染性能有帮忙的属性,残缺的教程,你能够看我的这篇文章 — 应用 content-visibility 优化渲染性能

应用 loading=lazy HTML 属性实现图片懒加载

OK,content-visibility 很不错,然而略有瑕疵。然而,咱们还有其余形式。

HTML5 新增了一个 loading 属性。

到明天,除了 IE 系列浏览器,目前都反对通过 loading 属性实现提早加载。此属性能够增加到 <img> 元素中,也能够增加到 <iframe> 元素中。

属性的值为 loading=lazy 会通知浏览器,如果图像位于可视区,则立刻加载图像,并在用户滚动到它们左近时获取其余图像。

咱们能够像是这样应用它:

<img src="xxx.png" loading="lazy">

这样,便能够十分便捷的实现图片的懒加载,省去了增加繁琐的 JavaScript 代码的过程

看看 loading=lazy 到明天(2023-02-26)的兼容性,还是十分不错的:

应用 decoding=async 实现图片的异步解码

除了 loading=lazy,HTML5 还新增了一个十分有意思的属性加强图片的用户体验。那就是 decoding 属性。

HTMLImageElement 接口的 decoding 属性用于通知浏览器应用何种形式解析图像数据。

它的可选取值如下:

  • sync: 同步解码图像,保障与其余内容一起显示。
  • async: 异步解码图像,放慢显示其余内容。
  • auto: 默认模式,示意不偏好解码模式。由浏览器决定哪种形式更适宜用户。

上文其实也提及了,浏览器在进行图片渲染展现的过程中,是须要对图片文件进行解码的,这一个过程快慢与图片格式无关。

而如果咱们不心愿图片的渲染解码影响页面的其余内容的展现,能够应用 decoding=async 选项,像是这样:

<img src="xxx.png" decoding="async">

这样,浏览器便会异步解码图像,放慢显示其余内容。这是图片优化计划中可选的一环。

同样的,咱们来看看到明天(2023-02-26),decoding="async" 的兼容性,整体还是十分不错的,作为渐进加强计划应用,是十分好的抉择。

理论测验 loading=lazydecoding=async 成果

OK,上面咱们制作一个简略的 DEMO,试一下 loading=lazydecoding=async 的成果。

咱们筹备一个领有 339 个图片的 HTML 页面,每个图片文件的 src 大小不一。

<div class="g-container">
    <img src="image.jpeg">
    <img src="image.jpeg">
    // ... 339 个
</div>

CSS 的设置也很重要,因为是纯图片页面,如果不给图片设置默认高宽,最页面刷新的一瞬间,<img> 元素的高宽都是 0,会导致所有 <img> 元素都在可视区内,所以,咱们须要给 <img> 设置一个默认的高宽:

img {
    margin: 8px;
    width: 300px;
    height: 200px;
    object-fit: cover;
}

这样,再不增加 loading=lazydecoding=async 的状态下,看看 Network 的体现:

我这里没有模仿弱网环境,网速十分快,能够看到,发送了 339 个图片资源申请,也就是全副的图片资源在页面加载的过程中都申请了,页面 Load 事件实现的工夫为 1.28s。

好,咱们给所有的图片元素,增加上 loading=lazydecoding=async

<div class="g-container">
    <img src="image.jpeg" loading="lazy" decoding="async">
    <img src="image.jpeg" loading="lazy" decoding="async">
    // ... 339 个
</div>

看看成果:

能够看到,这一次只发送了 17 个图片资源申请,页面 Load 事件实现的工夫为 26ms。

优化前 优化后
1.28s 26 ms

1.28s 到 26ms,成果是非常明显的,如果是弱网环境,对首屏加载性能的晋升,会更为显著!

当然,理论我测试的过程也,也独自试过 decoding="async" 的作用,只是因为是纯图片页面,成果不那么显著。感兴趣的同学,能够自行尝试。

总结一下

在本章节中,咱们介绍了不同的形式实现图片的懒加载、提早渲染、异步解码,它们别离是:

  1. 通过 onscroll 事件与 getBoundingClientRect API 实现图片的懒加载计划
  2. 通过 Intersection Observer(穿插观察器)实现比监听 onscroll 性能更佳的图片懒加载计划
  3. 通过 content-visibility: auto 实现图片资源的提早渲染
  4. 通过 loading=lazy HTML 属性实现图片懒加载
  5. 通过 decoding=async HTML 属性实现图片的异步解码

当然,本文是 古代图片性能优化及体验优化指南 的第四篇,后续将给大家带来图片优化的最初一个章节:

  • 可拜访性 & 图片资源的容错及错误处理

感兴趣的能够提前关注。

最初

OK,本文到此结束,心愿本文对你有所帮忙 :)

想 Get 到最有意思的 CSS 资讯,千万不要错过我的公众号 — iCSS 前端趣闻 😄

更多精彩 CSS 技术文章汇总在我的 Github — iCSS,继续更新,欢送点个 star 订阅珍藏。

如果还有什么疑难或者倡议,能够多多交换,原创文章,文笔无限,满腹经纶,文中若有不正之处,万望告知。

正文完
 0