渲染机制
DOCTYPE的作用
- DTD(文档定义类型)是一系列的语法规则,用来定义XML或者(X)HTML的文件类型。浏览器会使用它来判断文档类型,决定用何种协议来解析,以及切换浏览器模式
- DOCTYPE是用来声明文档类型和DTD规范的,一个主要的用途是文件的合法性验证。如果文件代码不合法,那么解析的时候会出一些差错。
DOCTYPE类型
- HTML5 <!DOCTYPE html>
- HTML 4.01 Strict 严格模式 该DTD包含所有HTML元素和属性,但不包括展示性和弃用的元素
- HTML 4.01 Transitional 传统模式 该DTD包含所有HTML元素和属性,
包括展示性和弃用的元素 (比如font)
浏览器渲染过程
所以浏览器的渲染过程主要包括以下几步:
- 解析HTML生成DOM树。
- 解析CSS生成CSSOM规则树。
- 将DOM树与CSSOM规则树合并在一起生成渲染树。
- 遍历渲染树开始布局,计算每个节点的位置大小信息。
- 将渲染树每个节点绘制到屏幕。
渲染阻塞
当浏览器遇到一个 script 标记时,DOM 构建将暂停,直至脚本完成执行,然后继续构建DOM。每次去执行JavaScript脚本都会严重地阻塞DOM树的构建,如果JavaScript脚本还操作了CSSOM,而正好这个CSSOM还没有下载和构建,浏览器甚至会延迟脚本执行和构建DOM,直至完成其CSSOM的下载和构建。
所以,script 标签的位置很重要。实际使用时,可以遵循下面两个原则:
- CSS 优先:引入顺序上,CSS 资源先于 JavaScript 资源。
- JS置后:我们通常把JS代码放到页面底部,且JavaScript 应尽量少影响 DOM 的构建。
重排reflow
定义
DOM结构中的每个元素都有自己的盒模型,这些都需要浏览器根据各种样式来计算并根据结果将元素放到它该出现的位置,这个过程叫做reflow
触发reflow
- 当增加、删除、修改DOM节点的时候,会导致reflow或者repaint
- 当你移动DOM节点,或者搞动画的时候
- 当你修改CSS样式的时候
- 当你resize窗口的时候(移动端没有这个问题),或者滚动的时候
- 当你修改网页默认字体的时候(这个会出现各种问题)
- 如何触发reflow应该至少要记住以上两点以上
重绘repaint
定义
当各种盒子的位置、大小以及其他属性改动,例如字体大小颜色等都确定下来以后,浏览器就把这个元素按照各自的特性绘制了一遍,于是页面内容就出现了,这个过程叫做repaint
触发repaint
- DOM改动
- CSS改动
如何尽可能少的进行重绘
将DOM改动或者CSS改动尽可能的一次性改完,不要一次操作分多次进行
例子:
//多次重绘
dom1.style.backgroundColor = 'red'
dom1.style.width= '50px'
dom1.style.height= '50px'
//一次重绘
//CSS
.add{
backgound-color: red;
width: 50px;
heiht: 50px;
}
//JS
dom2.className = 'add'
JS运行机制
JS是单线程的,不可以同时执行多个任务,但是同时也有异步操作。JS会优先执行同步操作,然后同步操作都完成以后再去执行异步操作。
console.log(1)
setTimeout(function() {
console.log(3)
}, 0)
console.log(2)
//输出顺序为 1 2 3 因为setTimeout是一个异步函数
console.log(1)
setTimeout(function() {
console.log(2)
}, 0)
while (true) {
}
//只输出1然后进入无线循环不输出2
验证了所有同步操作完成之前异步操作是不会被执行的。
Event Loop
for(var i = 0;i < 4;i++) {
setTimeout(function() {
console.log(i)
},1000)
}
//输出四个4
上面这段代码同时输出4个4.因为在循环的过程中遇到setTimeout会记住这个函数,但是不会去执行他,然后进入下一轮循环,等到循环结束,setTimeout被放入异步队列执行。
异步任务
- setTimeout 和 setInterval
- DOM事件
- ES6中的promise
总结
- 了解JS的单线程的概念
- 理解任务队列
- 理解Event Loop
- 理解哪些语句会放入异步任务队列
- 理解语句放入异步队列的时机