image.png

流程

  • 1 .在浏览器输入url后,浏览器会向服务器发送请求,浏览器返回一个html文件(二进制文本文件,相应头包含Content-Type:text/html )
  • 2 .浏览器解析html代码把html元素解析成js对象,解析完成✅,根据嵌套结构形成DOM树(包含html元素和文本节点(⚠️注意:会包含display:none的元素,注释,script标签) )
  • 3 .处理CSS标记,然后根据W3C css默认标准构成层叠样式表模型CSSOM(CSS解析可以与DOM解析同时)
  • 4 .然后将CSSOM和DOM树结合生成render tree(不会包含display:none 或者 尺寸为 0 的元素,同时根据规则把DOM分割成多个图层)
  • 5 .因为生成render tree 时只是将DOM元素和样式相结合,并不包含节点位置信息和大小信息,所以通过Layout(回流)阶段来计算在视口当中的位置和大小(float元素,absoulte元素,fixed元素脱离标准流就是脱离 render tree )
  • 6 .确定位置,大小之后浏览器就在屏幕上面绘制paint(重绘)阶段

渲染阻塞

JS可以操作DOM来修改DOM结构,可以操作CSSOM来修改节点样式,这就导致了浏览器在遇到<script>标签时,DOM构建将暂停,直至脚本完成执行,然后继续构建DOM。如果JavaScript脚本还操作了CSSOM,而正好这个CSSOM还没有下载和构建,浏览器甚至会延迟脚本执行和构建DOM,直至完成其CSSOM的下载和构建。所以,script标签的位置很重要。

由于CSSOM负责存储渲染信息,浏览器就必须保证在合成渲染树之前,CSSOM是完备的,这种完备是指所有的CSS(内联、内部和外部)都已经下载完,并解析完,只有CSSOM和DOM的解析完全结束,浏览器才会进入下一步的渲染,这就是CSS阻塞渲染。

CSS阻塞渲染意味着,在CSSOM完备前,页面将一直处理白屏状态,这就是为什么样式放在head中,仅仅是为了更快的解析CSS,保证更快的首次渲染。

回流和重绘

reflow(回流)

当浏览器发现布局发生了变化,这个时候就需要倒回去重新渲染,这个回退的过程叫reflowreflow会从html这个root frame开始递归往下,依次计算所有的结点几何尺寸和位置,以确认是渲染树的一部分发生变化还是整个渲染树。

repaint(重绘)

repaint则是当我们改变某个元素的背景色、文字颜色、边框颜色等等不影响它周围或内部布局的属性时,屏幕的一部分要重画,但是元素的几何尺寸和位置没有发生改变。

⚠️注意:reflow回流必定引起repaint重绘,重绘可以单独触发。

优化

  • 尽量用transform来做形变和位移
  • position属性为absolutefixed的元素,重排的开销会比较小,因为不用考虑它对其他元素的影响。
  • 只在必要的时候,才将元素的display属性为可见,因为不可见的元素不影响重排和重绘。另外,visibility : hidden的元素只对重绘有影响,不影响重排。
  • 使用window.requestAnimationFrame()window.requestIdleCallback()这两个方法调节重新渲染。
  • 简化并优化CSS选择器,尽量将嵌套层减少到最小。

https://www.jianshu.com/p/e6252dc9be32