冒泡:做用於子元素上的事件會一級一級向上傳遞,相似於冒泡的形式。
捕獲:做用於父元素的事件會一級一級向下傳遞到最終的子元素。html
文檔請參考 addEventListener,以及 runnoob的addEventListener
EventTarget.addEventListener()語法:瀏覽器
element.addEventListener(event, function, useCapture)
注意useCapture參數,他是一個boolean值,指定事件是否在捕獲或冒泡階段執行。默認爲false,若是指定爲true,代表在捕獲階段執行,指定爲true,代表在冒泡階段執行。this
先看以下代碼:spa
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>test</title> <style> #parent { height: 300px; background-color: #bcbcbc; } #son { margin-top: 100px; height: 100px; background-color: green; } </style> </head> <body> <div id="parent"> 我是父親 <div id="son">我是兒子</div> </div> <script> function handler(event) { console.log('target: ', event.target); console.log('curtrentTarget: ', event.currentTarget); } let pa = document.getElementById('parent'); pa.addEventListener('click', handler, false); let son = document.getElementById('son'); son.addEventListener('click', handler, false); </script> </body> </html>
使用瀏覽器運行這段代碼,效果以下:
日誌
咱們點擊兒子div,控制檯打印以下:
code
能夠看到第一次打印的target和currentTarget都是son,而第二次事件冒泡到了parent,此時target是son,currentTarget變成了parent。htm
咱們把代碼中的useCapture改成true:blog
let pa = document.getElementById('parent'); pa.addEventListener('click', handler, true); let son = document.getElementById('son'); son.addEventListener('click', handler, true);
而後再次運行,結果如圖:
事件
此時事件實在捕獲階段執行,也就是說會先觸發parent的click事件。圖片
仔細看前面的打印信息就知道了,target始終不變,它表明觸發事件的那個元素(無論是冒泡階段仍是捕獲階段都是指最底層的元素(這裏指son)。而currentTarget則表示當前階段註冊了EventListener的元素。
文檔參考: event.stopPropagation
API用法:
event.stopPropagation()
修改咱們的代碼,在handler中加入event.stopPropagation():
function handler(event) { console.log('target: ', event.target); console.log('curtrentTarget: ', event.currentTarget); event.stopPropagation(); }
再次運行,點擊兒子div,打印出來的日誌以下(冒泡階段):
捕獲階段打印日誌:
能夠看到,冒泡階段,點擊事件沒有繼續向上傳播到父元素;捕獲階段,點擊事件沒有繼續向下傳播到子元素。
P.S. 請考慮下在handler方法中,this到底指向target仍是currentTarget呢?