2012-09-19 3 views
3

У меня есть список объектов, каждый из которых имеет .bullet, который является SPAN. Я хочу привязать клик по пролету к обработчику, чем выполнить определенное действие на span с помощью jQuery. Я вижу какое-то поведение, которое я не понимаю, поэтому я надеюсь, что кто-то сможет объяснить, что происходит. В основном, это первый пример кода работы:Закрытие JavaScript для обработчика событий jQuery

for (var i = 0 ; i< length ; i++) { 

      (function(){ 
       dataNode = dataNodeList[i]; 

       var handler = function(e) { 

        e.data.node.bullet.firstChild.nodeValue = "- "; 


       }; 


       $(dataNode.bullet).on("click",{node:dataNode},handler); 


      })(); 

     } 

Однако этот второй вариант не работает:

for (var i = 0 ; i< length ; i++) { 

      (function(){ 
       dataNode = dataNodeList[i]; 

       var handler = function() { 

        dataNode.bullet.firstChild.nodeValue = "- "; 


       }; 


       $(dataNode.bullet).on("click",handler); 


      })(); 

     } 

В этом втором примере,

dataNode.bullet.firstChild.nodeValue = "- "; 

не оказывает никакого влияния на величину SPAN, который я планировал. Я ожидал, что dataNode.bullet все равно укажет на SPAN, который я хочу изменить из-за закрытия JavaScript. Итак, может кто-нибудь объяснить, почему это не удается? Благодарю.

+0

Две вещи: объявить «dataNode» в этой функции с помощью «var» и передать «i» этой вызываемой функции в цикле. (Конечно, добавьте «i» в свой список параметров.) – Pointy

+0

Возможный дубликат [Назначить обработчики кликов в цикле цикла] (http://stackoverflow.com/questions/4091765/assign-click-handlers-in-for-loop) - это очень распространенная проблема, поскольку природа поведения не очевидна. – Pointy

+0

Ах. Спасибо за указание, что я забыл объявить переменную внутри цикла. –

ответ

6

Попробуйте это:

for (var i = 0 ; i< length ; i++) { 
    (function(index){ 
     var dataNode = dataNodeList[index]; 

     var handler = function() { 
      dataNode.bullet.firstChild.nodeValue = "- "; 
     }; 

     $(dataNode.bullet).on("click",handler); 
    })(i); 
} 

Замыкание определяет новую область. Это необходимо, потому что ваш обработчик не вызывается до тех пор, пока цикл не завершится, поэтому i не является частью области действия в момент ее вызова или (в некоторых случаях) имеет последнее возможное значение из цикла.

+0

А, спасибо @Pointy – Shmiddty

+0

Это, похоже, решило главную проблему. Теперь, по крайней мере dataNode.bullet, кажется, указывает на правый элемент span. Спасибо за это. Однако я вижу еще одну проблему. dataNode.bullet.firstChild.nodeValue = "-" загадочно просто удаляет содержимое диапазона. Однако, если я сразу же последую этому примеру с строкой для прокрутки, то появятся оба изменения. Я не уверен, связано ли это с исходной проблемой или нет. –

+0

Не могли бы вы объяснить, почему нужно было поместить параметр index в анонимную функцию? Я не понимаю концептуально, почему это изменило бы ситуацию, и с важным отличием деляризации dataNode внутри функции мой код работает без этого индексного параметра. –

Смежные вопросы