瀏覽器測試Support(已移出jQuery蚓庭,作用單獨(dú)插件)
根據(jù)瀏覽器是否支持某項(xiàng)特定的功能特性甸鸟,來決定程序的執(zhí)行分支
由于$.browser基于navigator.userAgent檢測瀏覽器類型,很容易被用戶和瀏覽器欺騙崭添,并且缺乏靈活性和不夠全面终佛。
因此最好避免編寫基于特定瀏覽器的代碼。
相對于$.browser墨辛,$.support針對瀏覽器特定特性的檢測則更為有效。
$.browser的實(shí)現(xiàn)代碼如下:
// 用戶代理檢測正則表達(dá)式定義
var rwebkit = /(webkit)[ \/]([\w.]+)/,
ropera = /(opera)(?:.*version)?[\/]([\w.]+)/,
rmsie = /(msie)([\w.]+)/,
rmozilla = /(mozilla)(?:.*?rv:([\w.]+))?/,
// 到處都是把屬性取出來趴俘,作為局部變量使用睹簇,可以減少跨作用域查詢,提高性能
userAgent = navigator.userAgent,
// 用戶代理匹配結(jié)果
browserMatch,
// 實(shí)際執(zhí)行匹配的函數(shù)
uaMatch: function( ua ) {
ua = ua.toLowerCase();
// 依次匹配各瀏覽器
var match = rwebkit.exec( ua ) ||
ropera.exec( ua ) ||
rmsie.exec( ua ) ||
ua.indexOf("compatible") < 0 && rmozilla.exec( ua ) ||
[];
// match[1] || "" :match[1]為false(空字符串寥闪、null太惠、undefined、0等)時(shí)疲憋,默認(rèn)為""
// match[2] || "0" :match[2]為false(空字符串凿渊、null、undefined缚柳、0等)時(shí)埃脏,默認(rèn)為"0"
return { browser: match[1] || "", version: match[2] || "0" };},
// 將測試結(jié)果保存至jQuery.browser
browserMatch = jQuery.uaMatch(userAgent);
if ( browserMatch.browser ) {
jQuery.browser[ browserMatch.browser ] = true;
jQuery.browser.version = browserMatch.version;
}
// 不推薦使用safari標(biāo)記,用webkit代替
if ( jQuery.browser.webkit ) {
jQuery.browser.safari = true;
}
Support功能特性檢測法
即根據(jù)瀏覽器是否支持某項(xiàng)特定的功能特性喂击,來決定程序的執(zhí)行分支剂癌,這種方法不考慮瀏覽器類型和版本,也不考慮瀏覽器升級(jí)帶來的變化翰绊,更加安全佩谷、靈活,同時(shí)減少了維護(hù)工作监嗜,因此成為了當(dāng)下主流的檢測方法谐檀。例如綁定load事件的代碼:
// 兼容事件模型,通過檢測瀏覽器的功能特性裁奇,而非嗅探瀏覽器
if ( document.addEventListener ) {
// 使用較快的加載完畢事件
document.addEventListener( "DOMContentLoaded", DOMContentLoaded, false );
// 注冊window.onload回調(diào)函數(shù)
window.addEventListener( "load", jQuery.ready, false );
// 如果是IE事件模型
} else if ( document.attachEvent ) {
// 確保在onload之前觸發(fā)onreadystatechange桐猬,可能慢一些但是對iframes更安全
document.attachEvent( "onreadystatechange", DOMContentLoaded );
// 注冊window.onload回調(diào)函數(shù)
window.attachEvent( "onload", jQuery.ready );
// If IE and not a frame
// continually check to see if the document is ready
var toplevel = false;
try {
toplevel = window.frameElement == null;
} catch(e) {}
if ( document.documentElement.doScroll && toplevel ) {
doScrollCheck();
}
}
典型應(yīng)用:盒模型
盒模型是CSS中的一個(gè)概念,CSS 將所有的網(wǎng)頁元素都看做是一個(gè)矩形框刽肠,這個(gè)框由元素的內(nèi)容(content)溃肪、內(nèi)邊距(padding)免胃、邊框(border)和外邊距(margin)組成,
兩種盒模型
IE傳統(tǒng)模型:width和height屬性包括內(nèi)邊距和邊框?qū)挾?/p>
W3C標(biāo)準(zhǔn)模型:width和height屬性不包含邊距和邊框?qū)挾?/p>
尺寸封裝
jQueryn封裝了這兩種盒模型的差異惫撰,統(tǒng)一為W3C標(biāo)準(zhǔn)模型羔沙,并提供了修正后的接口:如下所示:
接口 計(jì)算公式
width, height? content
innerWidth, innerHeight content+padding
outerWidth, outerHeight content+padding+border+可選的margin
Sizzle選擇器
工作原理:
選擇器表達(dá)式:'div>p',
塊表達(dá)式 'div'、'p'
并列選擇器表達(dá)式: 'div, p'
塊分割器:對選擇器表達(dá)式從左到右分割出一個(gè)個(gè)塊表達(dá)式
查找器:對塊表達(dá)式進(jìn)行查找厨钻,找到的DOM元素?cái)?shù)組叫候選集
過濾器:對塊表達(dá)式和候選集進(jìn)行過濾
關(guān)系過濾器: 對塊表達(dá)式之間的關(guān)系進(jìn)行過濾:+ 緊挨著的兄弟關(guān)系扼雏;> 父子關(guān)系;“ ”祖先關(guān)系夯膀;“~”之后的所有兄弟關(guān)系
候選集:查找器的結(jié)果诗充,待過濾器進(jìn)行過濾
映射集:候選集的副本,過濾器和關(guān)系過濾器對映射集進(jìn)行過濾
工作流程:
1.使用塊分割器對選擇器表達(dá)式進(jìn)行分割诱建,從左向右
如果遇到","分割的并列選擇器表達(dá)式蝴蜓,只分割到第一個(gè)逗號(hào)前的選擇器表達(dá)式1,將剩余部分記錄下來涂佃。
2.對最后一個(gè)塊表達(dá)式進(jìn)行查找Sizzle.find励翼,結(jié)果放入到候選集set蜈敢,并將塊表達(dá)式中匹配的字符串部分刪除
3.如果最后一個(gè)塊表達(dá)式不為空(字符串)辜荠,過濾器Sizzle.filter對set進(jìn)行過濾
用分割器,對塊表達(dá)式進(jìn)行進(jìn)行分割抓狭,查找伯病,放到候選集set,刪掉塊表達(dá)式中已匹配的否过,剩余的部分記錄下來
查找器進(jìn)行查找匹配午笛,
過濾器對set進(jìn)行過濾
將以上查找和過濾得到候選集set復(fù)制,放入映射集checkSet苗桂,后邊的過濾操作在checkSet上進(jìn)行