0

I am appending trs to a table from a string. I use the following code to write an entire table using innerHTML, then I can use standard DOM to transfer the new bits to the existing table.

var div = document.createElement("div");
div.innerHTML = "<table><tbody>" + string + "</tbody></table>";

Using the following simple Javascript is fine, until we look at CSS styling. This causes each section to be in a different tbody. This is not acceptable as CSS styling is using :nth-child(odd)

document.getElementById("left").appendChild(div.firstChild.tBodies[0]);

Thus, I have changed the code to this, but it is only adding every other row to the table. What did I do wrong?

var tableBody = div.firstChild.tBodies[0];
var appendToTable = document.getElementById("left").tBodies[0];

var totalnodes = tableBody.childNodes.length;

for (var thenodes = 0; thenodes < totalnodes; thenodes++) {
    appendToTable.appendChild(tableBody.childNodes[thenodes]);
}
3
  • can you create a demo at jsfiddle.net Commented Mar 5, 2013 at 3:40
  • @ArunPJohny I would, however, it looks like we already found our answer. Commented Mar 5, 2013 at 3:49
  • then please post the answer and mark it as accepted Commented Mar 5, 2013 at 3:50

1 Answer 1

3

childNodes is a live node set, so when you remove it, the other elements shift down an index. So you end up getting every other row.

while (tableBody.childNodes.length) {
    appendToTable.appendChild(tableBody.childNodes[0]);
}
Sign up to request clarification or add additional context in comments.

5 Comments

So accessing a childNode removes it from the set? Where can I learn more about this live node set idea.
Not all the children of a tbody are rows. In some browsers, some of the child nodes will be text nodes. The above will transfer those as well (which isn't an issued, just pointing it out).
@michaellindahl—yes. You are moving nodes from one parent to another, so they are no longer members of the initial tbody element. It is all covered in the relevant specification.
@RobG Okay, so to try to understand this, DOM methods like appendChild will move the child to the new location? (I'm terrible at reading specs, also you are soo awesome!)
Yes, that's what's meant by If the newChild is already in the tree, it is first removed. The row is initially a member of the tbody's childNodes because it's a descendant. Once it's moved, it becomes a childNode of a different tbody. A live collection means it's updated as you go, it doesn't stay static (i.e. as it was when you first referenced it).

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.