Script-Assuming Styles

Recently, the topic of script-assuming styles came up again. With all the ajax and RIA flying around, its easy to forget that some folks fly with javascript disabled. This trap may lead to the developer creating styles that will assume script is enabled (since our heads are in script-land SO much) and wind up being useless to those without javascript. For example, a slideshow widget may have the style for the images set to hide them by default, then use javascript to display the images in-turn. Users that don’t have javascript will be looking at a page full of hidden images. No big deal to fix though, just make them visible by default and then have javascript hide them when the widget loads. The problem with this is that there will be a visible flicker when the page loads. The images will be visible for a split second, then they disappear.

The noscript tag could work here also (and without the flicker). Basically, have a noscript tag that would load a stylesheet specifically to ‘fix’ the widget to be usable when javascript is not enabled. This currently works, but there is some talk of the noscript tag not being included in XHTML5 and its a bit annoying to have that much distance between what is effectively the same logical group of styles just to cover the 2 modes. It would be especially annoying if this were a ‘3rd party’ widget or tool being dropped into a page.

I’ve talked about how it’d be nice if there was a :scriptEnabled pseudoclass available, but there (still) isn’t. The workaround is to have javascript code set a class on a root element that will just cascade and hide the images for you. Until today, I thought the body element was the best candidate for that: just add a ’scriptEnabled’ class to the body element (document.body) and then the styles will cascade. The trick was getting the script so that it would reliably be run AFTER the body was available. Without using a ‘dom ready’ approach, the best I’d could muster was to just have the script in line as the first child element of the body. It was a trade-off that I could live with.

Then I read this thread and I felt like a noob. In it, Simon Pieters describes the same approach, but used a much more appropriate element…and one that was much easier to get at without all the timing concerns. The root element itself: the html element (document.documentElement). The scriptEnabled class can be set on the document.documentElement and then the styles that want to assume that script is enabled would just be prefixed with .scriptEnabled. I had never thought about styling with the html element. I’ve used it (the html>blah css hack), but I’d never thought about using it for non-hackery. The nice part is, the code can be anywhere…the documentElement is (obviously) available when script is executing.

document.documentElement.className += ” scriptEnabled”;

On a related note: I now have a ‘noob’ category.