December 7, 2009
I just spent a while adding a feature to my blog, or from another point of view removing an annoyance from my writing.
I found myself often experiencing a conflict between either (1) leaving out explanations or details that were likely to be useful or entertaining to some readers, or (2) dumping content that is too extensive, too basic, too fancy, or whatever on other readers. Readers differ enough so there’s never really a “right” level and I found the resulting compromises uncomfortable. Most likely other writers of long-form posts experience the same conflict.
My response is basically simple. I added notes that open in place when the note reference is clicked.
- Like this
- The note looks like this when it’s is open, and another click will close it.
Why do something new?
Dead tree media has a number of techniques for dealing with optional content. Discursive footnotes, sidebars, flagged sections, etc. are used for content that may be too detailed or too basic for the main line. But these methods don’t work very well on the web. Footnotes in particular, the only one of these methods that is supported in common authoring environments, is terrible on the web, because reading a footnote typically involves scrolling far away, so you lose all your visual context, and then scrolling back again to continue reading, so you can no longer refer to the footnote.
On the other hand, we can show and hide content in web pages quite easily, since the advent of DOM twiddling libraries.
- What’s a DOM?
The concept is simple. I looked around fairly carefully for some existing way to do this that I could adopt in my (WordPress) environment. There doesn’t appear to be anything available (I’d still be happy to use an existing solution so let me know if I missed one). There are plenty of ways to support footnotes at the bottom of the page, but no way to handle notes that open and close in context, and that integrate cleanly with the rest of the page. So, I went to the trouble of implementing my own.
The basic mechanism is also simple. Unfortunately as could be expected with the web being a steaming pile of half-integrated standards and one-quarter documented software, the actual execution was not so simple and involved a couple of significant compromises. However in the end I hacked my way through it and have something that makes me fairly happy. The result is visible in the previous post and in this one.
What’s the design?
I pretty much stuck with notes (foot notes, end notes, etc.) as we understand them: a short reference (typically superscript), taking you to an arbitrary chunk of content that basically can contain anything. References are arbitrary text; they could just be numerals, letters, special characters, or whatever. They could all be the same — for example just asterisks. I prefer to use descriptive references so the reader doesn’t have to open a note to figure out whether they want to read it.
To simplify the design, a reference takes you to the immediately following note. That way I don’t need any links, anchors or identifiers. Notes open in place just after the reference, but they could be floated left or right (looking more like sidebars).
A number of pleasant properties emerged from the design.
- All of the appearance of references and notes is determined by normal CSS.
- What’s CSS?
- Modern web content is marked up to indicate the intended usage, and then styles are defined to say how it should look. Styles can be applied with a clever mechanism called “Cascading Style Sheets” that basically say “Make everything that’s marked this way look like this“. There are very powerful ways to describe which things to style and how they should look. Even pulling notes out of the text and making them into marginal notes could be done by styling them differently.
- Because we’re on the web notes can contain a very wide range of content; for example the steps of a tricky recipe could be annotated with embedded video, available for those who need it, out of the way for those who don’t.
- The open and closed state of notes is persistent, so the user can pretty much tailor the text to suit themselves. For example in the case of the annotated recipe, some illustrations could be open and others could be closed as desired.
- Notes can be nested to any depth. With my current styles the depth is indicated by the indentation. So far I haven’t actually needed to nest notes…
What’s the mechanism and what are the compromises?
I just defined custom elements for note references and notes, used jQuery to translate them into appropriately styled spans and divs respectively, and also used jQuery to add click handlers to open and close the notes.
- What does all this mean?
Then the “fun” began.
the “p” tag is evil
I had problems getting my notes to behave nicely; they kept introducing line breaks even when closed (and styled with display:hidden). Eventually I figured out that notes are incompatible with “p” tags, basically because of historical constraints. I’ll explain the specifics in another post so possibly other people trying to figure this out will find the answer. So in posts where I use notes, I have to use appropriately styled divs rather than “p” tags.
and feeds aren’t styled!
Now the rendering of a post depends heavily on the styles. But the posts in my feed didn’t have the style sheet, and feed readers strip all embedded style information. With unstyled divs rather than “p” tags, the feed version of the post was nearly unreadable.
So I had to figure out how to generate “p”s rather than divs when the post content was written out to the feed. WordPress has filter hooks for this kind of thing, but it turned out it doesn’t have a hook to process only content being written to feeds, so I had to find the right place to hack in another filter hook. (I may also explain this in a post; I’ve requested that WordPress add a standard hook for this.)
how can I make notes look OK in feeds?
Also, as unstyled divs (or “p”s), the notes couldn’t be distinguished from the main text. The only way to control the rendering of content in feeds is by choice of elements. So when generating a feed, I needed to either delete the notes or translate them into elements that would “look like notes” in a feed reader. After some thought I realized I could use definition lists, which look quite “note like” in typical feed readers, and even nest well.
- What does a definition list look like?
- I didn’t know either until I went looking. Like this:
- Note 1
- Some note content.
- Note 2
- Some more note content.
Perhaps going on somewhat longer.
Lots of leftovers
Now I basically have a blog with notes that work the way I want, within the limits of current web standards and software. But I still have a lot of cleanup before I feel done.
- I hacked an existing text replacement plugin for WordPress to use my hacked in filter hook. I should generalize my hack and release the plugin.
- The jQuery script does two searches when it should just do one; I need to figure out the right jQuery idiom.
- Authoring now requires manually generating the note markup. This is pretty easy but I should probably write some authoring macros.
- Content isn’t properly styled when printing and perhaps in other cases; I need to fix that, probably with more WordPress filtering.
- For extra credit, printing should reflect the customized state of the page (which notes are open or closed); this is likely to be hard, but maybe I can figure out how by deciphering some apps that do it, like Google Maps.
- I need to figure out how to get the filter hook adopted by standard WordPress so I don’t have to maintain a forked version.