渲染引擎 & 页面渲染流程 & 阻塞
文檔對象模型(Document Object Model,簡稱DOM)
瀏覽器渲染引擎
一個渲染引擎 主要模塊:
HTML 解析器
解釋 HTML 文檔的解析器,將 HTML 文本 解析成 DOM 樹
css 解析器
級聯樣式的解析器,為 DOM 中的各個元素計算出樣式信息,為布局提高基礎設施
javascript 引擎
使用 Javascript 代碼可以修改網頁的內容,也能修改 css 的信息
javascript 引擎能夠解釋 javascript 代碼,并通過 DOM 接口和 CSSOM 接口來修改網頁內容和樣式信息,從而改變渲染的結果。
layout 布局模塊
在 DOM 創建之后,Webkit 需要將其中的元素對象同樣式信息結合起來,
計算他們的大小位置等布局信息,形成一個能表達這所有信息的內部表示模型
繪圖模塊
使用 圖形庫 將布局計算后的各個網頁的節點 繪制成 圖像結果
瀏覽器渲染頁面的整個過程,瀏覽器會從上至下解析文檔:
以上這些模塊依賴很多其他的基礎模塊,包括要使用到網絡 存儲 2D/3D圖像 音頻視頻解碼器 和 圖片解碼器。
所以渲染引擎中還會包括如何使用這些依賴模塊的部分。
1. 遇見HTML 標記
調用 HTML 解析器解析為對應的 token (一個 token 就是一個標簽文本的序列化)
并構建 DOM 樹(就是一塊內存,保存著 tokens,建立它們之間的關系)
2.遇見 style/link 標記 調用 css 解析器 處理 CSS 標記并構建 內部表示結構 CSSOM 樹
CSS 解析器工作完成之后,在 DOM 樹上附加解釋后的樣式信息,這就是 RenderObject 樹
RenderObject 在創建的同時,Webkit 會根據網頁的結構創建 RenderLayer,同時構建一個繪圖上下文
根據 繪圖上下文 生成最終的圖像(這一過程需要依賴圖形庫)
3.遇見 script 標記 調用 javascript 解析器 處理 script 標記,綁定事件、修改 DOM 樹 / CSSOM樹 等
4.將 DOM 樹 與 CSSOM 樹 再次合并成一個渲染樹 Render 樹
5.根據 渲染樹 來布局,以計算每個節點的幾何信息____重排
6.將各個節點繪制到屏幕上____重繪
上面介紹的是一個完整的渲染過程
但現代網頁很多都是動態的,這意味著在渲染完成之后,
由于網頁的動畫或者用戶的交互,瀏覽器其實一直在不停地重復執行渲染過程。(重繪重排)
以上的數字表示的是基本順序,這不是嚴格一致的,這個過程可能重復也可能交叉
網頁在加載和渲染過程會觸發 "DOMContentLoaded" 和 "load" 事件
----> 分別在 DOM 樹解析完成后,觸發 "DOMContentLoaded"
----> DOM 樹構建并且網頁所有依賴資源都加載完成之后發生,觸發 "load"
實際測試
瀏覽器加載資源是異步的
用 <style> 內部樣式表 寫 css,是由 Parse HTML 異步解析的。
一張圖片分多次解析,其中 Parse HTML 這么快,體現了其異步執行,只是開啟了一個任務,讓它自己去請求資源并解析
css 阻塞 ---- 樣式寫在外部文件,在 index.css 中 link 導入
通過 link 進來的樣式 是同步解析的,由 Parse Stylesheet 進行解析
正因為是同步解析,所以 css 解析器 會阻塞頁面的渲染,從而避免了閃屏
這也是為什么推薦使用 <style link='index.css'> 引入外部樣式表
阻塞
css 阻塞
<style> 標簽中的樣式
1. 由 html 解析器進行解析
2. 不阻塞瀏覽器渲染
3. 不阻塞 DOM 解析
<link src='index.css'>引入的外部 css 樣式 (推薦使用 <link> 方式引入外部 css,可以避免閃屏現象)
1. 由 CSS 解析器進行解析
2. 會阻塞瀏覽器頁面渲染(原因:避免閃屏)
<link rel="stylesheet" href="css/my-sleep-3000-commen.css" />
3. 不阻塞 DOM 結構的解析
因為 DOM 解析 和 CSS 解析是兩個并行的進程
瀏覽器解析 DOM 生成 DOM Tree,解析 CSS 生成 CSS Tree
最終組成 render Tree,再渲染頁面,DOM 的解析,和 CSS的解析并行的。
4. 會阻塞 js 的執行(但不會阻塞 js 等資源的加載)
腳本在文檔解析階段會請求樣式信息,如果 css 還沒有完全加載解析完,腳本可能獲得錯誤的回復
FireFox 會在樣式表加載解析過程中,禁止所有腳本
對于 WebKit 而言,僅當腳本嘗試訪問樣式屬性可能會得到錯誤的回復時,禁止腳本的執行
優化方案: (盡可能快的提高 css 加載速度)
使用 CDN 加速
對 css 進行壓縮(用打包工具,比如 webpack, gulp 等,也可以通過開啟 gzip 壓縮)
減少 http 請求數,將多個 css 文件合并
js 阻塞
會阻塞 DOM 解析
因為 js 可能會修改 DOM 樹
會阻塞 頁面的渲染
因為 js 代碼可能會修改 DOM 樹 / CSSOM 樹 的結構
js 會順序執行,阻塞后續 js 邏輯的執行 (不阻塞 js 等其他資源的加載)
維護依賴關系
css 的解析 和 js 的執行 是互斥的 ( css 解析的時候 js 停止執行,js 執行的時候 css 停止解析)
預解析
WebKit 和 FireFox 都進行了這項優化。
在執行 js 腳本時,其他線程會解析文檔的其余部分 (只是檢查,不影響原結構),找出并加載需要網絡加載的其他資源
使得這些資源在并行連接上加載,從而提高總體速度
預解析器 不會修改 DOM 樹,而是將這件事交給 主解析器 處理
預解析器 只會解析外部資源的引用(例如外部腳本、樣式、圖片)
提前發送請求,提前解析外部資源內容
--------小尾巴
________一個人欣賞-最后一朵顏色的消逝-忠誠于我的是·一顆叫做野的心.決不受人奴役.怒火中生的那一刻·終將結束...
總結
以上是生活随笔為你收集整理的渲染引擎 & 页面渲染流程 & 阻塞的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 为什么北鼎的养生壶贵?
- 下一篇: 雅迪电动车24安锂电池,跑了两年后还能跑