前端頁面生命週期

2022-03-02 11:21:47 字數 3559 閱讀 7152

對頁面宣告週期的總結與回憶。

下文均為個人測試得出的結論,如有不對望指出。

了解頁面宣告週期面前,需要了解幾個概念。

1.在頁面中dom載入與css載入是非同步的。但是呢,也不絕對,比如內聯css是同步的。

2.頁面中js載入與dom載入是同步的,但是也不絕對,這個比較複雜後文介紹。

先看下頁面的生命週期:

domcontentloaded:dom載入完畢,但是外部資源可能沒有載入完畢,如樣式表、資源等。

load:瀏覽器所有資源載入完畢。

beforunload/unload 當使用者離開頁面的時候觸發。

在我們寫demo的時候,往往這樣寫:

window.onload=function()
可能會把我們初始化的資源都寫在onload中,但是在正常專案中,這樣寫的效率是不高的。

因為domcontentloaded 這個時候就已經載入完了我們的dom,這個時候就可以操作dom了。

但是因為樣式沒有載入,如果需要動態去獲採樣式的一些屬性,那麼就需要在onload中了。

domcontentloaded

用法:

document.addeventlistener("domcontentloaded",ready);

function ready()

因為前面提及到dom載入與資源載入是非同步的,這時候不要去拿取資源,所以不要去拿取資源檔案。

前面提及ui渲染執行緒與js引擎是互斥的,即使script 引用是以資源檔案src方式引用的,這時候依然會等待js的載入。

這時候就會有一些小問題,如果js載入時候過程過於漫長,那麼這樣使用者會不會以為宕機了,會不會懷疑有人刪庫跑路了?

如何提高使用者體驗度?

這時候就有async 與 defer 來幫助了。

對了,async只是針對外部資源,也就是對src有效,內聯js無效,defer對內聯與src都有效。

defer,我就不演示了,來介紹這兩個有什麼不同吧。

名稱特性

async

比如有幾個帶有async的js檔案,這幾個執行檔案順序是不知道的,也就是說async的資源檔案是非同步的

defer

會根據我們在頁面中書寫的順序執行

但是我建議不使用defer,看起來defer更好,實際上defer有致命性問題,只有 internet explorer 支援 defer 屬性。

看到這裡開心不開心?又少學了一樣東西。

但是呢,這個async 水有點深,怎麼說呢?

我剛才提及到了domcontentloaded會先執行,其實也不一定。

為何這麼說呢?比如我們頁面有很多不是async的js,然後可能async的資源檔案還有快取,當async載入完畢後,那麼不就要先執行async的資源。

所以async應該理解為獨立於dom生命週期載入執行。

舉乙個async的乙個好處的例子,也是我在網上看到的。

firefox, chrome和opera會在domcontentloaded執行時自動補全表單。

但是當人們看到頁面的時候表單還沒有補齊。這時候就是domcontentloaded被前面執行的js給堵塞了。

這裡提及到另外乙個現代主義瀏覽器的問題,為什麼我們將js指令碼放在body最後載入,是否可以減少到達domcontentloaded的時間?

其實不能,我們知道讓js放在dom元素可以讓docuemnt.getelementbyid 可以拿到元素,但是這依然可以在domcontentloaded中執行,似乎起不好什麼優化效果。

相對以前的瀏覽器,現在瀏覽器不對等待dom載入完畢後渲染,而是會先載入渲染一部分。

但是同樣有問題,比如我們要操作一些dom,但是dom太多,我們的js又在最後,那麼很有可能會亂。

所以我們開啟大型網頁的時候,常常見到嵌入到dom元素直接的。

像這樣:

但是,domcontentloaded依然要等到dom載入完畢。在這裡,其實domcontentloaded還沒有介紹完,因為還有ie的相容問題會在下面提及。

window.onload

window.onbeforeunload

有些網頁在我們在離開的時候,會問我們是否儲存。

就是用這個實現的。

支援情況:

ie、safari 完美支援

firefox、chrome 不支援文字提醒資訊

opera 不支援

window.onunload

使用者離開頁面的時候使用。

支援情況:

ie、safari 完美支援

firefox、chrome 不支援文字提醒資訊

opera 不支援

readystate

這個用的並不多,一般用來相容ie的。

但還有有些用的。比如我們使用async,非同步的時候希望去操作dom,不知道async是在載入後執行還是載入前,所以可以這樣。

if (document.readystate == 'loading')  else 

function dosomething()

回過來看下有什麼狀態:

乙個document 的 document.readystate 屬性描述了文件的載入狀態。

loading / 正在載入

document 仍在載入。

interactive / 可互動

文件已被解析,"正在載入"狀態結束,但是諸如影象,樣式表和框架之類的子資源仍在載入。
complete / 完成

文件和所有子資源已完成載入。表示 load 狀態的事件即將被觸發。
當這個屬性的值變化時,document 物件上的readystatechange 事件將被觸發。

這樣我們可以監聽到html的載入狀態了。

document.addeventlistener('readystatechange', () => log('readystate:' + document.readystate));
有一點上面可能產生誤解:是image的onload先執行呢?還是document.readystate 的complete 先執行呢?

這個不一定。因為如果image是最後乙個載入的資源,**的可能就先是complete。如果image不是最後乙個載入的資源,那麼就是image的onload了。

但是complete **的時候肯定資源都載入完成了。

本來打算在這裡介紹ie相容的,因為document.readystate是乙個非常常用相容處理,但是篇幅問題,就下次吧。

以上來自個人理解,如有不對,望指出。

頁面生命週期

如果頁面請求是回發,則在載入檢視狀態階段之後是載入回發資料階段。這個階段會檢查傳送的窗體字段值,並據此更新相應控制項的屬性。例如,通過 post 機制 發出訊號表示 textbox 控制項的名稱和使用者輸入的值 來回送使用者在 textbox web 控制項中輸入的文字。頁面獲得這些值,在控制項層次...

頁面生命週期

page preinit 該事件在初始化階段的開始被呼叫。用於建立動態控制項,動態設定主控件和主題,在呼叫該事件時,控制項的屬性尚未根據檢視狀態賦值。page init 用來對控制項屬性初始化。page initcomplete 頁面初始化完成時觸發。page preload page load 用...

JSP頁面生命週期

jspservice 方法被呼叫來處理客戶端的請求。對每乙個請求,jsp引擎建立乙個新的執行緒來處理該請求。如果有多個客戶端同時請求該jsp檔案,則jsp引擎會建立多個執行緒。每個客戶端請求對應乙個執行緒。以多執行緒方式執行可以大大降低對系統的資源需求,提高系統的併發量及響應時間。但也要注意多執行緒...