Monday, December 5, 2011

Why Is CSS Not Object-Oriented?

There's a brilliant but unreadable book called Pro CSS And HTML Design Patterns which attempts to analyze CSS and HTML and isolate design patterns, like the OOP classic. It fails and it succeeds. The author does identify commonalities and unifying principles within CSS, but these don't really qualify as "design patterns" as they don't have cohesive characteristics or nameable identities. In OO design, it's easy to understand what the Singleton pattern represents -- it's a single thing, instead of one of many. Nothing so comprehensible exists in this book.

I highly recommend this book, but as a mountain to climb, not as a silver bullet. The attempt to treat CSS and HTML like object-oriented software fails, because the DOM is just one massive object whose design cannot be changed, and CSS is not object-oriented at all. It is an incredibly coarse, brittle query language combined with an unimaginably complex set of decorating notations. Object-oriented CSS would be awesome, but faces tough questions. Which is the fundamental unit of CSS: a rule? a cohesive visual element on the page? the DOM tree a rule applies to?

CSS maps a tree of style rules to a tree of DOM objects. These mappings falter and frustrate, because mapping a tree to another tree is no task for human minds -- it's the whole reason compilers were invented -- but they also represent a tremendous improvement over the pre-CSS model, wherein a tag conveyed both styling and semantics.

This suggests an evolution, in which CSS compilers should ultimately exist, and indeed, some already do -- e.g., Front Page and Dreamweaver -- but they suck beyond belief, and the open source avenues to this destination are still very young.

Kyle Neath created a cool project called KSS which addresses the confusion CSS always creates. It's a simple and powerful system for documenting CSS. I think it's a step in the right direction, like Sass, but I also think that the world will be a much better place when we finally get CSS compilers built for grownups -- by which I mean people who could write the output code themselves, but have better things to do, like the intended user base for Rails generators or CoffeeScript.

KSS uses cohesive visual elements on the page as its idea of the fundamental unit of CSS:

You should document a rule declaration when the rule can accurately describe a visual UI element in the styleguide. Each element should have one documentation block describing that particular UI element's various states.

That sounds very object-oriented to me. The end result looks like this:

In keeping with this philosophy, KSS allows you to document an implicit object hierarchy with your section numbering:

KSS documentation is hierarchical in nature — any documentation blocks at [any point within the] styleguide hierarchy apply to the documentation blocks [beneath] that level. This means that documentation for 2.1 applies to documentation for 2.1.3.

For instance, you can cover "Buttons" in section 2.1, "Login Buttons" in section 2.1.1, and "Navigation Buttons" in section 2.1.2.

I plan to retrofit an old project with KSS in the next few days, firstly to get a better feel for it and secondly because I'm very curious if it helps me uncover an implicit object hierarchy which is already there in the code. I'll blog about it some more if I find out anything interesting.