将欲取之,必先与之,是谓微明。柔弱胜刚强。——老子
引子
我们在看一些前端优化规则的时候,比如雅虎军规等等,都有看到 style 写在 head 中
,但是外链 script 写在 body
的最后,以优化性能,都知道应该怎么做,但是不知道其中的原理。
如果还不知道浏览器渲染的原理的,看一看浏览器渲染原理这一篇文章。其实这个就是考验大家对 html 中的 css、javascript、dom
之间的解析和相互阻塞关系。
JavaScript 会阻塞 CSS、DOM 吗
提出自己观点
当我们把 script 标签写到页面的顶部时,dom 树在解析的时候检测到 script 标签是,会加载 script 里面的内容并且执行。我们假设在执行
javascript 会阻塞 dom
的解析和渲染,阻塞 css
的解析和加载。
验证自己的观点
在验证之前我们先把 chrome 的网速调到 40kb 每秒的下载和上传数据
第一步
第二步
我们来验证这个结论:
html 代码如下
1 | <!DOCTYPE html> |
在加载到
jquery 文件后,会先下载远程的 jquery 并且执行
他,他会阻塞 dom 的解析和渲染
,css 解析和渲染
,一直是白屏,等 jquery执行完成
了才接着解析 Dom 和 cssom 并且渲染,console.log 打印 h1 标签也是空数组。
如下图所示:
总结
javascript 加载会阻塞 css 解析和渲染
javascript 加载会阻塞 dom 解析和渲染
css 加载会阻塞 JavaScript 的加载和执行、会阻塞 Dom 的解析和渲染?
提出自己观点
因为上面我们已经验证过 JavaScript 会阻塞 Dom 的解析和渲染,同时也会解析 cssom 的解析和渲染,所以我们假设 css 的加载会阻塞
Dom 的解析
和渲染
,会阻塞
JavaScript 的加载
和执行
。
验证我们的假设
在上面的代码基础上修改代码如下:
1 | <!DOCTYPE html> |
执行结果如下图所示
css 加载对 Dom 的阻塞
如果按我们假设的 css 加载会阻塞 Dom 的解析和渲染
,那么执行的结果,应该是首先是白屏
,然后 h1 标签的 nodeList
应该是为空数组
的,但是在执行的时我们看到 h1 标签的 nodeList 是有值的
,注(还有 setTimeout 的作用是为了在下一个 Task 最先执行,感觉并不会影响我们的实验的结果
。)
这表示我们一开始的假设是有问题的,css 加载会阻塞 Dom 的渲染有阻塞,但是并不会阻塞 Dom 的解析
。
css 加载对 JavaScript 的阻塞
css 加载会对后续的 JavaScript 的执行会造成阻塞。
总结
css 加载对 Dom 的解析没有阻塞,但是对于 Dom 的渲染造成了阻塞。
css 加载对 JavaScript 的执行会造成阻塞
总结
如果还不了解整体的渲染流程可以看以前我前面的文章,浏览器渲染原理 (一)在网址中输入一个网站后面都做了什么
**_JavaScript 的加载会阻塞 Dom 的解析和渲染,并且也会阻塞 css 的解析和渲染。_**
**_Css 的加载会阻塞 Dom 的渲染,并不会阻塞 Dom 的解析,也会阻塞 JavaScript 的执行。_**