一、重绘不一定需要重排,重排必然会导致重绘。
回流会导致渲染树需要重新计算,开销比重绘大,所以我们要尽量避免回流的产生
重排:当渲染树的一部分必须更新并且节点的尺寸发生了变化,浏览器会使渲染树中受到影响的部分失效,并重新构造渲染树。
- 页面第一次渲染 在页面发生首次渲染的时候,所有组件都要进行首次布局,这是开销最大的一次回流。
- 浏览器窗口尺寸改变
- 元素位置和尺寸发生改变的时候
- 新增和删除可见元素
- 内容发生改变(文字数量或图片大小等等)
- 元素字体大小变化。
- 激活CSS伪类(例如::hover)。
- 设置style属性
- 查询某些属性或调用某些方法。比如说:
- offsetTop、offsetLeft、 offsetWidth、offsetHeight、scrollTop、scrollLeft、scrollWidth、scrollHeight、clientTop、clientLeft、clientWidth、clientHeight
- 除此之外,当我们调用getComputedStyle方法,或者IE里的currentStyle时,也会触发回流,原理是一样的,都为求一个“即时性”和“准确性”。
重绘:是在一个元素的外观被改变所触发的浏览器行为,浏览器会根据元素的新属性重新绘制,使元素呈现新的外观。
- 当render tree中的一些元素需要更新属性,而这些属性只是影响元素的外观,风格,而不会影响布局的,比如
- visibility、outline、背景色,改变字体颜色等属性的改变。
下面的代码是影响回流和重绘的:
var s = ;
= "2px"; // 回流+重绘
= "1px solid red"; // 再一次 回流+重绘
= "blue"; // 重绘
= "#ccc"; // 重绘
= "14px"; // 再一次 回流+重绘
(('abc!'));// 添加node,再一次 回流+重绘
二、减少reflow、repaint
- 不要一条一条的修改DOM的样式,可以先定义好css的class,然后修改DOM的className。
- 不要把DOM结点的属性值放在一个循环里当成循环里的变量。
- 为动画的HTML元件适用fixed或absolute的position,那么修改他们的css是不会reflow