请说明 DOMContentLoaded, load, beforeunload, unload 的触发时机

2022年1月15日

💎 加入 E+ 成長計畫 與超過 350+ 位軟體工程師一同在社群中成長,並且獲得更多的軟體工程學習資源

我们都知道,网页是浏览器载入、解析 HTML 而生。浏览器在解析完 HTML 后会建构出我们熟悉的 DOM 树,而透过 DOM 树,开发者就能容易地透过 JavaScript 去操作 DOM 节点,让网页不只是能看,而是能够互动。而网页与 DOM 也有我们熟知的生命周期,例如很常听到的 DOMContentLoaded ,以及面试中常会被问到的「DOMContentLoadedload 事件有什么不同?」

这篇文会以第一人称的形式,来模拟回答 DOM 生命周期常见的问题。我们就先从「DOMContentLoadedload 事件有什么不同?」这题开始吧!

DOMContentLoadedload 事件有什么不同?

DOMContentLoaded 是当 DOM 建构完成后会触发的事件,因此只要当 HTML 文件完全载入、解析完后就会出发。这个时候 CSS 的样式表、图片等可能还没完全载入。因为很多 JavaScript 脚本,需要等到 DOM 节点被完整建立出来后,才能够使用,不然没有 DOM 节点,就没办法去做操作;所以 DOMContentLoaded 可以帮助开发者侦测什么时候可以执行这些 JavaScript 脚本。

load (window.onload) 这个事件,则是在 HTML 文件完全载入、解析,以及 CSS 样式表、图片等各类资源都载入好后,才会被触发。所以可以理解成网页完整载入,才会触发 load 事件。也因此,load 会是在 DOMContentLoaded 之后被触发。如果 JavaScript 的逻辑会去改动到样式、图片等,就会更适合用 load 而非 DOMContentLoaded 帮助我们侦测。

我们也可以从另一个角度理解 DOMContentLoadedload 事件的不同。在document 物件有个readyState 的属性(详见此),它有三个值一个是loading 这代表 HTML 文件正在被解析中;第二个是interactive 这代表 HTML 文件已经完成读取和解析,而 DOMContentLoaded 已经被触发,所以已经可以有互动了;最后则是complete ,当进到这状态时,就会触发load 事件。

beforeunloadunload 的触发时机与作用分别为何?

DOMContentLoadedload 事件是在侦测 DOM 与网页的建置完成,是在生命周期的开始;而beforeunloadunload 则是在侦测声明周期的结尾,意即在网页要被关闭时触发。

beforeunload (window.onbeforeunload) 是在使用者要离开网页前会被触发,例如要去别页、关闭分页等等的状况时,会触发这个事件。它的用途是可以让开发者在使用者要离开前,能够做点什么。常见的使用情境,是使用者要离开网页前,会跳出一个弹跳视窗,询问使用者是不是真的要离开或关闭网页,这就是透过 beforeunload 的事件触发,来得知应该要跳出这个视窗。

至于 unload (window.onunload) 则是在离开或关闭网页后,才会被触发;所以它的触发时机是在 beforeunload 之后。如果我们要有弹跳视窗,不能用 unload 因为会太晚,我们会需要 beforeunload。而 unload 的用途通常会是用来埋资料分析,因为是在使用者离开网页时触发,我们就可以得知使用者确切是在什么时机离开了网页。

🧵 如果你想收到最即時的內容更新,可以在 FacebookInstagram 上追蹤我們