jquery ready函數(shù)源代碼研究
更新時(shí)間:2009年12月06日 00:57:12 作者:
我們都知道,很多時(shí)候,在頁面加載完后都需要做一些相應(yīng)的初始化動(dòng)作.例如,運(yùn)行某些js特效,設(shè)置表單等等.怎么知道頁面加載完了呢?
一般情況下都是設(shè)置body標(biāo)簽的onload監(jiān)聽window的load事件.但load事件是要在頁面的元素全部加載完了才觸發(fā)的,如果頁面上圖片較多或圖片太大,就會(huì)導(dǎo)致初始化的代碼未被執(zhí)行的時(shí)候用戶就做了其它操作了. Jquery庫提供了一個(gè)非常方便好用的函數(shù)( $(selector).ready()),讓我們可以在頁面的dom加載完后就可以做相應(yīng)的操作(當(dāng)然,這還得看用戶瀏覽器的支持).,而不用等待全部元素加載完成.例如:
$(document).ready(function (){ alert('use in page script tag') });
$(document).ready(function (){ alert('use in import js file') });
現(xiàn)在讓我們來研究一下這個(gè)函數(shù)的實(shí)現(xiàn).
原理:
在jquery腳本加載的時(shí)候,會(huì)設(shè)置一個(gè)isReady的標(biāo)記,監(jiān)聽DOMContentLoaded事件(這個(gè)不是什么瀏覽器都有的,不同瀏覽器,jquery運(yùn)作方式不一樣).當(dāng)然遇到調(diào)用ready函數(shù)的時(shí)候,如果isReady未被設(shè)置,那就是說頁面未加載完,就會(huì)把要執(zhí)行的函數(shù)用一個(gè)數(shù)組緩存起來,當(dāng)頁面加載完后,再把緩存的函數(shù)一一執(zhí)行.
Jquery中的詳細(xì)代碼分析:
ready: function(fn) {
// 綁定監(jiān)聽器
bindReady();
// 如果 DOM 加載完成
if ( jQuery.isReady )
// 馬上運(yùn)行此函數(shù)
fn.call( document, jQuery );
// 否則保存起來
else
// 把函數(shù)加入緩存數(shù)組中
jQuery.readyList.push( function() { return fn.call(this, jQuery); } );
return this;
}
讓我們看看jquery如果實(shí)現(xiàn)不同瀏覽器dom加載完成的通知 bindReady()函數(shù):
var readyBound = false;
function bindReady(){
if ( readyBound ) return;
readyBound = true;
// Mozilla,opera,webkitnightlies支持DOMContentLoaded事件
if ( document.addEventListener && !jQuery.browser.opera)
// 直接使用事件回調(diào)即可
document.addEventListener( "DOMContentLoaded", jQuery.ready, false );
// 如果是ie并且不是嵌在frame中
// 就需要不斷地檢查文檔是否加載完
if ( jQuery.browser.msie && window == top ) (function(){
if (jQuery.isReady) return;
try {
// 這個(gè)地方標(biāo)記一下,在后面解析(1)
document.documentElement.doScroll("left");
} catch( error ) {
//// 這個(gè)地方標(biāo)記一下,在后面解析(2)
setTimeout( arguments.callee, 0 );
return;
}
// and execute any waiting functions
jQuery.ready();
})();
if ( jQuery.browser.opera )
document.addEventListener( "DOMContentLoaded", function () {
if (jQuery.isReady) return;
for (var i = 0; i < document.styleSheets.length; i++) // 標(biāo)記(3)
if (document.styleSheets[i].disabled) {
setTimeout( arguments.callee, 0 );
return;
}
// and execute any waiting functions
jQuery.ready();
}, false);
if ( jQuery.browser.safari ) {
var numStyles;
(function(){
if (jQuery.isReady) return;
if ( document.readyState != "loaded" && document.readyState != "complete" ) { // 標(biāo)記(4)
setTimeout( arguments.callee, 0 );
return;
}
if ( numStyles === undefined )
numStyles = jQuery("style, link[rel=stylesheet]").length;
if ( document.styleSheets.length != numStyles ) { // 標(biāo)記(5)
setTimeout( arguments.callee, 0 );
return;
}
// and execute any waiting functions
jQuery.ready();
})();
}
// A fallback to window.onload, that will always work
jQuery.event.add( window, "load", jQuery.ready ); // 標(biāo)記(6)
}
}
(1):這個(gè)主要是測出ie下的dom ready,原理在這里http://javascript.nwbox.com/IEContentLoaded/,利用在ie下.當(dāng)dom未完成解析時(shí),調(diào)用document的document.documentElement.doScroll(”left”)會(huì)出錯(cuò)這個(gè)小技巧便可得知dom有沒有ready了.
(2):setTimeout( arguments.callee, 0 )這句是表示延遲0秒調(diào)用,實(shí)際上它不會(huì)馬上就調(diào)用,而是會(huì)盡可能快地調(diào)用,它告訴瀏覽器為當(dāng)前任何掛起的事件運(yùn)行完事件句柄并且完成了文檔當(dāng)前狀態(tài)的更新后才調(diào)用. Arguments.callee即是外層的匿名函數(shù),參數(shù)的調(diào)用者
(3):這個(gè)地方你也許覺得奇怪,為什么不在mozilla那里一起處理呢? 原因就是opera的DOMContentLoaded事件發(fā)生后,其css樣式是還沒完全可用的,所以要特殊處理,就是判斷每個(gè)css的tag都是不是enable了.
(4),(5):safari中document.readyState的狀態(tài)為loaded或complete時(shí),css文件引入還未能確定是不是解析完了的,所以要通過判斷其css文件數(shù)目
(6):最后,如果上面的hack都不支持的話…就用最保險(xiǎn)的load事件,保證能執(zhí)行到初始化代碼.
$(document).ready(function (){ alert('use in page script tag') });
$(document).ready(function (){ alert('use in import js file') });
現(xiàn)在讓我們來研究一下這個(gè)函數(shù)的實(shí)現(xiàn).
原理:
在jquery腳本加載的時(shí)候,會(huì)設(shè)置一個(gè)isReady的標(biāo)記,監(jiān)聽DOMContentLoaded事件(這個(gè)不是什么瀏覽器都有的,不同瀏覽器,jquery運(yùn)作方式不一樣).當(dāng)然遇到調(diào)用ready函數(shù)的時(shí)候,如果isReady未被設(shè)置,那就是說頁面未加載完,就會(huì)把要執(zhí)行的函數(shù)用一個(gè)數(shù)組緩存起來,當(dāng)頁面加載完后,再把緩存的函數(shù)一一執(zhí)行.
Jquery中的詳細(xì)代碼分析:
復(fù)制代碼 代碼如下:
ready: function(fn) {
// 綁定監(jiān)聽器
bindReady();
// 如果 DOM 加載完成
if ( jQuery.isReady )
// 馬上運(yùn)行此函數(shù)
fn.call( document, jQuery );
// 否則保存起來
else
// 把函數(shù)加入緩存數(shù)組中
jQuery.readyList.push( function() { return fn.call(this, jQuery); } );
return this;
}
讓我們看看jquery如果實(shí)現(xiàn)不同瀏覽器dom加載完成的通知 bindReady()函數(shù):
復(fù)制代碼 代碼如下:
var readyBound = false;
function bindReady(){
if ( readyBound ) return;
readyBound = true;
// Mozilla,opera,webkitnightlies支持DOMContentLoaded事件
if ( document.addEventListener && !jQuery.browser.opera)
// 直接使用事件回調(diào)即可
document.addEventListener( "DOMContentLoaded", jQuery.ready, false );
// 如果是ie并且不是嵌在frame中
// 就需要不斷地檢查文檔是否加載完
if ( jQuery.browser.msie && window == top ) (function(){
if (jQuery.isReady) return;
try {
// 這個(gè)地方標(biāo)記一下,在后面解析(1)
document.documentElement.doScroll("left");
} catch( error ) {
//// 這個(gè)地方標(biāo)記一下,在后面解析(2)
setTimeout( arguments.callee, 0 );
return;
}
// and execute any waiting functions
jQuery.ready();
})();
if ( jQuery.browser.opera )
document.addEventListener( "DOMContentLoaded", function () {
if (jQuery.isReady) return;
for (var i = 0; i < document.styleSheets.length; i++) // 標(biāo)記(3)
if (document.styleSheets[i].disabled) {
setTimeout( arguments.callee, 0 );
return;
}
// and execute any waiting functions
jQuery.ready();
}, false);
if ( jQuery.browser.safari ) {
var numStyles;
(function(){
if (jQuery.isReady) return;
if ( document.readyState != "loaded" && document.readyState != "complete" ) { // 標(biāo)記(4)
setTimeout( arguments.callee, 0 );
return;
}
if ( numStyles === undefined )
numStyles = jQuery("style, link[rel=stylesheet]").length;
if ( document.styleSheets.length != numStyles ) { // 標(biāo)記(5)
setTimeout( arguments.callee, 0 );
return;
}
// and execute any waiting functions
jQuery.ready();
})();
}
// A fallback to window.onload, that will always work
jQuery.event.add( window, "load", jQuery.ready ); // 標(biāo)記(6)
}
}
(1):這個(gè)主要是測出ie下的dom ready,原理在這里http://javascript.nwbox.com/IEContentLoaded/,利用在ie下.當(dāng)dom未完成解析時(shí),調(diào)用document的document.documentElement.doScroll(”left”)會(huì)出錯(cuò)這個(gè)小技巧便可得知dom有沒有ready了.
(2):setTimeout( arguments.callee, 0 )這句是表示延遲0秒調(diào)用,實(shí)際上它不會(huì)馬上就調(diào)用,而是會(huì)盡可能快地調(diào)用,它告訴瀏覽器為當(dāng)前任何掛起的事件運(yùn)行完事件句柄并且完成了文檔當(dāng)前狀態(tài)的更新后才調(diào)用. Arguments.callee即是外層的匿名函數(shù),參數(shù)的調(diào)用者
(3):這個(gè)地方你也許覺得奇怪,為什么不在mozilla那里一起處理呢? 原因就是opera的DOMContentLoaded事件發(fā)生后,其css樣式是還沒完全可用的,所以要特殊處理,就是判斷每個(gè)css的tag都是不是enable了.
(4),(5):safari中document.readyState的狀態(tài)為loaded或complete時(shí),css文件引入還未能確定是不是解析完了的,所以要通過判斷其css文件數(shù)目
(6):最后,如果上面的hack都不支持的話…就用最保險(xiǎn)的load事件,保證能執(zhí)行到初始化代碼.
您可能感興趣的文章:
- 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)事件
- JQuery下關(guān)于$.Ready()的分析
- JQuery的ready函數(shù)與JS的onload的區(qū)別詳解
- jquery ready函數(shù)深入分析
相關(guān)文章
jquery+css實(shí)現(xiàn)動(dòng)感的圖片切換效果
這篇文章主要介紹了jquery+css實(shí)現(xiàn)動(dòng)感的圖片切換效果,效果實(shí)現(xiàn)很精致,動(dòng)畫簡潔大方,推薦給大家,感興趣的小伙伴們可以參考一下2015-11-11
可輸入文字查找ajax下拉框控件 ComBox的實(shí)現(xiàn)方法
下面小編就為大家?guī)硪黄奢斎胛淖植檎襛jax下拉框控件 ComBox的實(shí)現(xiàn)方法。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2016-10-10
淺談jQuery中hide和fadeOut的區(qū)別 show和fadeIn的區(qū)別
下面小編就為大家?guī)硪黄獪\談jQuery中hide和fadeOut的區(qū)別 show和fadeIn的區(qū)別。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2016-08-08
淺析jQuery的鏈?zhǔn)秸{(diào)用之each函數(shù)
如果對于jquery的$()包裝器函數(shù)還不是很清楚,請先參閱我的上一篇日志:淺析jQuery的鏈?zhǔn)秸{(diào)用2010-12-12
jquery監(jiān)控?cái)?shù)據(jù)是否變化(修正版)
jquery監(jiān)控?cái)?shù)據(jù)是否變化(修正版) 之前寫的那篇中存在許多bug,今天重新整理了一下。還請各位指教2011-04-04
js實(shí)現(xiàn)的黑背景灰色二級導(dǎo)航菜單效果代碼
這篇文章主要介紹了js實(shí)現(xiàn)的黑背景灰色二級導(dǎo)航菜單效果代碼,涉及javascript操作頁面元素動(dòng)態(tài)切換的實(shí)現(xiàn)技巧,非常具有實(shí)用價(jià)值,需要的朋友可以參考下2015-08-08
如何使用jQuery Draggable和Droppable實(shí)現(xiàn)拖拽功能
本篇文章是對使用jQuery Draggable和Droppable實(shí)現(xiàn)拖拽功能的方法進(jìn)行了詳細(xì)的分析介紹,需要的朋友參考下2013-07-07
Jquery實(shí)現(xiàn)textarea根據(jù)文本內(nèi)容自適應(yīng)高度
本文給大家分享的是Jquery實(shí)現(xiàn)textarea根據(jù)文本內(nèi)容自適應(yīng)高度,這些在平時(shí)的項(xiàng)目中挺實(shí)用的,所以抽空封裝了一個(gè)文本框根據(jù)輸入內(nèi)容自適應(yīng)高度的插件,這里推薦給小伙伴們。2015-04-04

