隨著HTML5和CSS3的飛速發(fā)展,越來越多語義化的標(biāo)簽和炫酷的特性被應(yīng)用到web應(yīng)用開發(fā)中來,各大瀏覽器廠商紛紛開始支持這些新特性,web開發(fā)人員也都興趣十足地試用這些新特性開發(fā)出更絢麗有趣的應(yīng)用,但是各大瀏覽器對(duì)這些新特性參差不齊地支持(尤其是令人頭疼的IE)所帶來的版本兼容性問題始終都是縈繞在開發(fā)人員心頭的噩夢(mèng)。傳統(tǒng)的使用習(xí)慣使得我們很難摒棄老版本瀏覽器,開發(fā)人員只能選擇令人厭煩的手工測(cè)試,測(cè)試,再測(cè)試。
為了解決這一難題,Modernizr應(yīng)運(yùn)而生了。它的名字聽起來有點(diǎn)像Modernize, 確實(shí),該名字起源于使得開發(fā)體驗(yàn)?zāi)軌蚋F(xiàn)代化的目的,但它并非試圖使舊的瀏覽器現(xiàn)代化,也就是使它支持這些新特性(盡管你確實(shí)可以通過添加shim/polyfill腳本來讓瀏覽器支持某些不支持的新特性,后面會(huì)介紹)。
Modernizr是一個(gè)檢測(cè)瀏覽器對(duì)HTML5和CSS3特性支持的開源的js庫(kù),著名的HTML5/CSS3瀏覽器兼容性網(wǎng)站FindmeByIP就是基于該框架實(shí)現(xiàn)的。我們能夠利用它來檢測(cè)瀏覽器是否支持某種新特性,甚至可以額外加載script腳本,滿足你根據(jù)不同的情況動(dòng)態(tài)加載不同的js文件來減少下載量提高性能的需求。
Modernizr提供development和production兩個(gè)版本,development版本包含了對(duì)所有HTML5和CSS3新特性的檢測(cè),適用于學(xué)習(xí)和測(cè)試,對(duì)于剛開始使用Modernizr的新手來說,bella建議你使用這個(gè)版本。當(dāng)你熟悉了Modernizr的工作原理后,你就可以使用production這個(gè)自定義版本,你可以只下載任意數(shù)量的你需要檢測(cè)的特性從而大大減小下載量,這在某種程度上是能小幅提高你程序的性能的。你可以在http://modernizr.com/download/上下載這兩個(gè)版本,點(diǎn)擊該頁(yè)面上的development version鏈接,就可以下載development版,或者,你已經(jīng)看到了如下的特性顯示頁(yè)面
你可以勾選任意你想要測(cè)試的HTML5或CSS3特性,但是默認(rèn)情形下,Extra分類將會(huì)選中如下三項(xiàng):
a) HTML5 Shiv v3.6:它添加了一個(gè)腳本— HTML5 shim 它會(huì)迫使迫使 IE6-8 正確地設(shè)計(jì)并打印 HTML5 元素。如果你打算使用新的 HTML5 語義標(biāo)簽,例如 <header>、<footer>、 <nav>、<section>、<article>等等,那么你需要選這個(gè)選項(xiàng)。
b) Modernizr.load(yepnope.js):它添加了一個(gè)不包含在 development 版本中的可選擇的腳本加載器。它增加了3KB 的下載量,所以如果你不需要它,你可以放棄選擇它。
c) Add CSS Classes: 它將 Modernizr 類添加到開始的標(biāo)簽。如果你想檢測(cè)對(duì) CSS3 功能支持,那么你必須選擇這個(gè)選項(xiàng)。
Modernizr的使用方法很簡(jiǎn)單,當(dāng)你下載了如development版本后只需在頁(yè)面中引入js庫(kù)文件即可,如:
1 | < script type = "”text/javascript”" src = "“js/modernizr.js”" ></ script > |
添加完Modernizr引用后,js程序運(yùn)行的時(shí)候它會(huì)在html元素上添加一批CSS的class名稱,這些class名稱標(biāo)記當(dāng)前瀏覽器支持哪些特性和不支持哪些特性,如果支持會(huì)顯示相應(yīng)的特性名,不支持的話就顯示no-特性名。例如,如果檢測(cè)的瀏覽器支持boxshadow這個(gè)CSS3屬性,Modernizr就會(huì)在標(biāo)簽上添加boxshadow類,否則,就會(huì)添加no-boxshadow類。下圖顯示的是在chrome 23.0.1271.64版本上的HTML5和CSS3新特性支持情況。
然后,你只需要在你的CSS樣式表中定義相應(yīng)的樣式信息即可,你可以像下面這樣定義:
1 | .boxshadow #MyContainer { |
2 | border : none ; |
3 | -webkit-box-shadow: #666 1px 1px 1px ; |
4 | -moz-box-shadow: #666 1px 1px 1px ; |
5 | } |
6 | .no-boxshadow #MyContainer { |
7 | border : 2px solid black ; |
8 | } |
由于瀏覽器會(huì)忽略不支持的CSS3特性,如果當(dāng)前的瀏覽器版本不支持boxshadow屬性,它會(huì)忽略掉boxshadow類,轉(zhuǎn)而引用no-boxshadow類中定義的樣式,省去了你在js程序中檢測(cè)瀏覽器名稱的麻煩邏輯。
當(dāng)然,當(dāng)你的應(yīng)用場(chǎng)景需要你在程序中判斷是否支持某種新特性而給出不同的處理邏輯時(shí),你也可以利用Modernizr很容易地進(jìn)行判斷,此時(shí),你需要用到Modernizr創(chuàng)建的一個(gè)命名為”Modernizr”的全局對(duì)象,其內(nèi)容是為每一個(gè)檢測(cè)完的特性給出的布爾值結(jié)果所組成的列表,如果瀏覽器支持boxShadow屬性,那么Modernizr.boxShadow的值就是true,否則為false,所以引入庫(kù)文件后,你也可以使用此種方法來檢測(cè)瀏覽器對(duì)該特性的支持情況。這個(gè)js對(duì)象針對(duì)某些功能還包含了更為詳細(xì)的信息,如”Modernizr.video.h264”會(huì)告訴你瀏覽器是否支持這個(gè)特殊的編解碼器,”Modernizr.inputtypes.search”會(huì)告訴你當(dāng)前瀏覽器是否支持新的search input類型。
此外,如果Modernizr中并不包含你需要檢測(cè)的特性,你可以調(diào)用Modernizr封裝的addTest函數(shù)來測(cè)試,針對(duì)不同的HTML5和CSS3特性,我們可以在github(由于某種原因,Modernizr被封,該項(xiàng)目現(xiàn)托管在github上)上找到很多已經(jīng)寫好的addTest函數(shù)。我們還是一起來看一個(gè)簡(jiǎn)單的例子,如果你想測(cè)試瀏覽器是否支持getusermedia這個(gè)API(WebRTC新技術(shù)中的API),你可以編寫下面這樣的addTest函數(shù)來測(cè)試:
1 | Modernizr.addTest( 'getusermedia' , !!Modernizr.prefixed( 'getUserMedia' , navigator)); |
相信簡(jiǎn)單的介紹之后,你已經(jīng)初步體會(huì)到了Modernizr能為開發(fā)帶來的便利之處了。了解了Modernizr的功能和如何使用Modernizr后,看看它的源碼熟悉它的實(shí)現(xiàn)原理同樣能學(xué)習(xí)到不少新知識(shí)。Bella在這方面雖然是菜鳥一個(gè),但是還是跟大家分享一點(diǎn)看源碼的心得。
前面bella提到過Modernizr這個(gè)全局對(duì)象,具體它在Modernizr里是怎樣創(chuàng)建的呢?我們來看下面源碼:
1 | window.Modernizr = ( function ( window, document, undefined) { |
2 | var ...; |
3 | Modernizr = {}; |
4 | ... |
5 | return Modernizr; |
6 | })( this , this .document); |
這部分代碼用異步函數(shù)產(chǎn)生了一個(gè)命名空間(雖然js中并沒有真正意義上的命名空間),函數(shù)返回了一個(gè)Modernizr對(duì)象,而這個(gè)對(duì)象被分配到了window.Mordernizr下,這樣,其他的js程序就可以直接使用window.Modernizr或Modernizr對(duì)象。函數(shù)被調(diào)用時(shí)傳入的參數(shù)this指的是函數(shù)執(zhí)行的上下文環(huán)境,也即window這個(gè)全局對(duì)象。
Modernizr是如何測(cè)試對(duì)CSS3新特性的支持程度的呢?原來Modernizr會(huì)先創(chuàng)建一個(gè)DOM對(duì)象,然后利用這個(gè)對(duì)象下的style屬性來測(cè)試是否支持各CSS3新特性。代碼如下:
1 | var mod = 'modernizr' , |
2 | modElem = document.createElement(mod), |
3 | mStyle = modElem.style; |
對(duì)瀏覽器而言,無論它是否能夠識(shí)別我們新創(chuàng)建的html標(biāo)簽,我們都可以給它設(shè)定樣式,所以我們可以給這里新創(chuàng)建的標(biāo)簽設(shè)置樣式。假設(shè)我們想測(cè)試瀏覽器是否支持CSS中用hsla來定義顏色,我們可以先寫一個(gè)應(yīng)用了hsla屬性的樣式放到標(biāo)簽下,然后檢查樣式的值是否含有hsla的字符串,如果瀏覽器不支持,就不會(huì)有hsla字符串(因?yàn)閷?yīng)用了hsla屬性的樣式放到modernizr標(biāo)簽下的動(dòng)作根本就不會(huì)生效)。我們可以編寫如下代碼:
1 | tests[ 'hsla' ] = function () { |
2 | setCss(‘background-color:hsla(120,40%,100%,.5)’); |
3 | return contains(mStyle.backgroundColor, 'rgba' ) || |
4 | contains(mStyle.backgroundColor, 'hsla' ); |
5 | }; |
這里由于有些瀏覽器會(huì)將hsla的表示法轉(zhuǎn)成rgba,所以同時(shí)檢查是否有rgba這個(gè)字符串。
而對(duì)于帶有供應(yīng)商前綴的CSS屬性,我們還需給出不同的處理。回到boxShadow屬性上,Modernizr會(huì)去測(cè)試上面創(chuàng)建的mStyle變量下是否有boxShadow、WebkitBoxShadow、MozBoxShadow、OBoxShadow、msBoxShadow或KhtmlBoxShadow屬性,如果有則表示瀏覽器支持該屬性。這里主要用到了兩個(gè)Modernizr封裝的函數(shù),一個(gè)是testProp(),一個(gè)是testAllProps()。Modernizr.testProp(str)會(huì)返回一個(gè)給定的樣式屬性是否能被識(shí)別,而Modernizr.testAllProps(str)會(huì)返回一個(gè)給定的樣式屬性,或者是任意帶有供應(yīng)商前綴的樣式屬性是否能被識(shí)別。
有關(guān)更多的源碼知識(shí),等bella以后有更深入的研究后再跟大家介紹吧。bella相信如果你熟悉了Modernizr的原理和使用方法,它一定能夠幫助你提高開發(fā)效率。
最后,bella簡(jiǎn)單總結(jié)了一些可供大家學(xué)習(xí)Modernizr的資料:
1. Modernizr官網(wǎng): http://modernizr.com/docs/ 你可以在上面學(xué)習(xí)到Modernizr知識(shí),源碼和下載Modernizr。
2. Modernizr Test Suite網(wǎng)址:http://modernizr.github.com/Modernizr/test/index.html 你可以在上面查詢到各瀏覽器對(duì)HTML5和CSS3特性支持情況,查詢方法:
點(diǎn)擊該頁(yè)面下方的Show the Ref Tests from Caniuse and Modernizr,然后任意單擊一個(gè)測(cè)試的HTML5或CSS3特性的Table鏈接,即可看到各瀏覽器支持情況。
3. shim/polyfill腳本的相關(guān)信息: https://github.com/Modernizr/Modernizr/wiki/HTML5-Cross-Browser-Polyfills
4. 各種檢測(cè)HTML5和CSS3新特性的addTest函數(shù)下載地址:
https://github.com/Modernizr/Modernizr/tree/master/feature-detects
本文出自Tencent Wuhan Blog,轉(zhuǎn)載時(shí)請(qǐng)注明出處
|
新聞熱點(diǎn)
疑難解答