免费视频淫片aa毛片_日韩高清在线亚洲专区vr_日韩大片免费观看视频播放_亚洲欧美国产精品完整版

打開APP
userphoto
未登錄

開通VIP,暢享免費(fèi)電子書等14項(xiàng)超值服

開通VIP
聊聊事件冒泡與事件捕獲

什么是事件?

?  事件是文檔和瀏覽器窗口中發(fā)生的特定的交互瞬間。

什么是事件流:

? ?事件流描述的是從頁(yè)面中接受事件的順序( 說(shuō)白了就是解決頁(yè)面中事件流發(fā)生順序的問(wèn)題。),但有意思的是,微軟(IE)和網(wǎng)景(Netscape)開發(fā)團(tuán)隊(duì)居然提出了兩個(gè)截然相反的事件流概念,IE的事件流是事件冒泡流(event bubbling),而Netscape的事件流是事件捕獲流(event capturing)。

?

讓我們先聊聊DOM0級(jí)事件與DOM2級(jí)事件

?

  • DOM0

直接通過(guò) onclick寫在html里面的事件, 比如:

在標(biāo)簽內(nèi)寫onclick事件

<input onclick="alert(1)" />

?在JS寫onlicke=function(){}函數(shù)

1 document.getElementById("myButton").onclick = function () {2     alert('thanks');3 }

?

?

  • DOM2

主流瀏覽器DOM2級(jí)事件是通過(guò)以下兩個(gè)方法用于處理指定和刪除事件處理程序的操作:

  1. 添加事件 ??addEvenetListener ? ?------ ? 可以為元素添加多個(gè)事件處理程序,觸發(fā)時(shí)會(huì)按照添加順序依次調(diào)用。
  2. 刪除事件 ??removeEventListener ? ------- ??不能移除匿名添加的函數(shù)。

它們都有三個(gè)參數(shù):

  1. 第一個(gè)參數(shù)是事件名(如click)。
  2. 第二個(gè)參數(shù)是事件處理程序函數(shù)。 ?可以為匿名函數(shù),也可以為命名函數(shù)(但如果需要?jiǎng)h除事件,必須是命名函數(shù))
  3. 第三個(gè)參數(shù)如果是true則表示在捕獲階段調(diào)用,為false表示在冒泡階段調(diào)用。

使用DOM 2級(jí)事件處理程序的主要好處是可以添加多個(gè)事件處理程序,事件處理會(huì)按照他們的順序觸發(fā),通過(guò)addEventListener添加的事件只能用removeEventListener來(lái)移除,移除時(shí)傳入的參數(shù)與添加時(shí)使用的參數(shù)必須相同,這也意味著添加的匿名函數(shù)將無(wú)法移除,(注意:我們默認(rèn)的第三個(gè)參數(shù)都是默認(rèn)false,是指在冒泡階段添加,大多數(shù)情況下,都是將事件處理程序添加到事件的冒泡階段,這樣可以最大限度的兼容各個(gè)瀏覽器

?

匿名函數(shù)

1 //這是一個(gè)DOM 2級(jí)事件 添加事件最簡(jiǎn)單的方式(此時(shí)添加的是一個(gè)匿名函數(shù))2     <button>按鈕</button>3     <script>4         var btn=document.querySelector('button');5         btn.addEventListener('click',function(){6             console.log('我是按鈕')7         },false)   //當(dāng)?shù)谌齻€(gè)參數(shù)不寫時(shí),也是默認(rèn)為false(冒泡時(shí)添加事件)8     </script>

?

命名函數(shù)

1     <button>按鈕</button>2     <script>3         var btn=document.querySelector('button');4         btn.addEventListener('click',foo,false);5         function foo(){6             console.log('我是按鈕')7         }8            //其實(shí)操作就是把寫在里面的函數(shù)拿到了外面,而在原來(lái)的位置用函數(shù)名來(lái)代替9     </script>

?


?

看完以上的,我們?cè)倭私馐录芭菖c捕獲

