簡體   English   中英

無法刪除所有事件偵聽器

[英]Can't remove all event listeners

我正在嘗試從某個網站上刪除事件偵聽器,但沒有成功。

這是來自網站的事件偵聽器:
在此處輸入圖片說明

有一個 javascript 腳本可以創建這些事件:

document.addEventListener('contextmenu', function (ev) {
        ev.preventDefault();
    }
)

我試圖用以下方法刪除它:

document.removeEventListener('contextmenu', function (ev) {
                ev.preventDefault();
            }) 

我也試過:

(getEventListeners(document)).contextmenu = null

但它沒有用,我想是因為我使用了一個不同的新功能。

有沒有辦法清除所有事件?

參考:
無法刪除事件偵聽器

您需要指定綁定到removeEventListener的函數

您可以通過創建一個函數並傳遞對addEventListenerremoveEventListener的引用來做到這一點。

 // create a function function onRightClick(ev) { ev.preventDefault(); console.log('onRightClick') } // pass the function to both add and remove document.addEventListener('contextmenu', onRightClick) document.removeEventListener('contextmenu', onRightClick)

這是一個完整的示例,它將所有事件緩存到元素中,允許您刪除特定事件,所有事件類型的所有事件。

它還有一個 MutationObserver 觀察 DOM 的變化,如果一個元素被移除,那么附加到它的事件也會被移除。

 const Events = (() => { const cache = new Map const observer = new MutationObserver(function(mutations) { for (let mutation of mutations) { if (mutation.type === 'childList') { if (mutation.removedNodes.length) { console.log('element removed from the dom, removing all events for the element') mutation.removedNodes.forEach(x => Events.remove(x)) } } } }) // watch the dom for the element being deleted observer.observe(document.body, { childList: true }) return { add(el, type, fn, capture = false) { let cached = cache.get(el) if (!cached) { cached = {} cache.set(el, cached) } if (!cached[type]) { cached[type] = new Set } cached[type].add(fn) el.addEventListener(type, fn, capture) }, remove(el, type, fn) { const cached = cache.get(el) if (!cached) { return false } // remove all events for an event type if (type && !fn) { cached[type].forEach(fn => { el.removeEventListener(type, fn) }) cached[type] = new Set } // remove a specific event else if (type && fn) { el.removeEventListener(type, fn) // remove the event from the cache cached[type].delete(fn) } // remove all events for the element else { for (key in cached) { cached[key].forEach(fn => { el.removeEventListener(key, fn) }) } cache.delete(el) } }, show(el, type) { const cached = cache.get(el) if (!cached) { return false } if (type) { return cached[type] } return cached } } })() function onRightClick() {} Events.add(document, 'contextmenu', onRightClick) Events.remove(document, 'contextmenu', onRightClick) // remove a specific event callback Events.remove(document, 'contextmenu') // remove specific event types from an element Events.remove(document) // remove all events from an element const testElement = document.querySelector('#test_element') Events.add(testElement, 'click', function deleteSelf(e) { this.parentNode.removeChild(this) })
 <div id="test_element"> when you <strong>click me</strong> I will be deleted from the DOM which will fire the MutationObserver to remove all my events </div>

您可以嘗試克隆已添加所有偵聽器的元素並將其添加回其父元素。 使用cloning ,您會丟失所有附加到元素的偵聽器。 試試這個,

var element = document.getElementById('myElement'),
    clone = el.cloneNode(true);

element.parentNode.replaceChild(clone, element);

但是,這不適用於全局事件偵聽器,或者只是直接在文檔而不是元素上設置的事件偵聽器,因為文檔是層次結構的根(不能有 parentNode)

要擺脫未知的事件偵聽器,您可以clone元素,然后將原始內容移動到克隆的內容中,然后用克隆替換原始內容。

如果您不關心包含元素的事件偵聽器,您還可以使用.clone(true) (或false ,不記得了)深度克隆原始.clone(true) 這樣您就不必移動內容了。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM