近有一個項目是以華為的響應式效果為參考的,為了把項目做好,必然要把華為的源代碼重頭到尾過一遍,在切圖工作這已是家常便飯,當中有幾點發現,華為是基于bootstrap布局,運用了bootstrap的幻燈片組件,又進行了一些二次方法添加改造,而這次個過程中又碰觸到了另外一個超屌的js判斷ie版本的解決方案,決定將它分享:
jQuery在1.9版本之前,提供了一個瀏覽器對象檢測的屬性$.browser,使用率極高。但是在1.9版本發布之后,大家鐘愛的這個屬性被jQuery無情的拋棄了。大家開始著手尋找$.browser的替代方案。于是各種利用IE bug的檢測方法被搜了出來:
// shortest from a Russianvar ie=!-[1,]// Option from Dean Edwards:var ie=/*@cc_on!@*/false// Use the commented line:var ie//@cc_on=1// Variation (shorter variable):var ie='\v'=='v'// Option to Gareth Hayes (former record-holder):var ie=!+"\v1"
還有一些讀取navigator.userAgent的方式,在蘋果看來這些寫法都不夠友好,也不容易記憶,在搜索和挑選之后,終于找到了一個容易理解且友好方便的寫法!
解決方案
IE知道自身毛病很多,于是提供的一套官方的HTML hack方式:
<!--[if IE]>
// 全部IE版本可見
<![endif]-->
<!--[if IE 6]>
// IE6可見
<![endif]-->
依次等等。
這樣的寫法在其它瀏覽器里,完全就是一坨注釋而直接遭到無視,但在IE里卻不會。IE會分析里面的提到的版本號,并根據版本號確定要不要解析里面的DOM元素和文本內容。等一下!DOM元素?那豈不是可以使用js來獲取里面的DOM元素?反正誰看到了,誰就是IE!于是,國外大神就有了下面的寫法:
var isIE=function(){ var b=document.createElement('b')
b.innerHTML='<!--[if IE]><i></i><![endif]-->'
return b.getElementsByTagName('i').length===1}
這也太巧妙了!首先生成了一個b元素,設置它的innerHTML為一坨只有IE才認識的注釋,注釋里只有一個空的標簽,然后讀取里面的出現的元素i的個數是不是等于1,是不是等于1,是不是等于1。。。。
在大蘋果看來,這樣的寫法比其它任何一種都要好。至于為什么生成一個b元素并且里面寫一個i元素而不是div或者strong,更多是考慮到前者字節量更小。
檢測各個IE版本的方法也就順理成章了:
var isIE6=function(){ var b=document.createElement('b')
b.innerHTML='<!--[if IE 6]><i></i><![endif]-->'
return b.getElementsByTagName('i').length===1}// var isIE7// ...
更進一步
在蘋果看來,還可以進一步將版本號提取成參數,就能生成一個通用的檢測IE版本的函數了:
var isIE=function(ver){ var b=document.createElement('b')
b.innerHTML='<!--[if IE ' + ver + ']><i></i><![endif]-->'
return b.getElementsByTagName('i').length===1}if(isIE(6)){ // IE 6}// ...if(isIE(9)){ // IE 9}
這樣想檢測哪個版本都毫無壓力。但是,如果只想檢測是不是IE,而不關心瀏覽器版本,那只需要在調用函數的時候,不傳遞參數即可。
var ie=isIE()
最后依次貼下在各大瀏覽器里測試代碼的截圖。
alert('ie6:' + isIE(6) + '\n' + 'ie7:' + isIE(7) + '\n' + 'ie8:' + isIE(8) + '\n' + 'ie9:' + isIE(9) + '\n' + 'ie:' + isIE())
切圖網常年專注h5前端開發技術,關注用戶體驗,如果你對h5前端,響應式,微場景等該興趣請加公眾微信賬號:qietuwang
釋不同的瀏覽器版本
(1)、支持所有的IE瀏覽器(不包括IE10標準模式)
<!--[if IE]>只有IE6,7,8,9瀏覽器顯示(IE10標準模式不支持)<![endif]-->
(2)、所有非IE瀏覽器(不包括IE10標準模式)
<!--[if !IE]>只有非IE瀏覽器顯示(不包括IE10)<![endif]-->
(3)、IE10瀏覽器
目前還沒有找到該版本瀏覽器的像<!--[if IE 9]>似的單獨注釋,但IE10做得很不錯了,就單單布局而言,頁面在IE10、FireFox、Chrome上的表現已經沒有什么區別了。
(4)、IE9瀏覽器
<!--[if IE 9]>IE9瀏覽器顯示<hr/><![endif]-->
(5)、IE8瀏覽器
<!--[if IE 8]>IE8瀏覽器顯示<hr/><![endif]-->
(6)、IE7瀏覽器
<!--[if IE 7]>IE7瀏覽器顯示<hr/><![endif]-->
(7)、IE6瀏覽器
<!--[if IE 6]>IE6瀏覽器顯示<hr/><![endif]-->
(8)、IE10以下版本瀏覽器(不包括IE10)
<!--[if lt IE 10]>IE10以下版本瀏覽器顯示(不包括IE10)<hr/><![endif]-->
(9)、IE9及IE9以下版本瀏覽器(包括IE9)
<!--[if lte IE 9]>IE9及IE9以下版本瀏覽器顯示(包括IE9)<hr/><![endif]-->
(10)、IE6以上版本瀏覽器(不含IE6)
<!--[if gt IE 6]>IE6以上版本瀏覽器顯示(不含IE6)<hr/><![endif]-->
(11)、IE7及IE7以上版本瀏覽器
<!--[if gte IE 7]>IE7及IE7以上版本瀏覽器顯示(包含IE7)<hr/><![endif]-->
我們不可能為了兼容像上面那么寫,把整頁的內容分別寫在不同的注釋塊內。其實這里有兩種方法:
方法1:根據不同的瀏覽器版本,載入不同的css
如我們需要分別兼容IE6、7、8,我們可以這樣做
<!--[if IE 8]>
<link rel="stylesheet" type="text/css" href="ie8.cdd">
<![endif]-->
<!--[if IE 7]>
<link rel="stylesheet" type="text/css" href="ie7.cdd">
<![endif]-->
<!--[if IE 6]>
<link rel="stylesheet" type="text/css" href="ie6.cdd">
<![endif]-->
方法2:根據不同的瀏覽器版本,給html或body掛載不同的類如
<!--[if lt IE 7 ]><html class="ie6" lang="zh-cn"><![endif]-->
<!--[if IE 7 ]><html class="ie7" lang="zh-cn"><![endif]-->
<!--[if IE 8 ]><html class="ie8" lang="zh-cn"><![endif]-->
<!--[if IE 9 ]><html class="ie9" lang="zh-cn"><![endif]-->
lt,lte,gt,gte 分別表示什么意思:
lt:小于當前版本
lte:小于或等于當前版本,包括本身
gt:大于當前版本
gte:大于或等于當前版本,包括本身
在前端開發編寫Javascript代碼的過程中,經常要考慮不同瀏覽器之間的差異,找出兼容性方案。
今天這篇文章我們來看看兩個有意思的問題,都是因為瀏覽器不同帶給我們理解上的差異。
本篇文章的測試主要以最新Chrome,Firefox和IE8為代表。
Javascript
函數標識符
根據ECMAScript標準,變量名,函數方法名等標識符只能包含數字,字母,'$','_'等,是不能包含點運算符('.')的。
目前最新的Chrome,Firefox,Safari等瀏覽器都遵循這一原則,但是IE6,IE7,IE8卻不一樣,它們支持點運算符來進行函數方法命名。
我們將下面一段代碼在不同的瀏覽器中運行測試。這段代碼是定義一個對象A,然后在prototype上定義一個變量b,b為一個Function,然后生成一個A的實例a,最后返回a.b的類型。
測試代碼
首先是在Chrome瀏覽器中。
Chrome瀏覽器運行結果
通過報的錯誤,我們發現不支持點運算符'.'操作。
然后在IE8中測試。
IE8測試結果
在IE8中測試后發現,輸出了function,證明b已經明確定義為了對象A的一個屬性。
(吐槽一下:IE8的調試真的是相當麻煩!!!)
函數表達式標識符
根據ECMAScript標準,函數表達式的標識符只能在函數體內部訪問,它的作用域只存在于該函數體內部。
代碼
以上代碼中,b就是函數表達式的標識符。
在Chrome等高級瀏覽器中,在外部是無法訪問到b的,以下為測試結果。
Chrome測試結果
返回undefined,證明Chrome瀏覽器是遵循了ECMAScript規則的。
而在IE8中測試結果如下所示。
IE8測試結果
最后返回的結果是function,就證明IE8并沒有遵循ECMAScript規則。
解決方案
為了防止上述的問題發生,請避免使用IE的這些不遵循規則的特性,保證瀏覽器的兼容性。
什么是塊級函數聲明呢?我們先來看看下面這段代碼。
塊級函數聲明
就是在一段判斷語句中,滿足條件后才去定義函數,不滿足條件就不去定義函數。
如果在這段代碼后再去執行zero方法,結果會有什么差異呢?
首先來看看在Chrome瀏覽器下的運行結果。
Chrome運行結果
從運行結果來看,zero不是一個函數,說明zero的聲明為生效。
然后看看IE8的運行結果。
IE8運行結果
通過運行結果可以看出,在IE8中,即使變量variable不為true,方法zero仍然被成功定義。
對于塊級函數聲明問題,是在ES6中新增的標準,在早期不支持ES6標準的瀏覽器中和IE8中都一樣,包括早期的Chrome和Firefox等高級瀏覽器。
解決方案
遇到IE8級以下版本的瀏覽器,就避免使用塊級函數聲明的處理。
今天這篇文章總結了兩個與函數聲明和函數表達式有關的瀏覽器兼容性問題。在測試過程中發現IE瀏覽器真的是超級難用啊,而且有很多兼容性的問題都是來自于IE,所以大家盡可能的遠離IE吧。
*請認真填寫需求信息,我們會在24小時內與您取得聯系。