请说明 DOMContentLoaded, load, beforeunload, unload 的触发时机
2024年7月15日
我们都知道,网页是浏览器载入、解析 HTML 而生。 浏览器在解析完 HTML 后会建构出我们熟悉的 DOM 树,而透过 DOM 树,开发者就能容易地透过 JavaScript 去操作 DOM 节点,让网页不只是能看,而是能够互动。而网页与 DOM 也有我们熟知的生命周期,例如很常听到的 DOMContentLoaded
,以及面试中常会被问到的“DOMContentLoaded
与 load
事件有什么不同?”
这篇文会以第一人称的形式,来模拟回答 DOM 生命周期常见的问题。我们就先从“DOMContentLoaded
与 load
事件有什么不同?”这题开始吧!
DOMContentLoaded
与 load
事件有什么不同?
DOMContentLoaded
是当 DOM 建构完成后会触发的事件,因此只要当 HTML 文件完全载入、解析完后就会出发。这个时候 CSS 的样式表、图片等可能还没完全载入。因为很多 JavaScript 脚本,需要等到 DOM 节点被完整建立出来后,才能够使用,不然没有 DOM 节点,就没办法去做操作;所以 DOMContentLoaded
可以帮助开发者侦测什么时候可以执行这些 JavaScript 脚本。
load
(window.onload
) 这个事件,则是在 HTML 文件完全载入、解析,以及 CSS 样式表、图片等各类资源都载入好后,才会被触发。所以可以理解成网页完整载入,才会触发 load
事件。也因此,load
会是在 DOMContentLoaded
之后被触发。如果 JavaScript 的逻辑会去改动到样式、图片等,就会更适合用 load
而非 DOMContentLoaded
帮助我们侦测。
我们也可以从另一个角度理解 DOMContentLoaded
与 load
事件的不同。在 document
物件有个 readyState
的属性 详见此 MDN,它有三个值一个是 loading
这代表 HTML 文件正在被解析中;第二个是 interactive
这代表 HTML 文件已经完成读取和解析,而 DOMContentLoaded 已经被触发,所以已经可以有互动了;最后则是 complete
,当进到这状态时,就会触发 load
事件。
beforeunload
与 unload
的触发时机与作用分别为何?
DOMContentLoaded
与 load
事件是在侦测 DOM 与网页的建置完成,是在生命周期的开始;而 beforeunload
与 unload
则是在侦测声明周期的结尾,意即在网页要被关闭时触发。
beforeunload
(window.onbeforeunload
) 是在使用者要离开网页前会被触发,例如要去别页、关闭分页等等的状况时,会触发这个事件。它的用途是可以让开发者在使用者要离开前,能够做点什么。常见的使用情境,是使用者要离开网页前,会跳出一个弹跳视窗,询问使用者是不是真的要离开或关闭网页,这就是透过 beforeunload
的事件触发,来得知应该要跳出这个视窗。
至于 unload
(window.onunload
) 则是在离开或关闭网页后,才会被触发;所以它的触发时机是在 beforeunload
之后。如果我们要有弹跳视窗,不能用 unload
因为会太晚,我们会需要 beforeunload
。而 unload
的用途通常会是用来埋资料分析,因为是在使用者离开网页时触发,我们就可以得知使用者确切是在什么时机离开了网页。