当前位置: 首页 > Web前端 > HTML

页面重构和回流

时间:2023-04-02 16:34:00 HTML

在了解什么是重构和回流之前,我们应该先看看浏览器是如何渲染的?浏览器的渲染过程:1.处理HTML脚本,生成DOM树(DOM树包含所有HTML标签,包括display:none和js动态添加的元素等)2.处理CSS脚本,生成CSSOM树(DOM而CSSOM是一个独立的数据结构)3.将DOM树和CSSOM树合并成渲染树,渲染树不包含定位和几何信息。渲染树虽然和dom树很像,但是还是有区别的。渲染树不包含隐藏节点(如display:none节点和头节点),因为这些节点不会用于渲染,不会影响渲染,所以不会被包含在渲染树中。注意通过visibility:hidden隐藏的元素仍然会包含在rendertree中,因为visibility:hidden会影响布局和占用空间。4.布局渲染树中的内容,计算每个节点的几何外观5.将渲染树中的每个节点绘制到屏幕上。什么是重构和回流重构:当元素的某些属性发生变化时,这些属性只影响元素的外观和风格,不会改变元素的布局、大小,如颜色、背景等。此时触发的浏览器行为称为重构。回流:当元素的布局、大小和显示方式发生变化时,触发的浏览器行为称为回流。此外,每个页面都会在首次??加载时触发回流。注意:回流一定会引起重绘,重绘不一定伴随回流。同时,回流比重构对性能的影响更大。哪些操作会引起重绘和回流实际上,对rendertree中的元素进行任何操作都会引起回流或重绘,例如:添加、删除元素(回流+重绘)、隐藏元素、显示:无(回流+重绘)、可见性:hidden(只重绘,不重排)移动元素,比如改变top,left(jquery的animate方法是,改变top,left不一定影响重排),或者移动元素到另一个父元素。(Redrawing+reflow)对样式的操作(对不同属性的操作效果不同。例如元素尺寸变化——margins,padding,borders,widthandheight,content变化——比如计算值宽高变化导致的文本变化或者图片尺寸变化;)还有用户操作,比如改变Browsersize,改变浏览器的字体大小等(回流+重绘)浏览器对回流的优化因为回流是昂贵的,所以大部分浏览器都会优化回流,浏览器会维护一个队列。将所有会引起回流和重绘的操作放入这个队列中,当队列中的操作达到一定数量或达到一定时间间隔时,浏览器会刷新队列并进行批处理。这会将多次回流和重绘变成一次回流重绘。虽然有浏览器优化,但有些代码可能会强制浏览器提前刷新队列,因此浏览器优化可能不起作用。当你向浏览器请求一些样式信息时,浏览器会刷新队列,比如:offsetTop、offsetLeft、offsetWidth、offsetHeightscrollTop/Left/Width/HeightclientTop/Left/Width/Heightwidth、height请求getComputedStyle(),或者IE的currentStyle时你请求上面的一些属性,浏览器需要刷新队列才能给你最准确的值,因为队列中可能有影响这些值的操作。即使你获取的某个元素的布局和样式信息与最近发生或改变的布局信息无关,浏览器也会强行刷新渲染队列。如何减少回流和重绘根据上面触发回流和重绘的操作,我们可以知道,只要减少对渲染树的操作(合并多个DOM和样式修改),减少对一些样式信息的请求,我们可以减少Reflow、redraw,尽量利用好浏览器的优化策略。具体方法是:1.直接改className。如果样式是动态变化的,就用cssText(考虑浏览器没有优化)2.让要操作的元素“离线处理”,处理后一起更新:使用DocumentFragment进行缓存操作,造成回流和重绘;使用display:none技术,只造成两次回流和重绘;使用cloneNode(trueorfalse)和replaceChild技术,造成回流和重绘;3.不频繁访问会导致浏览器刷新队列的属性,如果真的要访问,使用缓存4.将元素从动画流中取出,减少回流的Render树的大小(即让文档流之外的动画元素,使用绝对定位等)。