
前言
很久沒有在簡書上寫blog,都在github上寫了,看有點時間就搬運(yùn)一下
關(guān)于事件委托的概念和原理就不多說,自行Google。
二層元素實現(xiàn)的委托
二層元素實現(xiàn)的委托是我自己定義的名稱,具體是如下的場景
<div id="tab">
<a href="javascript:;" title="left">left</dl>
<a href="javascript:;" title="right">right</dl>
</div>
然后將事件綁定在id="tab"元素上。這樣的場景也是在比較多的,高程對事件委托的解析也是用以上差不多的代碼解析的,具體實現(xiàn)是這樣的:
先是將事件綁定在id="tab"元素上,點擊是判斷title,title === ‘left’時觸發(fā)left的邏輯,否則觸發(fā)right的邏輯
document.querySelector('#tab')
.addEventListener('touchstart', e => {
const target = e.target;
if(target.title === 'left') {
// left的邏輯代碼
} else {
// right的邏輯代碼
}
}, false);
這樣的代碼乍看之下貌似沒有問題,但是,加入是下面的html代碼就會出現(xiàn)bug:
<div id="tab">
<a href="javascript:;" title="left"><img src="left_icon.png"> left</a>
<a href="javascript:;" title="right"><img src="right_icon.png"> right</a>
</div>
當(dāng)點擊a便簽的圖標(biāo),就會出現(xiàn)bug,只要是點擊中圖標(biāo),無論是點擊left還是right都會是觸發(fā)right的邏輯,
為什么?因為點擊中icon的話,e.target是img便簽,而不是a便簽,而img并沒有title,如果你說可以給img便簽也可以添加title,但這不是一個之便不治本的解決方案嗎?加入a便簽內(nèi)有更多的后代元素怎么辦?全都添加title嗎?明顯不現(xiàn)實。
event.path屬性實現(xiàn)委托
使用console.log(e)點path屬性,你可以卡到path是一個數(shù)組

升序正好是冒泡順序,正好可以利用這個順序?qū)崿F(xiàn)多層元素的事件委托。
document.querySelector('#tab')
.addEventListener('touchstart', e => {
const path = e.path;
for (let index = 0; index < path.length; index++) {
const element = path[index];
if(element.title === 'left') {
// left
break;
} else if(element.title === 'right') {
// right
break;
}
}
}, false);
event.composedPath()
雖說以上代碼已經(jīng)可以實現(xiàn)多級元素的事件委托,但是不幸的是path的兼容性是比較差[捂臉]
image
看上面的引用,可以知道path并非標(biāo)準(zhǔn)的,而composedPath才是標(biāo)準(zhǔn)的,但也是比較新的,換言之,兼容性也不會有多好,但path和composedPath一起使用,兼容必然會更高。
document.querySelector('#tab')
.addEventListener('touchstart', e => {
const path = e.path || e.composedPath();
for (let index = 0; index < path.length; index++) {
const element = path[index];
if(element.title === 'left') {
// left
break;
} else if(element.title === 'right') {
// right
break;
}
}
}, false);
小結(jié)
以上實現(xiàn)委托的方法是我自己自行意淫的,是不是主流實現(xiàn)方法?我還還沒有去驗證,先留個坑,誰那么巧合看到了我的文章,有更好的想法,或者主流方法實現(xiàn),請不吝賜教。
