渲染
最编程
2024-02-13 22:54:50
...
具体可以看:【JavaScript高级】浏览器原理:渲染引擎解析页面步骤、回流和重绘、composite合成、defer与async_karshey的博客
步骤
用户看到的页面分为两个阶段:页面内容加载完成DOMContentLoaded
和 页面资源加载完成Load
阶段。
-
DOMContentLoaded
事件触发时,仅DOM加载完成 -
load
事件触发时,页面上所有DOM、样式、脚本、图片都加载完成
渲染步骤大致分为以下6步:
- 解析HTML,构建DOM树
- 解析CSS,生成CSS规则树
- 合并DOM树和CSS规则树,生成render树
- 布局 render树(Layout/reflow),负责各元素尺寸、位置的计算
- 绘制 render树(paint),绘制页面像素信息
- 浏览器将各层信息发给GPU,GPU将各层合成(composite),显示在屏幕上
注意:以上步骤不一定一次性顺序完成。比如DOM树或CSS树被修改时,这些操作会重复执行。
DOM树与render树
DOM树与render树不完全对应:
-
display:none
的元素在DOM树中,但不在render树中 -
visibility:hidden
的元素在render树中
回流与重绘
回流reflow:浏览器布局发生变化后,要倒回去重新渲染。这个回退过程为回流。
重绘repaint:改变某个元素的背景色、文字颜色等不影响周围和内部布局的属性时,会引发重绘。
注意:
-
display:none
会触发回流,因为它不在render树中,改变了render布局 -
visibility:hidden
只会触发重绘,它的语义是隐藏元素,元素仍然占据布局空间,只是渲染成一个空框。此属性的改变不会改变布局,因此只触发重绘。
引起回流
- 页面的第一次渲染(初始化)
- DOM树的变化(如:增删节点)
- render树变化
- 浏览器窗口resize
- 获取元素的某些属性
现代浏览器会对回流做优化,它会等到足够数量的变化发生,再做一次批处理回流。
浏览器为了获得正确的值也会提前触发回流,这样就使得浏览器的优化失效了,这些属性包括offsetLeft、offsetTop、offsetWidth、offsetHeight、 scrollTop/Left/Width/Height、clientTop/Left/Width/Height、调用了getComputedStyle()。
引起重绘
- 引起回流必然引起重绘:回流对应render树的布局,重绘对应render树的绘制,布局在绘制之前
- 背景色、字体颜色改变等
减少回流与重绘
- 避免逐个修改节点样式,尽量一次性修改
- 可以将需要多次修改DOM的元素设置为
display:none
,操作完再显示(display:none
不再render树内,则render不会发生改变,不会引发回流重绘) - 避免多次读取某些属性
上一篇: 搞定前端面试必备的八个知识点(详尽版)
下一篇: 前端新手必知:浏览器的八个基本概念