Я подозреваю, что это связано с тем, как вы обрабатываете обновления DOM. Ваш код только добавляет событие к последней кнопке. Это известная проблема с for/loop
s ). Использование forEach
вместо for / loop обычно исправляет это , но, очевидно, не в этом случае. (Я ценю, что это немного волнисто. У другого члена SO может быть более подробная техническая причина, почему это не работает в этом случае.)
Тем не менее, как вы обнаружили, вам гораздо лучше делать это поэтапно, но вы должны пойти еще на несколько шагов дальше. Это позволит избежать попадания в ситуацию, в которой вы сейчас находитесь, и будет более производительным.
В данный момент вы пытаетесь достичь всего за один цикл: создание html-задачи, добавление ее в DOM и добавление прослушивателя событий для новой кнопки. Что вам нужно сделать, это создать all HTML, затем добавить that в DOM, затем взять все кнопки сразу, используя их класс, и добавить к ним слушателей.
const filteredTasks = [{ taskName: 'bob' },{ taskName: 'dave' }];
const tasks = document.querySelector('#tasks');
// Use `map` to create all the buttons
// I've used a data attribute here instead of an actual id
const html = filteredTasks.map(task => {
const buttonId = `${task.taskName.replace(/\s/g, '')}Button`;
return `<button class="taskButton" data-id="${buttonId}">${task.taskName}</button>`;
}).join('');
// Add that HTML to the DOM with one update
tasks.innerHTML = html;
// Grab all the taskButton buttons using their class,
// and add click listeners to them
const buttons = document.querySelectorAll('.taskButton');
[...buttons].forEach(button => button.addEventListener('click', performTask, false));
// `performTask` destructs the event target (clicked button)
// and logs the id
function performTask(e) {
const { dataset: { id } } = e.target;
console.log(id);
}
<div id="tasks"></div>