我正在尝试执行以下操作:
我有一组图像和选择(下拉)HTML元素,每个元素30个。我正在尝试在1到30的循环上使用AddEventListener,这样当我更改select的值时,图像src会更新(并且图像会更改)。
AddEventListener函数就是这个:
function AddEventListener(element, eventType, handler, capture)
{
if (element.addEventListener)
element.addEventListener(eventType, handler, capture);
else if (element.attachEvent)
element.attachEvent("on" + eventType, handler);
}
我试过这个并且有效:
var urlfolderanimalimages = "http://localhost/animalimages/";
var testselect = "sel15";
var testimg = "i15";
AddEventListener(document.getElementById(testselect), "change", function(e) {
document.getElementById(testimg).src = urlfolderanimalimages + document.getElementById(testselect).value;
document.getElementById(testimg).style.display = 'inline';
if (e.preventDefault) e.preventDefault();
else e.returnResult = false;
if (e.stopPropagation) e.stopPropagation();
else e.cancelBubble = true;
}, false);
但后来我尝试在循环中调用它并且它不起作用。该事件已添加,但当我更改任何选择时,它将更新最后一个(ID为i30的图像)。
var urlfolderanimalimages = "http://localhost/animalimages/";
for (k=1;k<=30;k++) {
var idselect = "sel" + k;
var idimage = "i" + k;
AddEventListener(document.getElementById(idselect), "change", function(e) {
document.getElementById(idimage).src = urlfolderanimalimages + document.getElementById(idselect).value;
document.getElementById(idimage).style.display = 'inline';
if (e.preventDefault) e.preventDefault();
else e.returnResult = false;
if (e.stopPropagation) e.stopPropagation();
else e.cancelBubble = true;
}, false);
}
我做错了什么?我是JavaScript(以及一般编程)的新手,对于引起呕吐的代码感到抱歉:(
答案 0 :(得分:8)
问题是你正在“关闭”相同的变量。
var未声明变量 1 。它只是为给定执行上下文中的标识符注释“停止查找”。
请参阅Javascript Closures "FAQ Notes"了解所有详细信息。 “执行上下文”和“范围链”部分最有趣。
常见习语是执行双重绑定以创建新的执行上下文。
E.g。
var k
for (k = 1; k < 10; k++) {
setTimeout((function (_k) {
return function () {
alert(_k)
}
})(k), k * 100)
}
从JavaScript第5版开始,有Function.bind
(它也可以在第3版中实现,例如bind from prototype.js),可以这样使用:
var k
for (k = 1; k < 10; k++) {
setTimeout((function () {
alert(this)
}).bind(k), k * 100)
}
1 此构造 在ECMAScript规范中称为变量声明。然而,这一陈述虽然可能被视为具有误导性,但强调要提出一个观点:另见“变量提升”。
答案 1 :(得分:1)
我也在http://meshfields.de/event-listeners-for-loop/找到了这个解决方案:
var myArr = [0,1,2,3];
for (var i = 0; i < myArr.length; i+=1) {
(function (i) {
document.getElementById('myDOMelement' myArr[i]).onclick = function () {
if (window.console.firebug !== undefined) {
console.log('myDOMelement' myArr[i]);
}
else {
alert('myDOMelement' myArr[i]);
}
};
}) (i);
}