1 浏览器前端渲染原理
2 html 和document区别
DOMContentLoaded与load的区别
1浏览器发送http请求,服务器返回html文档文件(一般是index.html文件)。
2浏览器将从服务器获取的html文档解析成DOM树。
3同时浏览器也会加载所需的css文件,并且将相应的css解析成 CSSOM(层叠样式标模型)
4将DOM树和CSSOM结合,创建渲染树(rending tree)。(此处会存在加载css,js文件阻塞狗构建渲染树问题)
5计算元素处于网页中的哪个位置,布局渲染树
6 绘制出我们看到的网页
上次6个过程中,中间会有哪些问题出现?
css阻塞:
js阻塞:
怎样解决js阻塞的问题
缓存不常更新的文件,比如(jquery文件)
2浏览器将从服务器获取的html文档解析成DOM树。
4将DOM树和CSSOM结合,创建渲染树(rending tree)。(此处会存在加载css,js文件阻塞狗构建渲染树问题)
css阻塞:
css加载**不会**阻塞DOM树的**解析**
css加载**会阻塞**DOM树的渲染
css加载会阻塞后面js语句的执行(**因为js语句可能会操作到dom元素,比如dom元素的位置计算,css设置display:none,会影响dom元素的位置**)
js阻塞 :
js会阻塞DOM解析,也就阻塞了dom树的形成,没有dom树,浏览器就无法渲染,所以当加载很大的js文件时,可以看到页面很长时间是一片空白。
原因:因为加载的js中可能会创建,删除节点,这些操作会对dom树产生影响,如果不阻塞,等浏览器解析完标签生成dom树后,js修改了某些节点,那么浏览器又得重新解析,然后生成dom树,性能比较差。
所以:怎样解决js阻塞的问题?
1 JavaScript 尽可能的放在标签底部。不要放在head标签中。
2按需加载(动态创建script标签)js,当需要使用到该js文件时,才去加载js文件
3 使用async和defer。
如果标签设置了 defer属性,则浏览器会异步的下载该文件并且不会影响到后续DOM的渲染;
如果有多个设置了defer的script标签存在,则会按照顺序执行所有的script;
defer脚本会在文档渲染完毕后,DOMContentLoaded事件调用前执行。
如果设置了async属性,会使得script脚本异步的加载并在允许的情况下执行
async的执行,并不会按着script在页面中的顺序来执行,而是谁先加载完谁执行。
推荐使用defer和async的场景(https://www.cnblogs.com/jiasm/p/7683930.html)
defer: 1 评论框
2 代码语法高亮
3 polyfill.js
async: 如果你的脚本并不关系页面中的DOM元素(文档是否解析完毕)。并且也不会产生其他脚本需要的数据。
例如: 百度统计
如果不太能确定的话,用defer总是会比async稳定。。
DOMContentLoaded顾名思义,就是dom内容加载完毕。那什么是dom内容加载完毕呢?我们从打开一个网页说起。当输入一个URL,页面的展示首先是空白的,然后过一会,页面会展示出内容,但是页面的有些资源比如说图片资源还无法看到,此时页面是可以正常的交互,过一段时间后,图片才完成显示在页面。从页面空白到展示出页面内容,会触发DOMContentLoaded事件。而这段时间就是HTML文档被加载和解析完成。
这时候问题又来了,什么是HTML文档被加载和解析完成。要解决这个问题,我们就必须了解浏览器渲染原理。
当我们在浏览器地址输入URL时,浏览器会发送请求到服务器,服务器将请求的HTML文档发送回浏览器,浏览器将文档下载下来后,便开始从上到下解析,解析完成之后,会生成DOM。如果页面中有css,会根据css的内容形成CSSOM,然后DOM和CSSOM会生成一个渲染树,最后浏览器会根据渲染树的内容计算出各个节点在页面中的确切大小和位置,并将其绘制在浏览器上。