码农之家

重绘重排理解与优化

浏览器加载网页时会生成DOM树和CSSOM树

重绘

当盒子的位置、大小以及其他属性,例如颜色、字体大小等都确定下来之后,浏览器便把这些原色都按照各自的特性绘制一遍,将内容呈现在页面上。重绘是指一个元素外观的改变所触发的浏览器行为,浏览器会根据元素的新属性重新绘制,使元素呈现新的外观。

触发重绘的条件:改变元素外观属性。如:color,background-color,font-size等。

重排(回流)

当渲染树中的一部分(或全部)因为元素的规模尺寸,布局,隐藏等改变而需要重新构建, 这就称为回流(reflow)。每个页面至少需要一次回流,就是在页面第一次加载的时候。

重绘和重排的关系:在回流的时候,浏览器会使渲染树中受到影响的部分失效,并重新构造这部分渲染树,完成回流后,浏览器会重新绘制受影响的部分到屏幕中,该过程称为重绘。

所以,重排必定会引发重绘,但重绘不一定会引发重排。

触发重排的条件:任何页面布局和几何属性的改变都会触发重排

比如:

触发重排的条件:改变元素的大小 位置 等如:width、height、pading、margin、position等, 添加删除DOM操作等

重绘重排的代价:耗时,导致浏览器卡慢。

优化

  1. 直接改变元素的className
  2. display:none;先设置元素为display:none;然后进行页面布局等操作;设置完成后将元素设置为display:block;这样的话就只引发两次重绘和重排;
  3. 不要经常访问浏览器的flush队列属性;如果一定要访问,可以利用缓存。将访问的值存储起来,接下来使用就不会再引发回流;
  4. 使用cloneNode(true or false) 和 replaceChild 技术,引发一次回流和重绘;
  5. 将需要多次重排的元素,position属性设为absolute或fixed,元素脱离了文档流,它的变化不会影响到其他元素;
  6. 如果需要创建多个DOM节点,可以使用DocumentFragment创建完后一次性的加入document;