#javascript #html #events #onclick
#javascript #HTML #Мероприятия #onclick
Вопрос:
В html есть 16 полей.
<div id="box-container">
<div class="box" data-coord="0:0" style="clear: left"></div> <div class="box" data-coord="0:1"></div> <div class="box" data-coord="0:2"></div> <div class="box" data-coord="0:3"></div>
<div class="box" data-coord="1:0" style="clear: left"></div> <div class="box" data-coord="1:1"></div> <div class="box" data-coord="1:2"></div> <div class="box" data-coord="1:3"></div>
<div class="box" data-coord="2:0" style="clear: left"></div> <div class="box" data-coord="2:1"></div> <div class="box" data-coord="2:2"></div> <div class="box" data-coord="2:3"></div>
<div class="box" data-coord="3:0" style="clear: left"></div> <div class="box" data-coord="3:1"></div> <div class="box" data-coord="3:2"></div> <div class="box" data-coord="3:3"></div>
</div>
Я хочу написать js-код, который будет выполнять следующее:
Когда я нажимаю на любое поле, оно выдает предупреждение о номере заказа от 1 до 16.
Ниже приведен мой js-код:
<script type="text/javascript">
var boxArray = document.getElementsByClassName("box");
for (var i = 0; i < boxArray.length; i ) {
boxArray[i].onclick = function () {
var say = function (i) {
alert(i);
};
say(i);
}
}
</script>
Но каждый раз оно предупреждает 16.
В чем проблема?
Не могли бы вы мне помочь, пожалуйста?
Ответ №1:
Используя классическое выражение функции IIFE: немедленного вызова, вы можете написать:
var boxArray = document.getElementsByClassName("box");
for (var i = 0; i < boxArray.length; i ) {
boxArray[i].onclick = (function (i) {
return function (e) {
var say = function (i) {
alert(i);
};
say(i);
};
})(i);
}
<div id="box-container">
<div class="box" data-coord="0:0" style="clear: left">1</div> <div class="box" data-coord="0:1">2</div> <div class="box" data-coord="0:2">3</div> <div class="box" data-coord="0:3">4</div>
<div class="box" data-coord="1:0" style="clear: left">5</div> <div class="box" data-coord="1:1">6</div> <div class="box" data-coord="1:2">7</div> <div class="box" data-coord="1:3">8</div>
<div class="box" data-coord="2:0" style="clear: left">9</div> <div class="box" data-coord="2:1">10</div> <div class="box" data-coord="2:2">11</div> <div class="box" data-coord="2:3">12</div>
<div class="box" data-coord="3:0" style="clear: left">13</div> <div class="box" data-coord="3:1">14</div> <div class="box" data-coord="3:2">15</div> <div class="box" data-coord="3:3">16</div>
</div>
Ответ №2:
Это связано с областью действия javascript. i
выходит за рамки цикла for, потому что вы использовали var
, поэтому, когда вы это делаете alert(i)
, оно принимает значение, которое i
остается после цикла (поскольку цикл уже запущен).
Измените цикл for с
for (var i = 0; i < boxArray.length; i )
Для
for (let i = 0; i < boxArray.length; i )
И это должно решить вашу проблему.
Ответ №3:
Вы можете использовать addEventListener
с локальной объявленной переменной, например, так
var boxArray = document.getElementsByClassName("box");
for (var i = 0; i < boxArray.length; i ) {
boxArray[i].addEventListener('click', (function(e) {
var num = i;
return function() {
alert(num);
}
})());
}
<div id="box-container">
<div class="box" data-coord="0:0" style="clear: left">1</div>
<div class="box" data-coord="0:1">2</div>
<div class="box" data-coord="0:2">3</div>
<div class="box" data-coord="0:3">4</div>
<div class="box" data-coord="1:0" style="clear: left">5</div>
<div class="box" data-coord="1:1">6</div>
<div class="box" data-coord="1:2">7</div>
<div class="box" data-coord="1:3">8</div>
</div>
Ответ №4:
Вы можете сделать это намного проще, если используете jQuery .index()
Это так же просто, как сделать это:
$(".box").click(function(){
var i = $(this).index();
alert(i);
});
ДЕМОНСТРАЦИЯ: http://jsbin.com/zoxirafufo/edit?html ,js, консоль, вывод