Как передать аргументы функции прослушивателя addEventListener?

ситуация чем-то вроде-

var someVar = some_other_function();
someObj.addEventListener("click", function(){
    some_function(someVar);
}, false);

проблема в том, что значение someVar не отображается внутри функции прослушивателя addEventListener, где он, вероятно, рассматривается как новая переменная.

22 ответов


нет абсолютно ничего плохого в коде, который вы написали. Оба!--2--> и someVar должны быть доступны, если они были доступны в контексте, где anonymous

function() { some_function(someVar); } 
.

проверьте, если предупреждение дает вам значение, которое вы искали, убедитесь, что оно будет доступно в области анонимной функции (если у вас нет больше кода, который работает на том же someVar переменная рядом с вызовом addEventListener)

var someVar; 
someVar = some_other_function();
alert(someVar);
someObj.addEventListener("click", function(){
    some_function(someVar);
}, false);

почему бы просто не получить аргументы из целевого атрибута события?

пример:

var someInput = document.querySelector('input');
someInput.addEventListener('click', myFunc, false);
someInput.myParam = 'This is my parameter';
function myFunc(evt)
{
  window.alert( evt.target.myParam );
}

JavaScript-это язык, ориентированный на прототип, помните!


этот вопрос старый, но я думал, что предложу альтернативу, используя ES5 .привязать() - для потомков. :)

function some_func(otherFunc, ev) {
    // magic happens
}
someObj.addEventListener("click", some_func.bind(null, some_other_func), false);

просто имейте в виду, что вам нужно настроить функцию прослушивателя с первым параметром в качестве аргумента, который вы передаете в bind (ваша другая функция), а второй параметр теперь является событием (вместо первого, как это было бы).


вы можете добавлять и удалять eventlisteners с аргументами, объявляя функцию переменной.

myaudio.addEventListener('ended',funcName=function(){newSrc(myaudio)},false);

newSrc метод с myaudio в качестве параметра funcName - имя функции, переменной

вы можете удалить слушателя myaudio.removeEventListener('ended',func,false);


довольно и старый вопрос, но у меня была та же проблема сегодня. Самое чистое решение, которое я нашел, - использовать концепцию каррирование.

код:

someObj.addEventListener('click', some_function(someVar));

var some_function = function(someVar) {
    return function curried_func(e) {
        // do something here
    }
}

называя функцию curried, она позволяет вызывать объект.removeEventListener для отмены регистрации eventListener в более позднее время выполнения.


вы можете передать somevar по значению (не по ссылке) через функцию javascript, известную как закрытие:

var someVar='origin';
func = function(v){
    console.log(v);
}
document.addEventListener('click',function(someVar){
   return function(){func(someVar)}
}(someVar));
someVar='changed'

или вы можете написать общую функцию wrap, такую как wrapEventCallback:

function wrapEventCallback(callback){
    var args = Array.prototype.slice.call(arguments, 1);
    return function(e){
        callback.apply(this, args)
    }
}
var someVar='origin';
func = function(v){
    console.log(v);
}
document.addEventListener('click',wrapEventCallback(func,someVar))
someVar='changed'

здесь wrapEventCallback(func,var1,var2) как:

func.bind(null, var1,var2)

someVar значение должно быть доступно только в some_function() контекста, а не от слушателя. Если вы хотите иметь его в слушателе, вы должны сделать что-то вроде:

someObj.addEventListener("click",
                         function(){
                             var newVar = someVar;
                             some_function(someVar);
                         },
                         false);

и использовать .

другой способ-вернуться someVar значение some_function() для дальнейшего использования в прослушивателе (как новый локальный var):

var someVar = some_function(someVar);

вот еще один способ (Этот работает внутри для циклов):

var someVar = some_other_function();
someObj.addEventListener("click", 

function(theVar){
    return function(){some_function(theVar)};
}(someVar),

false);

вы можете просто связать все необходимые аргументы с помощью 'bind':

root.addEventListener('click', myPrettyHandler.bind(null, event, arg1, ... ));

таким образом, вы всегда получите событие, arg1 и другие вещи, переданные myPrettyHandler.

http://passy.svbtle.com/partial-application-in-javascript-using-bind


использовать

   el.addEventListener('click',
    function(){
        // this will give you the id value 
        alert(this.id);    
    },
false);

и если вы хотите передать любое пользовательское значение в эту анонимную функцию, то самый простой способ сделать это -

 // this will dynamically create property a property
 // you can create anything like el.<your  variable>
 el.myvalue = "hello world";
 el.addEventListener('click',
    function(){
        //this will show you the myvalue 
        alert(el.myvalue);
        // this will give you the id value 
        alert(this.id);    
    },
false);

прекрасно работает в моем проекте. Надеюсь, это поможет


также попробуйте эти (IE8 + Chrome. Я не знаю для FF):

function addEvent(obj, type, fn) {
    eval('obj.on'+type+'=fn');
}

function removeEvent(obj, type) {
    eval('obj.on'+type+'=null');
}

// Use :

function someFunction (someArg) {alert(someArg);}

var object=document.getElementById('somObject_id') ;
var someArg="Hi there !";
var func=function(){someFunction (someArg)};

