如何在不破坏removeEventListener的情况下将self(this)传递给addEventListener?

时间:2016-02-24 15:49:23

标签: javascript

我在此处将checkboxchange事件添加到复选框。 (moveButton是一个复选框,因为我正在使用CSS复选框hack)

var self = this;
this.moveButton.addEventListener("change", function(e){self.toggleMove(e, self)});

如果选中该复选框,则会将eventListener添加到body.document

DR.prototype.toggleMove = function(e, self){
    if(self.moveButton.checked){
        document.body.addEventListener("click", function bodyEvent(e){self.removeableEventHandler(e, self)}, false);
    }else{
        console.log("unchecked");
        document.body.removeEventListener("click",  function bodyEvent(e){self.removeableEventHandler(e, self)}, false);
    }
}

如果我没有在函数中包装self.removeableEventHandler我无法将self附加到函数中,但是当我将其包装在函数中时,我将无法在取消选中该复选框时删除该事件。

DR.prototype.removeableEventHandler = function(e, self){
            console.log(e.clientX, e.clientY);
            self.ele.style.top = e.clientY + "px"; 
            self.ele.style.left = e.clientX + "px"; 
};

所以看起来好像我在这里有一点范围难题。不知道如何解决它。我在选中复选框时尝试使表单可移动,然后在未选中复选框时删除移动事件。

2 个答案:

答案 0 :(得分:1)

removeEventListener callbak函数需要引用与addEventListener中相同的函数,试试这个:

function bodyEvent(e) {
    self.removeableEventHandler(e, self);
}
DR.prototype.toggleMove = function(e, self) {
    if (self.moveButton.checked) {
        document.body.addEventListener("click", bodyEvent, false);
    } else {
        console.log("unchecked");
        document.body.removeEventListener("click", bodyEvent, false);
    }
};

答案 1 :(得分:1)

DR.prototype.toggleMove = (function () { var boundBodyEvent; function bodyEvent(e) { this.removeableEventHandler(e); } return function (e) { if (this.moveButton.checked) { boundBodyEvent= bodyEvent.bind(this); document.body.addEventListener("click", boundBodyEvent, false); } else { document.body.removeEventListener("click", boundBodyEvent, false); } }; }()); 通过传递原始函数引用。如果你传递副本就行不通。

你可以这样做:

self

我认为你不需要通过bind,这对我来说似乎很奇怪。我正在使用this覆盖bodyEvent中的DR来引用您的bodyEvent实例而不是DOM元素。

我也使用立即调用来避免将DR.prototype.init = function () { var self = this; document.body.addEventListener("click", function (e) { if (self.moveButton.checked) { self.removeableEventHandler(e); } }, false); } 放在全局范围内。

或者,你也可以不打扰删除事件监听器并在事件监听器中有一个开关:

{{1}}