Javascript 输入监听器
2021-04-26
76
我有一个按每行最后一列的值排序的产品表。我希望当我单击某个输入时,相应的复选框直接变为选中状态。这样,当我单击“保存”按钮时,数据库中将只更新选定的产品。
原始代码中有太多与问题无关的内容,因此我将其简化为:
var c = 10;
var count = 1;
pageList.forEach(element => {
document.getElementById("tabla_variantes").innerHTML+=`
<tr style="background: white;">
<th class="check_col" scope="row" style="padding: 0px; text-align: center; vertical-align: middle;">
<input type="checkbox" value="${element.numero}" id="row${count}" name="row-check-pro">
</th>
<td> //image </td>
<td> //product number </td>
<td> //product name </td>
<td> //product reference </td>
<td> //product price </td>
<td> //product stock </td>
<td style="text-align:center; vertical-align: middle; padding: 8px 18px;">
<input type="text" class="form-control text-end" id="posicion${element.numero}" value="${c}">
</td>
</tr>
`;
document.getElementById(`posicion${element.numero}`).addEventListener('input', (evt) => {
console.log('run'); // Do something
document.getElementById("row"+count).checked = true;
});
++count;
c += 10;
if (c > list.length*10) c = 10;
});
如您所见,我尝试为每个输入添加一个监听器,但控制台上没有显示任何内容。
2个回答
你真的应该委托
此外,我建议使用 map 而不是连接到 DOM。
这是一个替换
const container = document.getElementById("tabla_variantes");
const pageList = [{numero:1},{numero:2},{numero:3}];
container.addEventListener('input', (evt) => {
const tgt = evt.target;
if (tgt.name==="row-check-pro") {
if (!tgt.checked) tgt.closest("tr").querySelector(".text-end").value="";
}
if (tgt.classList.contains("text-end")) {
tgt.closest("tr").querySelector("[name=row-check-pro]").checked = tgt.value.trim() != "";
}
});
var c = 10;
var count = 1;
container.innerHTML+= pageList.map(element => {
const str = `<tr style="background: white;">
<th class="check_col" scope="row" style="padding: 0px; text-align: center; vertical-align: middle;">
<input type="checkbox" value="${element.numero}" id="row${count}" name="row-check-pro">
</th>
<td style="text-align:center; vertical-align: middle; padding: 8px 18px;">
<input type="text" class="form-control text-end" id="posicion${element.numero}" value="${c}">
</td>
</tr>
`;
++count;
c += 10;
if (c > pageList.length*10) c = 10;
return str;
}).join("");
<table id="tabla_variantes">
</table>
mplungjan
2021-04-26
主要问题是您将
+=
与
innerHTML
结合使用。这绝不是一个好主意。当您执行
x.innerHTML += str
时,浏览器必须处理
x
元素内的所有元素,构建 HTML 字符串,将该字符串返回给 JavaScript 代码,然后从 JavaScript 代码接受更新后的字符串,
拆除
x
的所有先前子元素,并将它们替换为通过解析新字符串创建的
新
子元素。这些元素的所有状态都将丢失,包括它们所拥有的任何事件处理程序。
最小更改是:
- 在字符串变量中构建所有 HTML
-
将其分配给
innerHTML
- 查找元素并向其添加事件处理程序
但您应该考虑使用事件委托和 DOM 遍历,而不是在每个单独的元素上使用处理程序。有关事件委托的更多信息,请参阅
Stack Overflow 上的这个答案
,但简短的版本是您在共同祖先元素上处理事件,然后使用
event.target
确定事件针对的后代。
T.J. Crowder
2021-04-26