HTML and Non-Script Styling

Published on February 21, 2012 (↻ February 5, 2024), filed under (RSS feed for all categories).

This and many other posts are also available as a pretty, well-behaved ebook: On Web Development.

If you are to style a document differently based on whether certain technology is available, you should keep two things in mind:

  1. HTML itself is static. An HTML document doesn’t care how it’s manipulated. Any ID or class names you’re using by default, that is, directly in the markup and not added by scripts, should reflect that fact.

  2. Separation of concerns is important for maintainability. ID or class names should hence be functional or generic.

For pragmatic reasons, techniques like class=no-js nicely avoid script-related classes all over the code but do not follow these principles. class=no-js misses 1) by not stating what the document represents but what it does not represent. It misses 2) because it is technology-centric, or behavioral.

Let’s see what else could do the trick.

Separation of concerns is the best starting point to come up with styling and scripting solutions. The challenge with non-script styling, however, is that there is justification for a root level ID or class name for which it is more difficult to find a “functional” name, which hence suggests a generic name. Alas, generic names are harder to work with as they tend to be less obvious and understandable.

What developers can do to cater for non-script styling while at the same time separating concerns is to, for example, use their project name as each HTML document’s @id or @class. For that reason we’ve moved to using “google” on some of Google’s properties, while on my site I could use “meiert.”

Similar to “no-js,” one can then use that “project” ID (or class) to use scripting to change that ID to, say, “project-script” and do the following:

.example {
  foo: bar;

/* Matches only when scripting is disabled: */

#project .example {
  foo: baz;

While, due to aforementioned lack of functional naming options, there is a trade-off in terms of how understandable such names are, they confer some meaning (HTML documents are marked as “project” documents), they can be repurposed for other script or styling maneuvers, and they are less likely to require markup changes again (which makes them more maintainable).

Note that the situation is different for tools like Modernizr which don’t require to hard-wire any IDs or classes in the HTML. This is, as we know, useful: What developers should care most about is the markup—it requires much greater effort to spoil projects just by their style sheets and scripts.

Was this useful or interesting? Share (toot) this post, or maybe treat me to a coffee. Thanks!

About Me

Jens Oliver Meiert, on September 30, 2021.

I’m Jens (long: Jens Oliver Meiert), and I’m a frontend engineering leader and tech author/publisher. I’ve worked as a technical lead for companies like Google and as an engineering manager for companies like Miro, I’m close to W3C and WHATWG, and I write and review books for O’Reilly and Frontend Dogma.

I love trying things, not only in web development (and engineering management), but also in other areas like philosophy. Here on I share some of my views and experiences.

If you want to do me a favor, interpret charitably (I speak three languages, and they can collide), yet be critical and give feedback for me to learn and improve. Thank you!

Comments (Closed)

  1. On February 22, 2012, 1:49 CET, Neovov said:

    Hi Jens,

    This is quite off-topic but here is two remarks concerning id and class names:

    - This is quite difficult to explain the need of meaning names for beginners. When someone start learning HTML and CSS he have other consideration than taking a minute to choose a good name. I think this is something we have to learn with experience. Otherwise, bad names can be explained with a proper code documentation.

    - I usually talk about “presentationnal states” when talking about scripts interacting with the styles. The main goal is to explain adding/removing/switching class names can easily change the whole presentation of a block (with all the benefits: performance, maintainability, less code, etc.). Sometimes putting a name on something allow to spread the words and develop a good practice. I know we will disagree, but speaking of states often leads to using “behavioral” or worst “presentationnal” class names.


  2. On February 29, 2012, 20:01 CET, Simon Schick said:

    If we’re talking about js and non-js I personally like more the functional class-names.

    If I’d just read the css-file of your example without knowing about this javascript-snippet adding the ID I would not know what the difference between these two css-selectors are. I would even may have problems finding the ID in the template-files.

    I always have a class in the body named js-enabled or js-disabled. I think this makes it more obvious.

  3. On March 10, 2012, 14:57 CET, Finn said:

    Wouldn’t it make more sense to use a .js class only and forget about the .non-js?

    .example {
        foo: bar;
    /* Matches only when scripting is enabled: */
    .js .example {
        foo: baz;

    This way it would work the same as Modernizr works and your HTML stays clean by default.

  4. On June 5, 2012, 9:29 CEST, Vivien Blasquez said:


    If I’d just read the css-file of your example without knowing about this javascript-snippet adding the ID I would not know what the difference between these two css-selectors are. I would even may have problems finding the ID in the template-files.