当前位置: 首页 > Web前端 > CSS

网页图片资源的加载和渲染时序

时间:2023-03-30 22:46:18 CSS

本文研究页面上图片资源的加载和渲染时序,以便我们更好地管理图片资源,避免不必要的流量,提升用户体验。浏览器的工作流程要研究图片资源的加载和渲染,首先要了解浏览器的工作原理。以Webkit引擎的工作流程为例:从上图可以看出,浏览器加载一个HTML页面后,会进行如下操作:解析HTML—>构建DOM树并加载样式—>解析样式—>构建样式规则树并加载javascript—>执行javascript代码,将DOM树与样式规则树进行匹配,构建渲染树,计算元素位置,进行布局绘制。从上图中,我们不能直观的看出图片资源是什么时候开始加载的。下图是图片加载渲染的时序:解析HTML【遇到标签加载图片】—>构建DOM树加载样式—>解析样式【遇到背景图片链接加载不上】—>构建样式规则treeandloadjavascript—>执行javascript代码结合DOM树和样式规则树匹配构建渲染树【遍历DOM树时加载相应样式规则上的背景图片】计算布局绘制的元素位置【开始渲染image]图片加载和渲染规则并不是页面中所有的标签图片和样式表背景图片都会被加载。display:none

图片资源请求如下:对于设置了display:none属性的元素,图片不会被渲染,但是将被加载。原理在匹配DOM树和样式规则树构建渲染树时,只有可见的元素和它们对应的样式规则会被组合输出到渲染树,也就是说还有不可见的元素。在匹配DOM树和样式规则树时,如果在元素对应的样式规则中找到display:none,浏览器会认为该元素不可见,因此不会将该元素输出到渲染树。上述代码中,标签元素上的图片会在解析HTML时加载。将DOM树与样式规则树匹配构建渲染树时,遍历DOM树上的元素,发现元素对应的样式规则上找到background-image属性,会加载背景图片,但是由于该元素是不可见元素(对应样式规则上的diaplay:none),该元素及其对应的样式规则不会输出到渲染树中。绘制时,由于渲染树上不存在该元素,所以不会绘制该元素的背景图。
图片资源请求如下:如果设置了display:none属性元素的子元素,样式中的背景图片sheet不会被渲染,也不会被加载;标签的图片不会被渲染,但是会被加载。原理如上所述,在匹配DOM树和样式规则树时,如果元素对应的样式规则上有display:none,浏览器会认为该元素的子元素不可见,所以不会显示theelement元素的子元素输出到渲染树。当构建渲染树遇到设置了display:none属性的不可见元素时,不会继续遍历不可见元素的子元素,所以不会加载该元素中子元素的背景图。绘制时,由于渲染树上没有设置display:none属性元素,并且该元素的子元素没有变化,所以不会渲染该元素中子元素的背景图。重复image.img-blue{background-image:url(../image/blue.png);}
图片资源请求如下:页面中的多个标签或样式表中的背景图片图片路径相同,且图片只加载一次。原理当浏览器请求资源时,首先会判断是否有缓存。如果有缓存并且还没有过期,就会从缓存中读取,不会再次请求。先加载的图片会保存在浏览器缓存中,以后再次请求相同路径的图片时会直接读取缓存中的图片。没有元素的背景图片.img-blue{background-image:url(../image/blue.png);}.img-orange{background-image:url(../image/orange.png);}图片资源请求如下:不加载不存在的元素的背景图。原理不存在的元素不会输出到DOM树中。渲染树构建过程中遍历DOM树时,无法遍历不存在的元素,所以不会加载图片,也不会输出到渲染树。在解析rendertree的时候,不存在的元素无法解析,不存在的元素自然不会被渲染。伪类背景图片.img-green{background-image:url(../image/green.png);}.img-green:hover{background-image:url(../image/red.png);}触发hover前的图片资源请求如下:触发hover后的图片资源请求如下:当伪类被触发时,hover上的背景图片将加载伪类样式。原理在触发hover之前,构建渲染树的过程中,遍历DOM树时,这个元素匹配的样式规则是nohoverstateselector.img-green的样式,所以nohoverstateselector.img的样式-green在绿色.png图像上加载。这个元素是可见元素,所以会输出到渲染树中,绘制的时候也会渲染green.png。hover被触发后,由于.img-green:hover的优先级更高,在构建新渲染树的过程中,元素匹配hover状态选择器,所以hover状态选择器.img-green:hover被加载为红色.png图像样式。这个元素是可见元素,所以会输出到渲染树,绘制的时候也会渲染red.png。应用占位图片在样式表中使用背景图片作为占位图片时,必须将背景图片转换为base64格式。这是因为背景图片的加载顺序在标签后面,可能要等到标签图片加载完毕后才开始加载背景图片,达不到预期的效果。在很多预加载场景中,图片只有在状态改变或触发后才会显示。比如点击一个Tab后,一个隐藏的带有display:none的父元素就会显示出来,这个父元素中的子元素图片就会显示在父元素中。鼠标悬停在图标上后,图标图片发生变化,直到图标悬停后才开始加载图片,导致闪烁体验不友好。在这种情况下,我们需要预加载图像。预加载的方式有很多种:如果是小图标,可以合并成一个sprite图片,所有的图标一起加载,然后再改变状态。使用上面提到的元素,设置display:none属性,图像不会被渲染,但会被加载。将要预加载的图像添加到元素背景图像或设置了display:none的标签中。在javascript中创建一个img对象,并将图片url设置为img对象的src属性。欢迎关注:Leechikit