Событие onClick в цикле For

Я попытался создать цикл с параметром for и increment по событию onclick, но он не работает.

Часть js:

 var gameCase = ['', '', '', '', '', '', '', '', ''], // 9
    itemLists = $('game').getElementsByTagName('li'); // 9 items

    for( var i = 0; i < itemLists.length; i++ ) {
         // i already egal to 9
         itemLists[i].onclick = function() {
              // do something
         }
    }

Но в этом случае цикл For уже завершен, прежде чем я смог щелкнуть элемент списка.

Кроме того, я хотел бы получить список элементов, которые я нажал, и сохранить его в массиве. Я попробовал gameCase [this] (в функции onclick), но я не знаю, хорошо ли это.

Ответ 1

Джон Ресиг очень хорошо освещает эту тему в "Секретах JavaScript-ниндзя" (http://ejohn.org/apps/learn/#59)

Вам нужно создать временную область для сохранения значения i

for ( var i = 0; i < itemLists.length; i++ ) (function(i){ 
  itemLists[i].onclick = function() {
      // do something
  }
})(i);

Edit:

var gameCase = ['', '', '', '', '', '', '', '', ''], // 9
$listParent = $('game').find('ul'), // li parent
itemLists = $('game').getElementsByTagName('li'); // 9 items

var listHandler = (function() {
  var i = 0;

  return function() {
    // $(this) will in here refer to the clicked li
    i++ // increment i

    if ( i === 9 ) {
      $listParent.off('click', 'li', listHandler); //remove eventhandler when i reaches 9
    }
  }
}());

$listParent.on('click', 'li', listHandler); // attach eventhandler to ul element

Это должно делать то, что вы хотите, не можете проверить его прямо сейчас, так как я на работе.

Ответ 2

Оберните слушателя:

onclick = (function(i) {return function() {
    ...
};})(i);

Это устраняет проблемы с областью переменной.

Ответ 3

Извините, если я не понял ваш вопрос правильно, Из кода я понимаю, что вы пытаетесь добавить обработчик onclick ко всем элементам списка, найденным в теге игры (возможно, это должен быть класс /id ).

Цикл for будет выполняться, когда тег/файл script загружается без какого-либо взаимодействия с пользователем.

Если вы хотите назначить функцию, которая использует текущее значение счетчика. Используйте следующий код:

itemLists[i].onclick = (function() {
    return function() {
         // TODO ---
        // Your handler code here
}
})();

Ответ 4

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

var gameCase = ['', '', '', '', '', '', '', '', ''], // 9
itemLists = $('game').getElementsByTagName('li'); // 9 items

itemLists.forEach(function(item,index){
    item.onclick = function() {
      // do something
 }
});