?


?

第一種(事件冒泡)IE提出

IE提出的事件流叫做事件冒泡,即事件開始時(shí)由最具體的元素接收,然后逐級(jí)向上傳播到較為不具體的節(jié)點(diǎn)。

 1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4     <meta charset="UTF-8"> 5     <title>Title</title> 6 </head> 7 <body onclick="bodyClick()"> 8  9     <div onclick="divClick()">10         <button onclick="btn()">11             <p onclick="p()">點(diǎn)擊冒泡</p>12         </button>13     </div>14     <script>15        16        function p(){17           console.log('p標(biāo)簽被點(diǎn)擊')18        }19         function btn(){20             console.log("button被點(diǎn)擊")21         }22          function divClick(event){23              console.log('div被點(diǎn)擊');24          }25         function bodyClick(){26             console.log('body被點(diǎn)擊')27         }28 29     </script>30 31 </body>32 </html>

接下來(lái)我們點(diǎn)擊一下頁(yè)面上的p元素,如下所示

正如上面我們所說(shuō)的,它會(huì)從一個(gè)最具體的的元素接收,然后逐級(jí)向上傳播, p=>button=>div=>body..........事件冒泡可以形象地比喻為把一顆石頭投入水中,泡泡會(huì)一直從水底冒出水面。

??


??

第二種(事件捕獲)網(wǎng)景提出

事件捕獲流的思想是不太具體的DOM節(jié)點(diǎn)應(yīng)該更早接收到事件,而最具體的節(jié)點(diǎn)應(yīng)該最后接收到事件,針對(duì)上面同樣的例子,點(diǎn)擊按鈕,那么此時(shí)click事件會(huì)按照這樣傳播:(下面我們就借用addEventListener的第三個(gè)參數(shù)來(lái)模擬事件捕獲流)

 1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4     <meta charset="UTF-8"> 5     <title>Title</title> 6 </head> 7 <body> 8  9 <div>10     <button>11         <p>點(diǎn)擊捕獲</p>12     </button>13 </div>14 <script>15     var oP=document.querySelector('p');16     var oB=document.querySelector('button');17     var oD=document.querySelector('div');18     var oBody=document.querySelector('body');19 20     oP.addEventListener('click',function(){21         console.log('p標(biāo)簽被點(diǎn)擊')22     },true);23 24     oB.addEventListener('click',function(){25         console.log("button被點(diǎn)擊")26     },true);27 28     oD.addEventListener('click',  function(){29         console.log('div被點(diǎn)擊')30     },true);31 32     oBody.addEventListener('click',function(){33         console.log('body被點(diǎn)擊')34     },true);35 36 </script>37 </body>38 </html>

同樣我們看一下后臺(tái)的打印結(jié)果

和冒泡流完全相反,從最不具體的元素接收到最具體的元素接收事件? body=>div=>button=>p?

?


?

  • 事件代理

在實(shí)際的開發(fā)當(dāng)中,利用事件流的特性,我們可以使用一種叫做事件代理的方法。

<ul id="color-list">    <li>red</li>    <li>yellow</li>    <li>blue</li>    <li>green</li>    <li>black</li>    <li>white</li></ul>

?

?如果點(diǎn)擊頁(yè)面中的li元素,然后輸出li當(dāng)中的顏色,我們通常會(huì)這樣寫:

1 var list_li = document.getElementsByTagName('li');2 for (var i = 0; i < list_li.length; i  ) {3     list_li[i].addEventListener('click',foo,false);4 }5 function foo (e) {6    let x = e.target;7    console.log(x.innerHTML)8 }

?

利用事件流的特性,我們只綁定一個(gè)事件處理函數(shù)也可以完成:

1 var list_ul = document.getElementById('color-list');2 list_ul.addEventListener('click', foo, false);3 function foo (e) {4     let x = e.target;5     if (x.nodeName == 'LI') {6       console.log(x.innerHTML)7     }8 }

?

?


