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

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

el.addEventListener("click", handle, false);
el.addEventListener("click", handle, false);

но если я хочу передать ему свои аргументы, он зарегистрируется и выстрелит дважды.

el.addEventListener("click", function() { handle(event, myArgument); }, false);
el.addEventListener("click", function() { handle(event, myArgument); }, false);

вопрос в том, почему и какое решение?

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

Я сделал основную анонимную функцию или закрытие, а затем более продвинутую версию, которая показана ниже, но она работала.

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

здесь код:

<html>
    <head>
        <script type="text/javascript">
            var handle_2 = function(evt, type) {
                var test;
                switch (type) {
                    case "focus": 
                        console.log(evt.target.value);
                        break;
                    case "click":
                        console.log(evt.target.id + " was clicked");
                        break;
                    default: console.log("no type found");
                }
            };

            window.onload = function() {
                var textbox = document.getElementById("t1");
                var button = document.getElementById("btn");
                textbox.value = "456";
                button.value = "Press";

                var typeFocus = "focus", typeClick = "click";

                textbox.addEventListener("focus", (function(typeFocus) { return function(evt) { handle_2(evt, typeFocus); }})(typeFocus), false);
                button.addEventListener("click", (function(typeClick) { return function(evt) { handle_2(evt, typeClick); }})(typeClick), false);

                // Registers again for each element. Why?
                textbox.addEventListener("focus", (function(typeFocus) { return function(evt) { handle_2(evt, typeFocus); }})(typeFocus), false);
                button.addEventListener("click", (function(typeClick) { return function(evt) { handle_2(evt, typeClick); }})(typeClick), false);
            };
        </script>
    </head>
    <body>
        <div id="wrapper">
            <input id="t1" type="text" />
            <input id="btn" type="button" />
        </div>
    </body>
</html>

любая помощь будет оценили. Спасибо.

3 ответов


самое простое решение-создать новый обработчик только один раз:

var newHandle = function(event) { handle(event, myArgument); };

el.addEventListener("click", newHandle, false);
el.addEventListener("click", newHandle, false);

Ну,

el.addEventListener("click", handle, false);
el.addEventListener("click", handle, false);

регистрируется в той же функции " handle ()"

el.addEventListener("click", function() { handle(event, myArgument); }, false);
el.addEventListener("click", function() { handle(event, myArgument); }, false);

регистры " function () {handle (event, myArgument)"... это две уникальные анонимные функции. Таким образом, он выстрелит дважды.

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

el.addEventListener("click", crateHandle(myArgument), false);

var createHandle = function(myArgument) {
  return function(event) {
    .... do something
  };
}

Он по-прежнему не решает проблему огня дважды хотя.


addEventListener регистрирует столько слушателей, сколько используется.

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