jQuery 的 ready()的純js替代方法
ready
方法是 jQuery 實(shí)現(xiàn)的在 html 頁(yè)面在 DOM(Document Object Model, 文檔對(duì)象模型) 樹完全加載完成后觸發(fā)的一個(gè)方法. 因?yàn)樗邮盏姆椒ㄔ陧?yè)面中所有的 DOM 都可訪問(wèn)時(shí)才執(zhí)行, 所以此時(shí)你完全可以訪問(wèn)和操作 html 中的元素.
在 jQuery 3.0 之前, 典型的匿名函數(shù)方式的用法如下:
$(document).ready(function() { // 在 .ready() 被觸發(fā)時(shí)執(zhí)行. });
在 jQuery 3.0 中 ready() 的變化
在 jQuery 3.0 發(fā)布之前, 有以下幾種 ready 方法的使用方式:
在 document 對(duì)象上: $(document).ready(handler);
在一個(gè)空元素上: $().ready(handler);
或直接使用 (即: 不在一個(gè)指定的元素上): $(handler);
以上的幾種方式是等價(jià)的. 傳入的 handler 會(huì)在頁(yè)面所有的 DOM 都加載完成后執(zhí)行, 不管它被哪個(gè)指定元素執(zhí)行. 也就是, 在 image 元素 $("img") 與 document 對(duì)象上調(diào)用 ready 方法不表明要等待這些元素加載完成后就觸發(fā) handler, 而是在整個(gè) DOM 樹加載完成后才觸發(fā).
在 jQuery 3.0 中, 除了 $(handler); 方法其它的都被棄用了. 官方的理由是:
因?yàn)檫@個(gè)選擇與 .ready() 方法的行為沒有關(guān)系, 它是低效的并且會(huì)誤導(dǎo)用戶猜測(cè)這個(gè)方法的行為.
Ready 和 Load 事件的不同點(diǎn)
ready 事件在頁(yè)面 DOM 完全加載后觸發(fā)并能正確的訪問(wèn)到元素. 而 load 事件在頁(yè)面 DOM 及資源文件(圖片,視頻等)都加載完成后才觸發(fā).
load 事件可以像下面這樣使用:
$(window).on("load", function(){ // 當(dāng)頁(yè)面所有資源(圖片,視頻等)全加載完成后才加載執(zhí)行 });
這會(huì)等待 DOM 加載完成以及圖片加載完成(根據(jù)圖片的大小, 需要加載一定的時(shí)間).
對(duì)于常規(guī)的 DOM 操作你多半不需要 load 事件, 但如果你想做一個(gè)等待頁(yè)面所有資源加載的一個(gè)加載效果或者是計(jì)算圖片的大小時(shí)這應(yīng)該是一個(gè)不錯(cuò)的選擇.
你可能并不需要 jQuery.ready()
ready 方法確保了其內(nèi)部的代碼都能正確的操作 DOM 元素. 這是什么意思? 當(dāng)你把 JavaScript 代碼放到 HTML 文檔中時(shí)它會(huì)確?;卣{(diào)函數(shù)里面的代碼在瀏覽器在已經(jīng)加載頁(yè)面中所有的元素時(shí)執(zhí)行:
<!doctype html> <html> <head> <meta charset="utf-8"> <title>.ready() 教程</title> <script src="https://cdn.jsdelivr.net/jquery/latest/jquery.min.js"></script> <script> $(function(){ // .ready() 的回調(diào)方法, 在 DOM 完全加載完后執(zhí)行 var length = $("p").length; // 下面會(huì)在console控制臺(tái)中輸出 1, 表示有段落 p 存在. // 這就證明了這個(gè)回調(diào)方法在 DOM 完全加載完后執(zhí)行. console.log(length); }); </script> </head> <body> <p>I'm the content of this website</p> </body> </html>
如果你把要執(zhí)行的 JavaScript 放到 body 元素里面的最后位置, 你就不需要用 ready() 方法把代碼包裹在里面了, 因?yàn)樵?JavaScript 代碼執(zhí)行時(shí)頁(yè)面中所有的元素都已經(jīng)加載完成, 所以此時(shí)你就可以訪問(wèn)或操作元素了:
<!doctype html> <html> <head> <meta charset="utf-8"> <title>.ready() 教程</title> </head> <body> <p>I'm the content of this website</p> <script src="https://cdn.jsdelivr.net/jquery/latest/jquery.min.js"></script> <script> var length = $("p").length; // 下面會(huì)在console控制臺(tái)中輸出 1, 表示有段落 p 存在. console.log(length); </script> </body> </html>
使用原生 JavaScript 替換 ready()
對(duì)于現(xiàn)代瀏覽器, 以及 IE9+, 你可以監(jiān)聽 DOMContentLoaded 事件:
document.addEventListener("DOMContentLoaded", function(){ // 在 DOM 完全加載完后執(zhí)行 });
在這里要記住當(dāng)事件已經(jīng)觸發(fā)后回調(diào)方法不會(huì)執(zhí)行(頁(yè)面觸發(fā)事件后才添加的這個(gè)事件監(jiān)聽). 為了確?;卣{(diào)函數(shù)始終能執(zhí)行, jQuery 檢測(cè)了document 的 readyState 屬性(參考), 如果檢測(cè)出的屬性值是 complete 就立即執(zhí)行回調(diào)函數(shù):
var callback = function(){ // 在 DOM 完全加載完后執(zhí)行 }; if ( document.readyState === "complete" || (document.readyState !== "loading" && !document.documentElement.doScroll) ) { callback(); } else { document.addEventListener("DOMContentLoaded", callback); }
你應(yīng)該始終記得引入 domReady 庫(kù), 它已經(jīng)實(shí)現(xiàn)了這個(gè)解決方案.
老版本的 IE
對(duì)于 IE8 及以下版本, 你可以使用 onreadystatechange 事件來(lái)檢測(cè) document 的 readyState 屬性:
document.attachEvent("onreadystatechange", function(){ // 檢測(cè) DOM 是否加載完全 if(document.readyState === "complete"){ // 為了確保在之后不會(huì)再觸發(fā) 移除事件監(jiān)聽 document.detachEvent("onreadystatechange", arguments.callee); // 實(shí)際處理程序... } });
另外你可以使用 load 事件, 像 jQuery 那樣, 這樣就可以在所有的瀏覽器中正確的執(zhí)行了. 這也導(dǎo)致有一定的時(shí)間延遲, 因?yàn)樗鼤?huì)等所有的資源都加載完成. 記住在這個(gè)解決方案中你還是得去檢測(cè) readyState, 如上所述, 這是為了確保當(dāng)事件已經(jīng)觸發(fā)后也能執(zhí)行回調(diào)函數(shù).
結(jié)論
如果你正在尋找一個(gè)原生 JavaScript 來(lái)代替 ready 方法你可以通過(guò) DOMContentLoaded 事件來(lái)解決. 如果你的系統(tǒng)需要支持 IE 那么你就要確保 DOM 已經(jīng)加載完全!
- jquery $(document).ready() 與window.onload的區(qū)別
- jQuery之$(document).ready()使用介紹
- JQuery onload、ready概念介紹及使用方法
- jquery中的$(document).ready()使用小結(jié)
- Jquery中"$(document).ready(function(){ })"函數(shù)的使用詳解
- jquery的$(document).ready()和onload的加載順序
- jquery ready()的幾種實(shí)現(xiàn)方法小結(jié)
- jquery中的$(document).ready()與window.onload的區(qū)別
- 用javascript實(shí)現(xiàn)jquery的document.ready功能的實(shí)現(xiàn)代碼
- JQuery 引發(fā)兩次$(document.ready)事件
相關(guān)文章
理運(yùn)用命名空間讓js不產(chǎn)生沖突避免全局變量的泛濫
為了避免變量之間的覆蓋與沖突,可以生成命名空間,命名空間是一種特殊的前綴,在不同的匿名函數(shù)中,根據(jù)功能聲明一個(gè)不同的命名空間2014-06-06layui 實(shí)現(xiàn)自動(dòng)選擇radio單選框(checked)的方法
今天小編就為大家分享一篇layui 實(shí)現(xiàn)自動(dòng)選擇radio單選框(checked)的方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2019-09-09基于JS實(shí)現(xiàn)一個(gè)簡(jiǎn)單的投票demo
這篇文章主要介紹了如何利用JavaScript實(shí)現(xiàn)一個(gè)簡(jiǎn)單的投票demo,文中的示例代碼講解詳細(xì),對(duì)我們學(xué)習(xí)有一定參考價(jià)值,需要的可以參考一下2022-06-06JS實(shí)現(xiàn)元素上下左右移動(dòng)效果
這篇文章主要為大家詳細(xì)介紹了JS實(shí)現(xiàn)元素上下左右移動(dòng)效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-10-10深入理解Javascript動(dòng)態(tài)方法調(diào)用與參數(shù)修改的問(wèn)題
這篇文章主要是對(duì)Javascript動(dòng)態(tài)方法調(diào)用與參數(shù)修改的問(wèn)題進(jìn)行了詳細(xì)的分析介紹,需要的朋友可以過(guò)來(lái)參考下,希望對(duì)大家有所幫助2013-12-12JavaScript中callee和caller的區(qū)別與用法實(shí)例分析
這篇文章主要介紹了JavaScript中callee和caller的區(qū)別與用法,結(jié)合實(shí)例形式分析了javascript中callee和caller的功能、區(qū)別、用法及操作注意事項(xiàng),需要的朋友可以參考下2019-06-06layui中select,radio設(shè)置不生效的解決方法
今天小編就為大家分享一篇layui中select,radio設(shè)置不生效的解決方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2019-09-09JavaScript中的各種寬高屬性的實(shí)現(xiàn)
這篇文章主要介紹了JavaScript中的各種寬高屬性的實(shí)現(xiàn),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2020-05-05