Rewriting content with Javascript
I wanted some Javascript which, upon some trigger, would replace the content in a named HTML element. At first, I thought it would be simple:
document.getElementById("js-example").innerHTML = "the new content“;
This works in Safari and Internet Explorer, but encounters a bug in Firefox. In particular, each time the content is replaced via innerHTML, an additional newline (vertical whitespace) is inserted into the document.
My next attempt was to use the W3C DOM model by removing all of the children of our div and then adding the new text:
var theDiv = document.getElementById("js-example");
var divChildren = theDiv.childNodes;
var i = divChildren.length;
while (i-->0) {
theDiv.removeChild(divChildren[i]);
}
var textNode = document.createTextNode("the new content“);
theDiv.appendChild(textNode);
This has two problems:
- Markup isn’t interpreted by createTextNode
- The additional newline still appears!
All that extra code for nothing.
Next, I tried to clone the div with surprisingly better luck:
var theDiv = document.getElementById("js-example");
var newDiv = theDiv.cloneNode(false); /* shallow copy */
theDiv.parentNode.replaceChild(newDiv,theDiv);
var textNode = document.createTextNode("the new content“);
newDiv.appendChild(textNode);
This solution uses the W3C DOM to perform a shallow copy of the div and then add our new content. It’s better than our previous iteration because the newline is finally gone! We still can’t support markup in our replacement fragment, however.
Let’s try a unification of our original innerHTML approach and our DOM mangling:
var theDiv = document.getElementById("js-example");
var newDiv = theDiv.cloneNode(false); /* shallow copy */
theDiv.parentNode.replaceChild(newDiv,theDiv);
newDiv.innerHTML = the new content“;
Hooray! It works! With a shallow clone and the innerHTML technique, we avoid the newline bug in Firefox and Mozilla. Further, we can allow rich markup in our replacement fragments.
Rejoice!
Note: The Firefox problem goes away if the div doesn’t have a display style of ‘table’.
No comments yet. Be the first.
Leave a reply

