In the previous post, I unveiled a new method of display block-level code snippets on the site. While developing this new method, I ran into a couple of cross-browser compatibility issues that delayed release of the work. Primarily, when dealing with elements that maintain whitespace (the <pre> tag and the <textarea> tag), special considerations need to be made to handle things in Internet Explorer to make the code function the same as in other browsers. Specifically, carriage returns/new lines are treated differently, as is assigning text via the innerHTML property.

Line Breaks, the <pre> Element, and IE

Typically, whitespace is ignored in HTML documents. The HTML standard, however, urges web browsers to maintain whitespace within the <pre> element. Thus, the following code:


<pre>
line 1
	line 2
line 3
</pre>

…will produce the following result:

line 1
	line 2
line 3

There’s an invisible character at the end of each line that tells the browser to end the line and move to the beginning of the next one. So if you wanted to add, remove, or interact with these line breaks you’d have to know what the special character is. In typical standards-based browsers, the special character is \n, so if you wanted to remove line breaks from preformatted text you could do something like this:


var pres = document.getElementsByTagName('pre');
for (var i in pres) {
	pres[i].innerHTML = pres[i].innerHTML.replace(/\n/g,'');
}

This will not work for Internet Explorer though, as Internet Explorer uses \r for line breaks. In the example above, you’d have to modify the code to replace both \r and \n:


pres[i].innerHTML = pres[i].innerHTML.replace(/\n|\r/g,'');

Great! Except there’s also a problem with innerHTML, IE, and preformatted text… which leads me to:

innerHTML Removes Whitespace in IE

Apparently, whenever text is obtained or set via the innerHTML property, IE erroneously removes all the whitespace. Which is funny because innerHTML was created by Microsoft.

To address this issue, we’ll just have to use DOM based methods for getting and setting text (which we should be doing anyway). So instead of the previous code to remove line breaks, we could use this code in IE to double the line breaks:


var pres = document.getElementsByTagName('pre');
for (var i in pres) {
	for (var j in pres[i].childNodes) {
		if (pres[i].childNodes[j].nodeType == 3) {
			pres[i].childNodes[j].nodeValue = pres[i].childNodes[j].nodeValue.replace(/\r/g,'\r\r');
		}
	}
}

The code checks every <pre> tag for text nodes, and if found doubles line breaks (in IE). Using nodeValue in this manner is similar to the use of innerHTML, but IE doesn’t see the same bug as before!

About

Not Just a Hat Rack (NJHR) focuses on best practice solutions for problems you’ll encounter during a typical site build. There’s an emphasis on new technology when possible (HTML5, CSS3, etc.), but all suggested solutions will work cross-browser, quickly and efficiently. more »

I'm Andrew Church, an aspiring web developer currently living and working in Washington, DC. I’ve been employed as a professional developer since 2004, when I graduated with a degree in Information Sciences & Technology from Penn State University. I'm particularly interested in front-end web development technologies (HTML, CSS, JavaScript), but I do have experience with the entire site build process. « less

Tweets

Delicious