回流与重绘
浏览器的渲染机制:
浏览器渲染页面一般分为五个步骤
1、处理HTML并构建DOM树
2、处理css构建CSSOM树
3、将DOM和CSSOM树合并成一个渲染树
4、根据渲染树来布局,计算每个节点的位置
5、调用GPU绘制,合并图层,显示在屏幕上
重绘:当我们对DOM的修改导致了样式的变化,却并未影响其几何属性(比如修改字体颜色、背景颜色等),浏览器不需重新计算元素的几何属性、直接为该元素绘制新的样式(跳过了上图所示的回流环节)。这个过程叫做重绘。
回流:当我们对 DOM 的修改引发了 DOM 几何尺寸的变化(比如修改元素的宽、高或隐藏元素等)时,浏览器需要重新计算元素的几何属性(其他元素的几何属性和位置也会因此受到影响),然后再将计算的结果绘制出来。这个过程就是回流(也叫重排)。
导致回流的几种情况:
1、页面初始化
2、浏览器窗口缩放
3、改变元素的边距、填充、宽、高、边框
4、offset、scroll、client等属性是由计算获得的,浏览器为了获取这些值也会回流
5、当我们调用了 getComputedStyle 方法,或者 IE 里的 currentStyle 时,也会触发回流。原理是一样的,都为求一个“即时性”和“准确性”。
涉及到的css属性有margin,padding,height,width,border,display,min-height,position,top,right,bottom,left,float,clear,line-height,text-align,overflow,overflow-y,font-weight,font-family,font-size,white-space等
导致重绘的情况
css 属性中,color 、border-style、border-radius、visibility、text-decoration、box-shadow、background、background-image、background-position、background-repeat、background-size、outline、outline-color等属性变更。
动动手
var s = document.body.style; s.padding = "2px"; // 回流+重绘 s.border = "1px solid red"; // 再一次 回流+重绘 s.color = "blue"; // 再一次重绘 s.backgroundColor = "#ccc"; // 再一次 重绘 s.fontSize = "14px"; // 再一次 回流+重绘 // 添加node,再一次 回流+重绘 document.body.appendChild(document.createTextNode('abc!'));
//requestAnimationFrame是什么呢? //他也是个计时器 //与setTimeout和setInterval不同, //requestAnimationFrame不需要设置时间间隔 //setTimeout和setInterval的问题是,它们都不精确。 //它们的内在运行机制决定了时间间隔参数实际上只是 //指定了把动画代码添加到浏览器UI线程队列中以等待执行的时间。 //如果队列前面已经加入了其他任务, //那动画代码就要等前面的任务完成后再执行 //requestAnimationFrame采用系统时间间隔, //保持最佳绘制效率,不会因为间隔时间过短,造成过度绘制,增加开销; //也不会因为间隔时间太长,使用动画卡顿不流畅, //让各种网页动画效果能够有一个统一的刷新机制, //从而节省系统资源,提高系统性能,改善视觉效果 //【1】requestAnimationFrame会把每一帧中的所有DOM操作集中起来, // 在一次重绘或回流中就完成, // 并且重绘或回流的时间间隔紧紧跟随浏览器的刷新频率 //【2】在隐藏或不可见的元素中,requestAnimationFrame将不会进行重绘或回流, // 这当然就意味着更少的CPU、GPU和内存使用量 //【3】requestAnimationFrame是由浏览器专门为动画提供的API, // 在运行时浏览器会自动优化方法的调用, // 并且如果页面不是激活状态下的话,动画会自动暂停, //有效节省了CPU开销 //控制台输出1和0 var timer = requestAnimationFrame(function(){ console.log(0); }); console.log(timer);//1 //控制台什么都不输出 var timer = requestAnimationFrame(function(){ console.log(0); }); cancelAnimationFrame(timer); //cancelAnimationFrame方法用于取消定时器
参考:
文献1:https://www.cnblogs.com/yangyangxxb/p/10081546.html
文献2:https://www.chaojimake.cn/questioninfo_188.html

浙公网安备 33010602011771号