浏览器渲染机制二

399 阅读4分钟

渲染树的构建

在dom树和cssdom树都渲染完成之后,就会开始构建渲染树。渲染树就是对dom和cssdom树的结合,得到每一个节点对应什么样式的数据结构。这个结合的过程大体上是遍历整个dom树。然后再cssdom树里匹配到对应的样式。渲染树有一下几个特点:

1.渲染树的根节点是html

在 Google Web Fundamentals 这个文档中,渲染树的根节点是body,实际上html节点上的样式也是可以显示再页面上的,而head标签里的内容和显示没有关系,所以渲染树是没head这部分的。

2.渲染树和dom树的结构并不完全一致

渲染树会把所有不可见的元素忽略掉,所以dom树的节点有display:none;属性节点以及他的子节点,最终都不会出现在渲染树中。但是有visicility:hidden样式的元素会出现在渲染树中,因为具有这个样式的元素是需要占位的,只不过是它不显示出来。

3.样式优先级

同一个dom节点,会匹配多个cssdom节点,而最终显示的由哪个css样式来确定,就是样式优先级的问题了。当一个元素有多个样式的时候,样式优先级的顺序是:

内联样式 > ID选择器 > 类选择器 > 标签选择器 > 通用选择器 > 继承样式 > 浏览器默认样式

还有一套计算优先级的方法,浏览器对每个css样式都有一个权重值,需要确定优先级时,直接用公司计算整条选择器的权重作为该样式的优先级:

  • 内联样式权重值 1000
  • id权重值100
  • 类选择器、属性选择器和伪类选择器里样式的权重是10
  • 标签选择器里样式的权重是1
  • 通用选择器直接忽略

布局(layout)

渲染完成后,计算渲染树上的每个节点后,技能计算出每个元素所占空间的大小和位置。这个过程就是布局。

绘制(paint)

布局之后,每个元素的大小位置就有了,经过最后绘制这一步,就可以把样式绘制在屏幕上,在绘制过程中,浏览器会调用图像处理器,逐层逐块的把所有计算好位置和样式的元素都绘制出来。 ###重排(reflow)和重绘(repaint) 渲染树是动态构建的,dom节点和css节点的改动,都可能造成渲染树的重建,渲染树的改动就会造成重排重绘,下面我们介绍这两个概念,以及他们在什么情况下出发:

1、重排

当我们在dom中新增和删除了元素,或者是改变了某些元素的大小和位置和布局,在这个时候渲染树里,这个有改动的节点和它影响到的节点,都要重新计算,在改变发生时,要重新经历dom的改动,cssdom的构建,渲染树的构建、布局和绘制整个流程,这个过程就叫做 "重排",也叫做 "回流"。

2、重绘

重绘是我们改变元素的字体颜色和背景色的时候,并不会改变它的大小和位置,也不会影响到其他元素的布局,浏览器会对直接对元素的样式重新绘制,这个过程就叫重绘。

知识拓展

如何减少重排重绘 可以通过这几种方式进行优化

  • 不要逐项更改样式可以把需要的样式逐项手机起来,用一次操作进行修改
  • 用class的变动替代直接样式修改
  • 不要循环操作dom,循环的结果也要收集起来,最后用一次操作来完成
  • 需要频繁改动的元素(比如动画)尽量使用绝对定位,脱离文档流的元素会减少对后面元素的影响
  • 在条件允许的情况下,尽量使用css3动画,它可以调动gpu执行渲染