简体   繁体   English

使用for循环并传递不同的参数将事件侦听器添加到多个元素

[英]Adding event listener to multiple elements using for loop and passing different parameters

<div id="mydiv0"></div>
<div id="mydiv1"></div>
<div id="mydiv2"></div>


var myArray = [
  document.getElementById("mydiv0"),
  document.getElementById("mydiv1"),
  document.getElementById("mydiv2")
];

function myFunction(x){
  alert("my number is " + x);
}

for(var i = 0; i < myArray.length; i++){
  myArray[i].addEventListener("click", function(){myFunction(i);});
}

I want to attach event listener to each element in myArray. 我想将事件侦听器附加到myArray中的每个元素。 When clicked, an alert message should be displayed showing numbers 0,1 and 2 for mydiv0, mydiv1 and mydiv2 respectively. 单击时,将显示一条警告消息,分别显示mydiv0,mydiv1和mydiv2的数字0、1和2。 I tried using for loop as seen in the example above, but no matter which div I click on, I get "my number is 3" message. 如上例所示,我尝试使用for循环,但是无论我单击哪个div,都会收到“我的号码为3”的消息。 Is there a way to pass the different values of variable i as a parameter of myFunction? 有没有办法将变量i的不同值作为myFunction的参数传递?

You can simply declare the variable in the loop with let instead of var that creates a block scope local variable. 您可以简单地在循环中使用let而不是var声明变量,以创建块作用域局部变量。

 var myArray = [ document.getElementById("mydiv0"), document.getElementById("mydiv1"), document.getElementById("mydiv2") ]; function myFunction(x){ alert("my number is " + x); } for(let i = 0; i < myArray.length; i++){ myArray[i].addEventListener("click", function(){myFunction(i);}); } 
 <div id="mydiv0">Div 0</div> <div id="mydiv1">Div 1</div> <div id="mydiv2">Div 2</div> 

You have to create a isolated scope for click callback. 您必须为点击回调创建一个隔离范围。

for(var i = 0; i < myArray.length; i++){
  (function(i){
    myArray[i].addEventListener("click", function(){myFunction(i);});
  })(i);
}

Use bind : 使用bind

 var myArray = [ document.getElementById("mydiv0"), document.getElementById("mydiv1"), document.getElementById("mydiv2") ]; function myFunction(x){ alert("my number is " + x); } for(var i = 0; i < myArray.length; i++){ myArray[i].addEventListener("click", myFunction.bind(null, i)); } 
 div { height: 20px; width: 200px; border: 1px solid black; } 
 <div id="mydiv0"></div> <div id="mydiv1"></div> <div id="mydiv2"></div> 

Alternatively, you can use data attribute as follows. 另外,您可以如下使用data属性。

<div id="mydiv0" data-value="1"></div>
<div id="mydiv1" data-value="2"></div>
<div id="mydiv2" data-value="3"></div>

for(var i = 0; i < myArray.length; i++){
    myArray[i].addEventListener("click",  function() {
        myFunction(this.getAttribute('data-value'));
    });
}

Just use 'let' instead of 'var' as below : 只需使用“ let”而不是“ var”,如下所示:

for(let i = 0; i < myArray.length; i++){
    myArray[i].addEventListener("click", function(){myFunction(i);});
}

'let' allows you to declare variables that are limited in scope to the block, statement, or expression on which it is used. 'let'允许您声明变量,其作用域仅限于使用它的块,语句或表达式。 This is unlike the 'var' keyword, which defines a variable globally, or locally to an entire function regardless of block scope. 这与'var'关键字不同,该关键字在全局范围内或整个函数本地定义变量,而与块范围无关。

