假设游览器已经获取到了html文件。
一、基本流程
解析html以构建dom树 ->
构建render树 ->
布局render树 ->
绘制render树
所以,浏览器会解析三个东西:
(1) HTML/SVG/XHTML
,解析这三种文件会产生一个 DOM Tree
。
(2) CSS
,解析 CSS
会产生 CSS
规则树。
(3) js脚本,主要是通过 DOM API 和 CSSOM API 来操作 DOM Tree 和 CSS Rule Tree.
二、渲染过程
当浏览器获得一个html文件时,会“自上而下”加载,并在加载过程中进行解析渲染
解析:
浏览器会将
HTML
解析成一个DOM
树,DOM
树的构建过程是一个深度遍历过程:当前节点的所有子节点都构建好后才会去构建当前节点的下一个兄弟节点。
将
CSS
解析成CSS Rule Tree
。
根据
DOM
树和CSSOM
来构造Rendering Tree
。注意:Rendering Tree
渲染树并不等同于 DOM 树,因为一些像Header
或display:none
的东西就没必要放在渲染树中了。
有了Render Tree,浏览器已经能知道网页中有哪些节点、各个节点的CSS定义以及他们的从属关系。下一步操作称之为Layout,顾名思义就是计算出每个节点在屏幕中的位置。
再下一步就是绘制,即遍历render树,并使用UI后端层绘制每个节点。
image
重点:上述这个过程是逐步完成的,为了更好的用户体验,渲染引擎将会尽可能早的将内容呈现到屏幕上,并不会等到所有的html都解析完成之后再去构建和布局render树。它是解析完一部分内容就显示一部分内容,同时,可能还在通过网络下载其余内容。
三、渲染过程的概念
Reflow(回流):浏览器要花时间去渲染,当它发现了某个部分发生了变化影响了布局,那就需要倒回去重新渲染。
Repaint(重绘):如果只是改变了某个元素的背景颜色,文字颜色等,不影响元素周围或内部布局的属性,将只会引起浏览器的repaint,重画某一部分。
Reflow要比Repaint更花费时间,也就更影响性能。要尽量避免过多的Reflow。
reflow的原因:
页面初始化的时候;
操作DOM时;
某些元素的尺寸变了;
如果 CSS 的布局属性发生变化了。
所以再优化页面渲染性能的时候,减少 reflow/repaint就是基本出发点
js的加载和执行的特点:
载入后马上执行;
执行时会阻塞页面后续的内容(包括页面的渲染、其它资源的下载)。原因:因为浏览器需要一个稳定的DOM树结构,而JS中很有可能有 代码直接改变了DOM树结构,比如使用 document.write 或 appendChild,甚至是直接使用的location.href进行跳转,浏览器为了防止出现JS修 改DOM树,需要重新构建DOM树的情况,所以 就会阻塞其他的下载和呈现;
作者:EdmundChen
链接:https://www.jianshu.com/p/fd3493345f8f