瀏覽器事件是什么:
事件是用戶操作網頁時發生的交互動作,比如 click/move, 事件除了用戶觸發的動作外,還可以是文檔加載,窗口滾動和大小調整。事件被封裝成一個 event 對象,包含了該事件發生時的所有相關信息( event 的屬性)以及可以對事件進行的操作( event 的方法)。
事件觸發的過程是怎樣的
瀏覽器的事件觸發實際上是有三個階段的,首先捕獲,即從根節點開始傳播,一直到目標元素,然后從目標元素開始冒泡,冒泡到根節點。
目前vue不綁定修飾符的話默認都是執行冒泡階段的回調函數,如果父元素也有綁定點擊事件,就會先執行子元素事件,再執行父元素事件。也可以使用capture來指定捕獲階段執行,這樣如果父元素綁定的也是捕獲事件,那就會先執行父元素的回調,再執行子元素的回調。主要是一個執行先后順序的問題
對事件委托的理解
事件委托就是利用了事件冒泡的機制,比如ul下的li,本來我們需要給每個li綁定點擊事件,但是這樣會消耗大量內存,因此我們給ul綁定點擊事件,用戶點擊li的時候,就會冒泡到ul上,執行ul的點擊事件,這時候我們利用event.target來識別實際觸發事件的子元素。這個target身上可以獲取到li的一些屬性,或者當初在li循環的時候就把data-id 定義好,就可以直接用target.dataset.id來獲取點擊的li元素的id
例如:
<ul @click="myEvent($event)"><li :data-id="1">1</li><li :data-id="2">2</li><li :data-id="3">3</li>
</ul>
const myEvent = (event) => {console.log(event.target.dataset.id,'event.target')
}
事件委托的使用場景
大量元素需要綁定的情況吧,無限滾動列表、動態渲染的表格數據,比如數據可能動態生成,越來越多,或者會有一些動態生成的dom元素不好綁定【vue已經不需要手動做事件委托了,Vue的模板語法已優化事件處理機制,直接通過@click綁定到子元素時,Vue會復用事件處理器而非重復創建,因此短列表或靜態內容無需強制使用事件委托】
事件委托的局限性
當然,事件委托也是有局限的。比如 focus、blur 之類的事件沒有事件冒泡機制,所以無法實現事件委托;mousemove、mouseout 這樣的事件,雖然有事件冒泡,但是只能不斷通過位置去計算定位,對性能消耗高,因此也是不適合于事件委托的。
如何阻止事件冒泡
vue中使用.stop修飾符,或者手動調用event.stopPropagation