?

  • 冒泡還是捕獲?

    對(duì)于事件代理來(lái)說(shuō),在事件捕獲或者事件冒泡階段處理并沒有明顯的優(yōu)劣之分,但是由于事件冒泡的事件流模型被所有主流的瀏覽器兼容,從兼容性角度來(lái)說(shuō)還是建議大家使用事件冒泡模型。

?

  IE瀏覽器兼容

   IE瀏覽器對(duì)addEventListener兼容性并不算太好,只有IE9以上可以使用。

   要兼容舊版本的IE瀏覽器,可以使用IE的attachEvent函數(shù)

object.attachEvent(event, function)

   兩個(gè)參數(shù)與addEventListener相似,分別是事件和處理函數(shù),默認(rèn)是事件冒泡階段調(diào)用處理函數(shù)。并且由于IE瀏覽器只支持事件冒泡,所以添加的程序都被添加到冒泡階段。要注意的是,寫事件名時(shí)候要加上"on"前綴("onload"、"onclick"等)。

?

 區(qū)別

  addEventListener與attachEvent除了參數(shù)個(gè)數(shù)以及第一個(gè)參數(shù)意義不同外。還有如下兩點(diǎn):

  1. 事件處理程序的作用域不相同:addEventListener的作用域是元素本身,this指的是觸發(fā)元素。而attachEvent事件處理程序會(huì)在全局變量?jī)?nèi)運(yùn)行,this指的是window,所以剛才的例子返回的結(jié)果是undefined,而不是元素id。
  2. 為一個(gè)事件添加多個(gè)事件處理程序時(shí),執(zhí)行順序不同:使用addEventListener時(shí)瀏覽器會(huì)按照添加順序執(zhí)行,IE瀏覽器使用attachEvent時(shí),如果添加的方法過(guò)多時(shí),IE瀏覽器將不會(huì)按照順序執(zhí)行。

?


?

  • 阻止事件冒泡與阻止默認(rèn)事件

  阻止事件冒泡 ??stopPropagation() 方法

  可以阻止事件冒泡,也可以阻止事件捕獲,也可以阻止處于目標(biāo)階段

  使用stopPaopagation()方法可以停止事件在DOM層次的傳播,不再派發(fā)事件。

 1 <div id="p">parent 2       <div id="c">child</div> 3 </div> 4 <script type="text/javascript"> 5 var p = document.getElementById('p'), 6       c = document.getElementById('c'); 7       c.addEventListener('click', function (e) { 8       e.stopPropagation() 9            alert('子節(jié)點(diǎn)冒泡')   //不再向上冒泡到父級(jí)10 }, false);11 p.addEventListener('click', function () {12          alert('父節(jié)點(diǎn)冒泡')}, false);13 </script>

?

  阻止默認(rèn)事件 ??event.preventDefault() 方法 ? (基本沒作用吧...很少有需求將默認(rèn)事件取消掉吧)

event.preventDefault()

?

?

來(lái)源:http://www.icode9.com/content-4-156851.html
本站僅提供存儲(chǔ)服務(wù),所有內(nèi)容均由用戶發(fā)布,如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊舉報(bào)。
打開APP,閱讀全文并永久保存 查看更多類似文章
猜你喜歡
類似文章
JavaScript DOM 事件模型
JavaScript中的DOM與BOM
DOM事件模型總結(jié)【分享】
js修改onclick動(dòng)作的四種方式
HTML DOM addEventListener() 方法 | 菜鳥教程
JS中DOM重點(diǎn)基礎(chǔ)知識(shí)實(shí)驗(yàn)(全)
更多類似文章 >>
生活服務(wù)
分享 收藏 導(dǎo)長(zhǎng)圖 關(guān)注 下載文章
綁定賬號(hào)成功
后續(xù)可登錄賬號(hào)暢享VIP特權(quán)!
如果VIP功能使用有故障,
可點(diǎn)擊這里聯(lián)系客服!

聯(lián)系客服