情况有点像
var someVar = some_other_function();
someObj.addEventListener("click", function(){
some_function(someVar);
}, false);
问题是someVar的值在addEventListener的侦听器函数中是不可见的,在addEventListener中它可能被视为一个新变量。
情况有点像
var someVar = some_other_function();
someObj.addEventListener("click", function(){
some_function(someVar);
}, false);
问题是someVar的值在addEventListener的侦听器函数中是不可见的,在addEventListener中它可能被视为一个新变量。
当前回答
下面的代码为我工作良好(firefox):
for (var i=0; i<3; i++) {
element = new ... // create your element
element.counter = i;
element.addEventListener('click', function(e){
console.log(this.counter);
... // another code with this element
}, false);
}
输出:
0
1
2
其他回答
其他替代方法,可能没有bind的使用那么优雅,但它对于循环中的事件是有效的
for (var key in catalog){
document.getElementById(key).my_id = key
document.getElementById(key).addEventListener('click', function(e) {
editorContent.loadCatalogEntry(e.srcElement.my_id)
}, false);
}
它已经测试了谷歌chrome扩展和可能e.srcElement必须替换为e.srcElement在其他浏览器
我发现这个解决方案使用Imatoria发布的评论,但我不能标记为有用的,因为我没有足够的声誉:D
完美的解决方案是使用闭包,像这样:
function makeSizer(size) { return function () { document.body.style.fontSize = `${size}px`; }; } //pass parameters here and keep the reference in variables: const size12 = makeSizer(12); const size24 = makeSizer(24); const size36 = makeSizer(36); document.getElementById('size-12').addEventListener("click", size12); document.getElementById('size-24').addEventListener("click", size24); document.getElementById('size-36').addEventListener("click", size36); document.getElementById('remove-12').addEventListener("click", ()=>{ document.getElementById('size-12').removeEventListener("click", size12); alert("Now click on 'size 12' button and you will see that there is no event listener any more"); }); test<br/> <button id="size-12"> size 12 </button> <button id="size-24"> size 24 </button> <button id="size-36"> size 36 </button> <button id="remove-12"> remove 12 </button>
因此,基本上你将一个函数包装在另一个函数中,并将其分配给一个变量,你可以注册为事件侦听器,但也可以取消注册!
这个问题很老了,但我想我可以使用ES5的.bind()为后代提供一个替代方案。:)
function some_func(otherFunc, ev) {
// magic happens
}
someObj.addEventListener("click", some_func.bind(null, some_other_func), false);
请注意,您需要设置listener函数,将第一个参数作为传递给bind(您的另一个函数)的参数,第二个参数现在是事件(而不是第一个,因为它本来就是)。
可能不是最优的,但对于那些不精通js的人来说已经足够简单了。将调用addEventListener的函数放到它自己的函数中。通过这种方式,传递给它的任何函数值都保持自己的作用域,并且您可以尽可能多地迭代该函数。
示例我与文件读取,因为我需要捕捉和渲染图像和文件名的预览。在使用多文件上传类型时,我花了一段时间来避免异步问题。尽管上传了不同的文件,我还是会意外地在所有渲染中看到相同的“名称”。
最初,所有的readFile()函数都在readFiles()函数中。这导致了异步作用域问题。
function readFiles(input) {
if (input.files) {
for(i=0;i<input.files.length;i++) {
var filename = input.files[i].name;
if ( /\.(jpe?g|jpg|png|gif|svg|bmp)$/i.test(filename) ) {
readFile(input.files[i],filename);
}
}
}
} //end readFiles
function readFile(file,filename) {
var reader = new FileReader();
reader.addEventListener("load", function() { alert(filename);}, false);
reader.readAsDataURL(file);
} //end readFile
另一种解决方法是使用数据属性
function func(){
console.log(this.dataset.someVar);
div.removeEventListener("click", func);
}
var div = document.getElementById("some-div");
div.setAttribute("data-some-var", "hello");
div.addEventListener("click", func);
斯菲德尔