我正在尝试在我的项目中有一个基于class.prototype的类,在那里我没有内联函数。考虑到这个例子,不可能删除myVideo
视频对象上的eventListener,我在类中有这个对象。
这是一个理论示例,而不是我的实际生产代码
var myClass = function () {
this.initialize();
}
MyClass.prototype.myVideo = null;
MyClass.prototype.initialize = function () {
this.myVideo = document.getElementById("myVideo");
this.myVideo.addEventListener("ended", this.onMyVideoEnded, false);
this.myVideo.play();
}
MyClass.prototype.onMyVideoEnded = function (event) {
// cannot remove event listener here
// this.myVideo.removeEventListener("ended", this.onMyVideoEnded, false);
}
有没有办法将处理程序保留为Class.prototype函数,并添加和删除侦听器。我需要实例化和创建很多这种类型的对象,并且在保留匿名函数作为事件处理程序时,我担心内存泄漏和对象持久性(所有以前创建的对象都会收到"结束"事件)。
或者我应该考虑一种不同的方法(内联函数,在初始化函数内部,作为事件处理程序)。这些确实会影响可读性和一致性,所以我想不惜一切代价避免它们。
您需要将函数onMyVideoEnded
与附加它的上下文绑定:
例如:
this.myVideoEndedHandler = this.onMyVideoEnded.bind(this);
this.myVideo.addEventListener("ended", this.myVideoEndedHandler, false);
要删除侦听器,还可以使用存储处理程序:
this.myVideo.removeEventListener("ended", this.myVideoEndedHandler, false);
这是因为当事件触发函数onMyVideoEnded
时,会得到错误的this
参数。
我使用这个:
this.element.handler = handler.bind(this);
this.element.removeEventListener('event', this.element.handler, false);
this.element.addEventListener('event', this.element.handler, false);
或者使用WeakMap对象:
var handlers = new WeakMap();
var self = this;
handlers.set(this.element, { handler: handler.bind(self) });
var handler = handlers.get(this.element).handler;
this.element.removeEventListener('event', handler, false);
this.element.addEventListener('event', handler, false);