难以将唯一的事件侦听器添加到已创建的<div>通过 for 循环的元素</div><div id="text_translate"><p>我正在做一个项目来学习一些 JavaScript,目标是在单页 web 应用程序中动态提供电子邮件。 应用程序的HTML已经使用createElement JS方法创建。 到目前为止,我已经成功地显示了包含所有电子邮件的“收件箱”页面,如下图所示:</p><p> <a href="https://i.stack.imgur.com/V8cZq.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/V8cZq.png" alt=""></a></p><p> 我目前正在尝试通过使用 addEventListener 使这些单独的电子邮件中的每一个都可以点击。 我遇到的问题是,每当我单击任何一封电子邮件时,都会呈现收件箱中的第一个 email(id:1,主题:测试电子邮件),并且无法查看任何其他电子邮件。</p><p> <a href="https://i.stack.imgur.com/BBjQj.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/BBjQj.png" alt=""></a></p><p> 我可以看到相同的 email.id 被应用到所有创建的 div 的事件侦听器,尽管所有 div 都被正确创建,并包含来自相应电子邮件的所有信息。</p><p> 这是加载邮箱 JS,它呈现收件箱中的所有电子邮件:</p><pre> function load_mailbox(mailbox) { // Show the mailbox and hide other views document.querySelector('#emails-view').style.display = 'block'; document.querySelector('#compose-view').style.display = 'none'; document.querySelector('#single-view').style.display = 'none'; // Show the mailbox name document.querySelector('#emails-view').innerHTML = `<h3>${mailbox.charAt(0).toUpperCase() + mailbox.slice(1)}</h3>`; // GET request fetch(`/emails/${mailbox}`).then(response => response.json()).then(emails => { // Print emails to console console.log(emails); // Iterate through each email for(var i = 0; i < emails.length; i++) { var email = emails[i]; // Create div and append email content to HTML var emaildiv = document.createElement('div'); emaildiv.style.borderStyle = 'solid'; emaildiv.style.borderColor = 'black'; emaildiv.style.borderWidth = '0.1rem'; emaildiv.style.borderRadius = '0'; emaildiv.style.marginBottom = '0.2rem'; emaildiv.style.padding = '0.3rem'; emaildiv.innerHTML = `<b>${email.sender}</b> --- ${email.subject}<br>${email.timestamp}`; // If individual email selected then view email emaildiv.addEventListener('click', () => view_email(email)); // Populate div HTML with emails document.querySelector('#emails-view').append(emaildiv); console.log(email.read); // Colour backgrounds based on whether emails have been read if (email.read == true) { emaildiv.style.backgroundColor = 'lightgrey'; } console.log(email); } });}</pre><p> 这是视图 email JS,它应该渲染个人 email 的 HTML:</p><pre> // View email function view_email(email) { console.log(email.id); // Show the mailbox and hide other views document.querySelector('#emails-view').style.display = 'none'; document.querySelector('#compose-view').style.display = 'none'; document.querySelector('#single-view').style.display = 'block'; // GET request fetch(`/emails/${email["id"]}`).then(response => response.json()).then(email => { // Create div, set class, and append email content to HTML var reademail = document.createElement('div'); reademail.innerHTML = ''; reademail.style.borderStyle = 'solid'; reademail.style.borderColor = 'black'; reademail.style.borderWidth = '0.1rem'; reademail.style.borderRadius = '0'; reademail.style.marginBottom = '0.2rem'; reademail.style.padding = '0.3rem'; reademail.innerHTML = ` <b>From:</b> ${email.sender}<br> <b>To:</b> ${email.recipients}<br> <b>Subject:</b> ${email.subject}<br> <b>Timestamp:</b> ${email.timestamp}<br> <button class="btn btn-sm btn-outline-primary" id="Reply">Reply</button> <hr> ${email.body}`; // Populate div HTML with emails document.querySelector('#single-view').append(reademail); // Mark unread emails as read if (email.read === 'false') { fetch(`/emails/${email}`, { method: 'PUT', body: JSON.stringify({ read: true }) }) } }); }</pre><p> 这是存储在 email GET 响应中的示例(虚拟数据):</p><pre> { "id": 1, "sender": "user@example.com", "recipients": ["user@example.com"], "subject": "Hello,": "body", "Hello, world:", "timestamp": "Oct 24 2020, 12:00 AM", "read": false, "archived": false }</pre><p> 我已经尝试将其他每封电子邮件的 ID 硬编码到视图 email JS 中,并且可以看到该功能按要求工作(显示电子邮件)。</p><p> 因此,我知道问题与上面的加载邮箱 JS 有关,并且可能与事件侦听器如何在 for 循环中应用有关。 如果有人可以阐明如何将唯一的事件侦听器应用于每个单独的 div,将不胜感激。</p><p> 谢谢!</p></div> - Difficulty adding unique event listener to created <div> elements via a for loop

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 将相同的事件侦听器添加到具有不同参数的多个元素 - Adding same event listener to multiple elements with different parameter 单击另一个循环时将事件侦听器添加到元素 - Adding event Listener to elements on click of another in loop 将相同的事件侦听器添加到多个元素 - Adding the same event listener to multiple elements 在js中向多个select元素添加事件监听器 - Adding event listener to multiple select elements in js 使用“ for”循环添加“ click”事件监听器 - Adding 'click' event listener using 'for' loop 难以将唯一的事件侦听器添加到已创建的<div>通过 for 循环的元素</div><div id="text_translate"><p>我正在做一个项目来学习一些 JavaScript,目标是在单页 web 应用程序中动态提供电子邮件。 应用程序的HTML已经使用createElement JS方法创建。 到目前为止,我已经成功地显示了包含所有电子邮件的“收件箱”页面,如下图所示:</p><p> <a href="https://i.stack.imgur.com/V8cZq.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/V8cZq.png" alt=""></a></p><p> 我目前正在尝试通过使用 addEventListener 使这些单独的电子邮件中的每一个都可以点击。 我遇到的问题是,每当我单击任何一封电子邮件时,都会呈现收件箱中的第一个 email(id:1,主题:测试电子邮件),并且无法查看任何其他电子邮件。</p><p> <a href="https://i.stack.imgur.com/BBjQj.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/BBjQj.png" alt=""></a></p><p> 我可以看到相同的 email.id 被应用到所有创建的 div 的事件侦听器,尽管所有 div 都被正确创建,并包含来自相应电子邮件的所有信息。</p><p> 这是加载邮箱 JS,它呈现收件箱中的所有电子邮件:</p><pre> function load_mailbox(mailbox) { // Show the mailbox and hide other views document.querySelector('#emails-view').style.display = 'block'; document.querySelector('#compose-view').style.display = 'none'; document.querySelector('#single-view').style.display = 'none'; // Show the mailbox name document.querySelector('#emails-view').innerHTML = `<h3>${mailbox.charAt(0).toUpperCase() + mailbox.slice(1)}</h3>`; // GET request fetch(`/emails/${mailbox}`).then(response => response.json()).then(emails => { // Print emails to console console.log(emails); // Iterate through each email for(var i = 0; i < emails.length; i++) { var email = emails[i]; // Create div and append email content to HTML var emaildiv = document.createElement('div'); emaildiv.style.borderStyle = 'solid'; emaildiv.style.borderColor = 'black'; emaildiv.style.borderWidth = '0.1rem'; emaildiv.style.borderRadius = '0'; emaildiv.style.marginBottom = '0.2rem'; emaildiv.style.padding = '0.3rem'; emaildiv.innerHTML = `<b>${email.sender}</b> --- ${email.subject}<br>${email.timestamp}`; // If individual email selected then view email emaildiv.addEventListener('click', () => view_email(email)); // Populate div HTML with emails document.querySelector('#emails-view').append(emaildiv); console.log(email.read); // Colour backgrounds based on whether emails have been read if (email.read == true) { emaildiv.style.backgroundColor = 'lightgrey'; } console.log(email); } });}</pre><p> 这是视图 email JS,它应该渲染个人 email 的 HTML:</p><pre> // View email function view_email(email) { console.log(email.id); // Show the mailbox and hide other views document.querySelector('#emails-view').style.display = 'none'; document.querySelector('#compose-view').style.display = 'none'; document.querySelector('#single-view').style.display = 'block'; // GET request fetch(`/emails/${email["id"]}`).then(response => response.json()).then(email => { // Create div, set class, and append email content to HTML var reademail = document.createElement('div'); reademail.innerHTML = ''; reademail.style.borderStyle = 'solid'; reademail.style.borderColor = 'black'; reademail.style.borderWidth = '0.1rem'; reademail.style.borderRadius = '0'; reademail.style.marginBottom = '0.2rem'; reademail.style.padding = '0.3rem'; reademail.innerHTML = ` <b>From:</b> ${email.sender}<br> <b>To:</b> ${email.recipients}<br> <b>Subject:</b> ${email.subject}<br> <b>Timestamp:</b> ${email.timestamp}<br> <button class="btn btn-sm btn-outline-primary" id="Reply">Reply</button> <hr> ${email.body}`; // Populate div HTML with emails document.querySelector('#single-view').append(reademail); // Mark unread emails as read if (email.read === 'false') { fetch(`/emails/${email}`, { method: 'PUT', body: JSON.stringify({ read: true }) }) } }); }</pre><p> 这是存储在 email GET 响应中的示例(虚拟数据):</p><pre> { "id": 1, "sender": "user@example.com", "recipients": ["user@example.com"], "subject": "Hello,": "body", "Hello, world:", "timestamp": "Oct 24 2020, 12:00 AM", "read": false, "archived": false }</pre><p> 我已经尝试将其他每封电子邮件的 ID 硬编码到视图 email JS 中,并且可以看到该功能按要求工作(显示电子邮件)。</p><p> 因此,我知道问题与上面的加载邮箱 JS 有关,并且可能与事件侦听器如何在 for 循环中应用有关。 如果有人可以阐明如何将唯一的事件侦听器应用于每个单独的 div,将不胜感激。</p><p> 谢谢!</p></div> - Difficulty adding unique event listener to created <div> elements via a for loop 将点击事件分配给具有不同参数的多个元素 - Assigning click event to multiple elements with different parameters 动态js画布将事件侦听器添加到for循环中的多个点 - kinetic js canvas adding event listener to multiple points within for loop "将多个变量传递给事件监听器" - Passing multiple variables to an event listener 通过原生JavaScript传递事件侦听器参数? - Passing event listener parameters with native javascript?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM