...

【JavaScript】浏览器的解析过程

解析过程

这里省略了浏览器从输入 URL 到拿到 DNS,然后打开网页的过程。

相当于直接就从服务器请求了一个index.html

1. 先写一个导入的 html 看看

<!DOCTYPE html>  
<html lang="en">  
  <head>  
    <meta charset="UTF-8" />  
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />  
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />  
    <title>Document</title>  
    <link rel="stylesheet" href="style.css" />  
    <!-- 下载的过程 不会阻碍html本身一行行的解析  -->  
  </head>  
  <body>  
    <script></script>  
    <h1>hello javascript</h1>  
  </body>  
</html>  

<!--  

1 首先像服务器请求,请求过来的是一份index.html,记住,此时只有一个html文件  
2 然后浏览器index.html从上到下一行行解析,看到了link css文件  
3 此时会下载css文件,但不会阻止浏览器继续解析html,css也只是下载而已  
4 如果此时遇到了script标签 那么就会阻塞html,  
 -->  

image-20220826145349658

2. 整体流程

  • 下载单个 html
  • 逐行解析
  • 遇到 link 里的 css 之后另起一个线程下载 + 解析
  • 遇到 script 标签直接阻塞,直到 js 下载解析完才行
  • 构建 DOM Tree
  • css 解析完成之后 构建 CSSOM Tree
  • DOM Tree + CSSDOM Tree = Render Tree 此时有了这个 Render Tree。这个时候信息是整体很全的(包裹节点以及样式,但没节点的尺寸和位置信息)。还有由于一些display:none等等。此时是不会显示页面上的
  • Layout 闪亮登场,来计算一下位置和尺寸信息,layout 里面包含很多位置信息,Render Tree 只有节点和样式而已。
  • Layout + Render Tree = Painting 了
  • 最后 Display(Painting 绘制到像素点之上,就会 display)

image-20220826151314549

这里有几个难点

Q:就是 Render Tree 最后是不是就是显示在页面上的样子?

A:当然不是了。因为还有 Layout,需要对一些位置和大小信息进行计算,还有一些不需要显示在页面上的,比如display:none进行计算。

Q:JS 和 CSS 标签会阻碍 DOM 渲染吗?

CSS 并不会组合 DOM Tree 渲染,但是 JS 会。CSS 会组合 Render Tree 渲染,因为 Render Tree 就是 CSSOM+DOM 的合体。

3. 回流(reflow)

为什么会有回流呢?

比如你 JS 操作 dom 了,这一下 DOM Tree 都少了,接下来肯定必须重新计算以后的步骤了。位置也要变。

修改个颜色 color 这样的就不是 reflow,因为位置大小都没变。

image-20220826145349658

<body>  
  <h1>hello javascript</h1>  
  <script>  
    var el = document.querySelector('h1');  
    el.addEventListener('click', () => {  
      el.remove();  
    });  
  </script>  
</body>  

第一次生成页面就是叫 layout 布局

第二次之后都要 reflow 了。

4. 重绘(repaint)

这个其实很好理解,直接和 reflow 对比来看就可以了。

image-20220826154248659

⚠️ 回流一定会触发重绘,而重绘不一定会回流

这肯定的,reflow 发生在位置有变化,位置都变了那么肯定 repaint 了。

但是 repain 有可能只是改个颜色,跟你位置没关系。

5. 合成(composite)

这个其实就类似于 ps 那种一张图片有很多图层 layer,html 显示其实也有的。

我们看到的页面其实是由于多重 layer 才显示出来的。

  • 标准流是一个图层

Q:新的 layer 如何创建呢?

以下几个属性可以生成新的 layer

Q:那么如何验证呢?

在浏览器的工具类

image-20220826154602186

写一个验证一下多重 layer

<!DOCTYPE html>  
<html lang="en">  
  <head>  
    <meta charset="UTF-8" />  
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />  
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />  
    <title>Document</title>  
    <style>  
      .box {  
        width: 200px;  
        height: 200px;  
        background-color: gold;  
      }  
      .h2 {  
        /* fixed会生成新的图层,absolute不会 */  
        background-color: pink;  
        position: fixed;  
      }  
    </style>  
  </head>  

  <body>  
    <div class="box"></div>  
    <div class="h2">h2</div>  
  </body>  
</html>  

image-20220826155022764

那么如何优化呢?

多了一层 layer 会在另一层,这样就不会影响标准流的那一层的位置等等信息,性能上可能会好一点,但也不是什么都要新建一层,因为内存和浏览器还需要点性能。还是要看情况的。

共有评论(0)

登陆即可评论哦