Issue
Basically the question. My code (below) is quite lengthy and probably terrible as I am very new to coding. I am aware that I should put the JavaScript and HTML in different documents, but I prefer it like such. What I’d like to do is create a table, that, when users enter a column, a button appears next to the column giving them the option to delete it had they made a mistake.
document.getElementById("add").onclick = function() {
var node = document.createElement("Tr");
document.getElementById("list").appendChild(node);
var node = document.createElement("Td");
var text = document.getElementById("w").value;
var textnode = document.createTextNode(text);
node.appendChild(textnode);
document.getElementById("list").appendChild(node);
var node = document.createElement("Td");
var text = document.getElementById("m").value;
var textnode = document.createTextNode(text);
node.appendChild(textnode);
document.getElementById("list").appendChild(node);
var node = document.createElement("Td");
var text = document.getElementById("p").value;
var textnode = document.createTextNode(text);
node.appendChild(textnode);
document.getElementById("list").appendChild(node);
}
<table id="list">
<tr>
<th scope="col">Word</th>
<th scope="col">English</th>
<th scope="col">Pronunciation</th>
</tr>
<tfoot>
<tr>
<div class="boxy_bois">
<td><input type="text" id="w" class="w" required/></td>
<td><input type="text" id="m" class="m" required/></td>
<td><input type="text" id="p" class="p" /></td>
</div>
</tr>
</tfoot>
</table>
<div class="button_boi">
<button class="button_boi" id="add">Enter</button>
</div>
Solution
Your code create incorrect HTML result.
It becomes <tr></tr><td></td>...
instead of <tr><td></td>...</tr>
.
With current JavaScript, you can create new element using string and insert to exists HTML using insertAdjacentHTML()
. It is a lot easier than create DOM object and appendChild()
.
document.getElementById("add").onclick = function() {
let listTable = document.getElementById("list");
let tfoot = listTable.querySelector('tfoot');
let wordValue = document.getElementById("w").value;
let engValue = document.getElementById("m").value;
let pronunValue = document.getElementById("p").value;
let trHTML = '<tr>' +
'<td>' + wordValue + '</td>' +
'<td>' + engValue + '</td>' +
'<td>' + pronunValue + '<button class="deletethis" type="button" title="delete this row">x</button></td>' +
'</tr>';
tfoot.insertAdjacentHTML('beforebegin', trHTML);
}
// use event delegation to listen on click delete row.
document.addEventListener('click', (e) => {
let thisTarget = e.target;
let thisBtn = thisTarget.closest('.deletethis');
if (thisBtn) {
// if correct button then delete the whole table row (tr).
e.preventDefault();
thisTarget.closest('tr').remove();
}
});
<table id="list">
<tr>
<th scope="col">Word</th>
<th scope="col">English</th>
<th scope="col">Pronunciation</th>
</tr>
<tfoot>
<tr>
<div class="boxy_bois">
<td><input type="text" id="w" class="w" required /></td>
<td><input type="text" id="m" class="m" required /></td>
<td><input type="text" id="p" class="p" /></td>
</div>
</tr>
</tfoot>
</table>
<div class="button_boi">
<button class="button_boi" id="add">Enter</button>
</div>
From the code above, I use the new querySelector()
, closest()
to select the near elements.
I use event delegation to detect delete row button were click and then delete the whole tr
because newly created element can’t detect when using normal addEventListener
.
Answered By – vee
Answer Checked By – David Goodson (AngularFixing Volunteer)