html页面加载js、css、页面内容时的影响与关系

前言

估计大家都听过,尽量将 CSS 放头部,JS 放底部,这样可以提高页面的性能。然而,为什么呢?大家有考虑过么?很长一段时间,我问过不少团队里前端的开发人员,但实际得到的解释一塌糊涂,这里总结一下。

总结

  • CSS 不会阻塞 DOM 的解析,但会阻塞 DOM 渲染。
  • JS 阻塞 DOM 解析,但浏览器会"偷看"DOM,预先下载相关资源。
  • 浏览器遇到<script>且没有 defer 或 async 属性的 标签时,会触发页面渲染,因而如果前面 CSS 资源尚未加载完毕时,浏览器会等待它加载完毕在执行脚本。

所以,你现在明白为何<script>最好放底部,<link>最好放头部,如果头部同时有<script><link>的情况下,最好将

测试

针对上述总结,下面将做一段测试,不想看直接看总结。

环境

准备的原文代码如下,我们给它加了一个样式,背景颜色为绿色。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        div {
        	width: 200px;
        	height: 200px;
            background: lightgreen; /*绿色背景*/
        }
    </style>
</head>
<body>
    <div></div>
</body>
</html>

准备的css代码如下,命名=test.css,将div的背景色改为红色。

div {
  background: red; /*红色背景*/
}

准备的js代码如下,命名=test.js,将输出div内容到浏览器。

const div = document.querySelecot('div');
console.log(div);

为了方便测试,还准备了一个函数,进行延迟加载上述的 js、css等内容,下面我们给只要添加sleep的元素都添加3秒的延迟操作,便于查看对应的效果。

function sleep(time) {
  return new Promise(function(res) {
    setTimeout(() => {
      res()
    }, time);
  })
}
效果1

1、在<head>中插入test.js文件;
2、将添加了sleep方法延迟3秒的css文件test.css加入到html中的任意位置;
3、打开浏览器,可以看到是首先打印出 div 这个 DOM 节点,过 3s 左右之后才渲染出一个浅蓝色的 div。这就证明了 CSS 是不会阻塞 DOM 的解析的,尽管 CSS 下载需要 3s,但这个过程中,浏览器不会傻等着 CSS 下载完,而是会解析 DOM 的。

效果2

1、在<head>中按顺序分别添加 css、js文件,css文件延迟3秒,效果如下

<header>
    <link rel="stylesheet" href="/css/sleep3000-test.css">
    <script src="/js/test.js"></script>
</header>

2、答案是浏览器会转圈圈三秒,但此过程中不会打印任何东西,之后呈现出一个浅蓝色的 div,再打印出 null;

答案是浏览器会转圈圈三秒,但此过程中不会打印任何东西,之后呈现出一个浅蓝色的 div,再打印出 null。结果好像是 CSS 不单阻塞了页面渲染,还阻塞了 DOM 的解析啊!稍等,在你打算掀桌子疯狂吐槽我之前,请先思考一下是什么阻塞了 DOM 的解析,刚才已经证明了 CSS 是不会阻塞的,那么阻塞了页面解析其实是 JS!但明明 JS 的代码如此简单,肯定不会阻塞这么久,那就是 JS 在等待 CSS 的下载,这是为什么呢?

仔细思考一下,其实这样做是有道理的,如果脚本的内容是获取元素的样式,宽高等 CSS 控制的属性,浏览器是需要计算的,也就是依赖于 CSS。浏览器也无法感知脚本内容到底是什么,为避免样式获取,因而只好等前面所有的样式下载完后,再执行 JS。因而造成了之前例子的情况。

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值