Javascript:addEventListener(),removeEventListener()和bind()

时间:2017-09-27 19:16:14

标签: javascript jquery

我想添加和事件监听器,我希望事件监听器调用的函数绑定到调用范围,我希望能够在将来的某个任意日期删除监听器。

显而易见的事情不起作用:

function Thing(){
    this.thingINeed = "important!"
}

// the function that does the thing. 
Thing.prototype.handlerFunction = function(e){
    console.log(this.thingINeed)
    e.preventDefault;
}

// do the binding.
window.document.body.addEventListener('click', this.handlerFunction.bind());

// sometime later...this is my best guess. The event listener remains active. 
window.removeEventListener('click', this.handlerFunction.bind());

// this also doesn't work: 
window.removeEventListener('click', this.handlerFunction);

所以我把一些工作的代码鞭打在一起:

function Thing(){
    this.thingINeed = "important!"
}

Thing.prototype.handlerFunction = function(e){
    console.log(this.thingINeed);
    e.preventDefault;
}

// Where the 'magic' happens...
this.boundHandlerFunction = this.handlerFunction.bind(this);

window.document.body.addEventListener('click', this.boundHandlerFunction);

// sometime later...
window.removeEventListener('click', this.boundHandlerFunction);

MDN详细介绍了匹配事件监听器与删除的内容,但没有提到.bind(),我也找不到其他人这样做的例子。没有广泛的评论,代码并不是很明显。

有更好的方法吗?

jQuery事件监听器可以被命名,这使得它们很容易被删除,但这对于vanilla来说是不可能的吗?

感谢。

1 个答案:

答案 0 :(得分:2)

问题可归结为 - Function.prototype.bind返回一个新功能。当您将绑定函数设置为变量并在addEventListenerremoveEventListener中使用它时,它都有效,因为它们都引用相同的函数。第一个代码块不起作用,因为它们引用了不同的函数。这是一个人为的例子:

function foo () {}

// does not work because foo.bind() returns a new function each time
// these functions are not the same object
document.addEventListener('click', foo.bind())
document.removeEventListener('click', foo.bind())

//does work because both reference the same function
var boundFoo = foo.bind()

document.addEventListener('click', boundFoo)
document.removeEventListener('click', boundFoo)

我不太会谈论jQuery如何处理事件,但是在vanilla JS中没有解决这种行为。