浏览器渲染浅析
1.浏览器渲染主要流程
不同的浏览器内核不同,所以不同浏览器的渲染过程也不太一样。
这里我们看下WebKit 的渲染主要流程:
webkit.png
网页的生成过程,大致可以分成五步。
(1)HTML代码转化成DOM Tree
HTML Parser的任务是将HTML文档解析成DOM Tree
(2)CSS代码转化成CSSOM
CSS Parser将CSS解析成Style Rules,Style Rules也叫CSSOM(CSS Object Model)
(3)结合DOM和CSSOM,生成一棵渲染树(包含每个节点的视觉信息)
主要包含两步:样式计算和以正确的层叠顺序应用规则
(4)创建渲染树后,下一步就是布局(Layout),即将所有渲染树的所有节点进行平面合成
创建渲染树后,下一步就是布局(Layout),这个过程就是通过渲染树中渲染对象的信息,计算出每一个渲染对象的位置和尺寸,将其安置在浏览器窗口的正确位置,而有些时候我们会在文档布局完成后对DOM进行修改,这时候可能需要重新进行布局,也可称其为回流,本质上还是一个布局的过程,每一个渲染对象都有一个布局或者回流方法,实现其布局或回流。
对渲染树的布局可以分为全局和局部的,全局即对整个渲染树进行重新布局,如当我们改变了窗口尺寸或方向或者是修改了根元素的尺寸或者字体大小等;而局部布局可以是对渲染树的某部分或某一个渲染对象进行重新布局。
(5)将布局绘制(paint)在屏幕上
在绘制阶段,系统会遍历呈现树,并调用呈现器的“paint”方法,将呈现器的内容显示在屏幕上。绘制工作是使用用户界面基础组件完成的
"生成布局"(flow)和"绘制"(paint)这两步,合称为"渲染"(render)。
2.重绘/重排/回流
3.脚本处理(js阻塞dom解析)
浏览器解析文档,当遇到<script>标签
的时候,会立即解析脚本,停止解析文档(因为JS可能会改动DOM和CSS,所以继续解析会造成浪费)。
如果脚本是外部的,会等待脚本下载完毕,再继续解析文档。现在可以在script标签上增加属性 defer或者async,保证不阻塞dom解析
脚本解析会将脚本中改变DOM和CSS的地方分别解析出来,追加到DOM Tree和Style Rules上。
4.CSS处理
CSS不会影响Dom解析,但是会影响渲染
CSS的加载会阻塞后面JS的执行
5.页面渲染优化
在改变文档根元素的字体颜色等视觉性信息时,会触发整个文档的重绘,而改变某元素的字体颜色则只触发特定元素的重绘;改变元素的位置信息会同时触发此元素(可能还包括其兄弟元素或子级元素)的布局和重绘。某些重大改变,如更改文档根元素的字体尺寸,则会触发整个文档的重新布局和重绘,据此及上文所述,推荐以下优化和实践:
(1)HTML文档结构层次尽量少,最好不深于六层;
(2)脚本尽量后放,放在前即可;
(3)少量首屏样式内联放在标签内;
(4)样式结构层次尽量简单;
(5)在脚本中尽量减少DOM操作,尽量缓存访问DOM的样式信息,避免过度触发回流;
(6)减少通过JavaScript代码修改元素样式,尽量使用修改class名方式操作样式或动画;
(7)动画尽量使用在绝对定位或固定定位的元素上;
(8)隐藏在屏幕外,或在页面滚动时,尽量停止动画;
(9)尽量缓存DOM查找,查找器尽量简洁;
(10)涉及多域名的网站,可以开启域名预解析