js中有很多兼容問題,今天先來討論一些常用的關於低版本IE的兼容。(基本上都是為了兼容IE8一下的)
一、事件對象的兼容問題(event)
比如想要獲取鼠標坐標時候需用到event,在高級瀏覽器中會主動傳遞該參數,但是在IE8及以下瀏覽器中,將event放在了window.event屬性下,此時用邏輯短路即可輕松解決
btn.onclick=function(ev){
var e=ev||window.event;
console.log(e);
}
二、事件監聽綁定和移除的兼容問題(綁定:addEventListener和IE:attachEvent,移除:removeEventListener和IE:detachchEvent)
事件綁定的方式分為兩種DOM0級和DOM2級,DOM0級沒有兼容性問題,但是不能同時綁定多個事件因為會覆蓋,DOM2是事件監聽綁定事件可以同時綁定多個事件不會覆蓋但是IE8一下卻不支持,它有自己的綁定方式:attachEvent,這時候就要考慮兼容了。
我們可以封裝一個兼容寫法添加事件監聽和移除事件監聽的方法:
/**
* 添加事件監聽
* @param ele <DOMobject> 添加事件的DOM元素
* @param type <string> 事件類型(不帶on)
* @param fn <function> 事件處理函數
* @param [isCapture] <boolean>可選參數,是否捕獲, true代表捕獲,false代表冒泡,默認為false
*/
function on(ele,type,fn,isCapture){
if(isCapture===undefined)isCapture=false;
if(ele.attachEvent){
ele.attachEvent("on"+type,fn);
}else{
ele.addEventListener(type,fn,isCapture)
}
}
/**
* 移除事件監聽
* @param ele <DOMobject> 添加事件的DOM元素
* @param type <string> 事件類型(不帶on)
* @param fn <function> 事件處理函數
* @param [isCapture] <boolean>可選參數,是否捕獲, true代表捕獲,false代表冒泡,默認為false
*/
function off(ele,type,fn,isCapture){
if(isCapture===undefined)isCapture=false;
if(ele.detachchEvent){
ele.detachchEvent("on"+type,fn);
}else{
ele.removeEventListener(type,fn,isCapture)
}
}
//使用方法
<button id="btn">取消box事件</button>
<div id="box">box</div>
<script src="utils.js"></script>
<script>
//上面引入了外部封裝好的添加和移除監聽方法在utils.js中
var btn=document.querySelector("#btn");
var box=document.querySelector("#box");
function foo(){
//放到函數中是為了能添加和移除是同一個事件,只需要拿到foo
console.log("我是box事件")
}
on(box,"click",foo);//添加box事件
on(btn,"click",function(){
//btn點擊時移除box事件
off(box,"click",foo);
});
</script>
三、獲取滾動條高度的兼容問題(scrollTop)
window.onscroll=function(){
var scrollTop = document.documentElement.scrollTop || window.pageYOffset || document.body.scrollTop;
console.log(scrollTop);
}
四、獲取鍵盤事件的鍵盤碼的兼容問題(keyCode和IE:which)
document.onkeydown=function(ev){
var e=ev||window.event;
var keyCode=e.keyCode||e.which;
console.log(keyCode);
}
五、事件委托精確獲取目標元素的兼容問題(target和IE:srcElement)
btn.onclick=function(ev){
var e = ev || window.event;
var target=e.target||e.srcElement;
console.log(target);
}
六、阻止事件的默認行為的兼容問題(preventDefault和IE:returnValue)
默認行為是瀏覽器之中非常重要的構成之一,比如標簽類的超鏈接跳轉、form表單提交、瀏覽器行為的右鍵菜單、鼠標按下文字選中等都屬於瀏覽器的默認行為,我們用下面的方法阻止它們。但是我們不能隨意的去禁止全部的默認事件;
<a href="javascript:void(0)" >點擊跳轉到百度</a>
<form action="javascript:void(0)" >
<input type="text">
<button id="link">表單里面的button</button>
</form>
document.oncontextmenu = function( ev ){
var e = ev || window.event;
if(e.preventDefault){
e.preventDefault();
}else{
e.returnValue = false;
//return false也可以阻止默認事件但是適合后面沒有其他邏輯代碼,否則會終止函數執行
}
}
七、阻止事件冒泡的兼容問題(stopPropagation和IE:cancelBubble)
document.onclick = function( ev ){
var e = ev || window.event;
if(e.stopPropagation){
e.stopPropagation();
}else{
e.cancelBubble = true;
}
}
八、獲取非行間CSS樣式的兼容性問題(getComputedStyle和IE:currentStyle)
/**
* 獲取元素最終樣式值
* @param obj <DOMobject> 要獲取屬性的元素對象
* @param attr <string> 樣式名稱
* @return <string> 獲取到的樣式值
*/
function getStyle(obj,attr){
if(obj.currentStyle){
return obj.currentStyle[attr];
}else{
return getComputedStyle(obj,false)[attr]
}
}
//使用方法
var box=document.querySelector(".box");
var width=getStyle(box,"width");
console.log(width);
以上內容全部由自己整理,暫時想到的就這些,如果有小伙伴發現有問題或者有其他更好方法,歡迎評論區一起討論學習。