以下是演示的完整代码:http://jsfiddle.net/DF2Uw/4/
基本上,我使用FOR
循环生成多个事件侦听器。我生成了多个<selects>
,希望检测onChange事件并返回已更改的特定选择的ID。然而,似乎只有最后一个事件侦听器幸存下来,因为其他事件侦听器没有触发。
对这种行为有什么解释吗?
HTML
<ol id="slots"></ol>
JAVASCRIPT
var slotnameHtml = '';
for (var i = 0; i < 3; i += 1) {
var slotname = document.createElement('select'),
slottime = document.createElement('select'),
slotlist = document.createElement('li');
slotname.innerHTML = slotnameHtml;
slottime.innerHTML = '<optgroup><option value="1">00:01</option><option value="2">00:02</option></optgroup>';
slottime.id='test'+i;
slotlist.appendChild(slotname);
slotlist.appendChild(slottime);
document.getElementById('slots').appendChild(slotlist);
slottime.addEventListener('change', function () {
alert(slottime.id)
});;
}
这是因为绑定到change
的处理程序不会立即运行,而是稍后运行。同时,for
循环已经运行,slottime
已经反弹到其最终值(您创建的最后一个<select>
元素)。所有处理程序将只看到该值。
您可以引入一个闭包,以便处理程序可以访问正确的元素:
document.getElementById("slots").appendChild(slotlist);
(function(slottime) {
slottime.addEventListener("change", function() {
alert(slottime.id);
});
})(slottime);
正如Teemu在评论中所说,最简单的解决方案是利用this
绑定到处理程序内的目标元素的事实:
slottime.addEventListener("change", function() {
alert(this.id);
});
您必须使用以下警报参数:
alert(this.getAttribute('id'));