0

问题:一个事件监听器想要将自己从目标监听器列表中移除。侦听器可以是匿名函数和/或动态生成(闭包或绑定)

这是一个解决方案(在“严格模式”下不起作用):(“点击”事件的示例)

function(ev){
   // .... some stuff
   ev.target.removeEventListener("click",arguments.callee);
}

但这在 ES5 严格模式下不起作用。

问题:还有其他解决方案吗?

4

4 回答 4

1

只需命名它 - 它甚至适用于函数表达式。

… function myListener(ev){
   // … some stuff
   ev.target.removeEventListener("click", myListener);
} …
于 2017-04-21T13:40:11.667 回答
0

事件绑定适用于每个事件名称的函数(处理程序)实例的注册!

基本上,当您调用 addEventListener 时,您定义了在触发给定命名事件时要调用的函数地址。

因为你使用bind你打破了这个机制,只是因为bind返回了一个新函数(见绑定文档)。

但是,根据我从您的代码中了解到的情况,您正在尝试运行一次事件处理程序(并从事件注册列表中自行分离)。

如果是这样,为什么不告诉addEventListener只运行一次小时处理程序(参见addEventListener文档)?这是一个更简单的代码:

function listener(s,ev){
  "use strict";
  console.log("executing listener once with ", s)
}
window.addEventListener('load', function(){
  i = document.querySelector('input');
  i.addEventListener("change",listener.bind(i,"abc"), {once:true});
  i.addEventListener("change",listener.bind(i,"def"), {once:true});
});

你可以在这里测试它:https ://jsfiddle.net/rptsrfLz/

于 2017-04-23T07:50:04.307 回答
0

当您通过 addEventListener 添加事件侦听器时,您可以通过命名函数来完成,以便您有参考。

于 2017-04-21T13:40:28.660 回答
0

感谢您的回答评论。

例如,在使用闭包模式时,命名函数是一种解决方案。但不适用于有界函数:函数名引用原始函数,而不是有界实例。

一些例子:

function listener(s,ev){
  "use strict";
  if (ev.target.value == s){
    console.log("<bounded> I found " + s+ ", Bye !");
    // Doesn't work : listener references original (not bounded) function
    ev.target.removeEventListener(ev.type, listener);
    // Who am I ?? ;-)
  } else {
    console.log("<bounded> still waiting for " +s + " " + new Date());
  }
}
window.addEventListener('load', function(){
  i = document.querySelector('input');
  i.addEventListener("change",listener.bind(i,"abc"));
  i.addEventListener("change",listener.bind(i,"def"));
});

我写了这个丑陋的解决方法:

function autoRefBind(f, ...args){
  var o = {};
  o.me = f.bind(o,...args);
  return o.me;
}
function listener(s,ev){
  "use strict";
  if (ev.target.value == s){
    console.log("<bounded> I found " + s+ ", Bye !");
    ev.target.removeEventListener(ev.type, this.me);
  } else {
    console.log("<bounded> still waiting for " +s + " " + new Date());
  }
}
window.addEventListener('load', function(){
  i = document.querySelector('input');
  i.addEventListener("change",autoRefBind(listener,"abc"));
  i.addEventListener("change",autoRefBind(listener,"def"));
});

但它非常......丑陋:“这个”必须是这个“愚蠢”的对象{我:}

于 2017-04-23T06:50:22.190 回答