// mouseover is inactive
addEvent (object, 'mouseover', func);
// mouseover is now active
addEvent (object, 'mouseover');
// mouseover is inactive

надеюсь, что нет опечаток :-)


один из способов-сделать это с внешняя функция:

elem.addEventListener('click', (function(numCopy) {
  return function() {
    alert(numCopy)
  };
})(num));

этот метод обертывания анонимной функции в круглые скобки и вызова ее сразу называется жизнь (Сразу Же Вызывается Функция-Выражение)

вы можете проверить пример с двумя параметрами вhttp://codepen.io/froucher/pen/BoWwgz.

catimg.addEventListener('click', (function(c, i){
  return function() {
    c.meows++;
    i.textContent = c.name + '\'s meows are: ' + c.meows;
  }
})(cat, catmeows));


отправка аргументов функции обратного вызова eventListener требует создания изолированной функции и передачи аргументов этой изолированной функции.

вот хорошая маленькая вспомогательная функция, которую вы можете использовать. На основе примера "hello world" выше.)

одна вещь, которая также необходима, - это поддерживать ссылку на функцию, чтобы мы могли удалить прослушиватель чисто.

// Lambda closure chaos.
//
// Send an anonymous function to the listener, but execute it immediately.
// This will cause the arguments are captured, which is useful when running 
// within loops.
//
// The anonymous function returns a closure, that will be executed when 
// the event triggers. And since the arguments were captured, any vars 
// that were sent in will be unique to the function.

function addListenerWithArgs(elem, evt, func, vars){
    var f = function(ff, vv){
            return (function (){
                ff(vv);
            });
    }(func, vars);

    elem.addEventListener(evt, f);

    return f;
}

// Usage:

function doSomething(withThis){
    console.log("withThis", withThis);
}

// Capture the function so we can remove it later.
var storeFunc = addListenerWithArgs(someElem, "click", doSomething, "foo");

// To remove the listener, use the normal routine:
someElem.removeEventListener("click", storeFunc);

Я застрял в этом, поскольку я использовал его в цикле для поиска элементов и добавления к нему listner. Если вы используете его в цикле, то это будет работать отлично

for (var i = 0; i < states_array.length; i++) {
     var link = document.getElementById('apply_'+states_array[i].state_id);
     link.my_id = i;
     link.addEventListener('click', function(e) {   
        alert(e.target.my_id);        
        some_function(states_array[e.target.my_id].css_url);
     });
}

    var EV = {
        ev: '',
        fn: '',
        elem: '',
        add: function () {
            this.elem.addEventListener(this.ev, this.fn, false);
        }
    };

    function cons() {
        console.log('some what');
    }

    EV.ev = 'click';
    EV.fn = cons;
    EV.elem = document.getElementById('body');
    EV.add();

//If you want to add one more listener for load event then simply add this two lines of code:

    EV.ev = 'load';
    EV.add();

следующий подход работал хорошо для меня. Изменено из здесь.

function callback(theVar) {
  return function() {
    theVar();
  }
}

function some_other_function() {
  document.body.innerHTML += "made it.";
}

var someVar = some_other_function;
document.getElementById('button').addEventListener('click', callback(someVar));
<!DOCTYPE html>
<html>
  <body>
    <button type="button" id="button">Click Me!</button>
  </body>
</html>

следующий ответ правильный, но приведенный ниже код не работает в IE8, если предположим, что вы сжали файл js с помощью yuicompressor. (На самом деле, все еще большинство народов США используют IE8)

var someVar; 
someVar = some_other_function();
alert(someVar);
someObj.addEventListener("click",
                         function(){
                          some_function(someVar);
                         },
                         false);

Итак, мы можем исправить эту проблему как следует, и она отлично работает во всех браузерах

var someVar, eventListnerFunc;
someVar = some_other_function();
eventListnerFunc = some_function(someVar);
someObj.addEventListener("click", eventListnerFunc, false);

надеюсь, это будет полезно для тех, кто сжимает файл js в рабочей среде.

Удачи!!


внутри всех функций есть специальная переменная:аргументы. Вы можете передать свои параметры в качестве анонимных параметров и получить к ним доступ (по заказу) через аргументы переменной.

пример:

var someVar = some_other_function();
someObj.addEventListener("click", function(someVar){
    some_function(arguments[0]);
}, false);

следующий код отлично работал для меня (firefox):

for (var i=0; i<3; i++) {
   element = new ...   // create your element
   element.counter = i;
   element.addEventListener('click', function(e){
        console.log(this.counter);
        ...            // another code with this element
   }, false);
}

выход:

0
1
2

вам нужно:

newElem.addEventListener('click', {
    handleEvent: function (event) {
        clickImg(parameter);
    }
});

другая альтернатива, возможно, не такая элегантная, как использование bind, но она действительна для событий в цикле

for (var key in catalog){
    document.getElementById(key).my_id = key
    document.getElementById(key).addEventListener('click', function(e) {
        editorContent.loadCatalogEntry(e.srcElement.my_id)
    }, false);
}

Он был протестирован для расширений google chrome и, возможно, e.srcElement должен быть заменен на e.источник в других браузерах

Я нашел это решение, используя комментарий сообщение от Imatoria но я не могу отметить его как полезный, потому что у меня недостаточно репутации: D