Taming nested OLs with 1 nested CSS rule
- Published: 2024-02-04 15:54
- Updated: 2024-02-07 15:50
I recently wondered—With how few CSS rules can I tame nested, ordered lists of any depth:
- In a fluid and responsive way
- That adapts to @media declarations
- Without further modifications
- Whilst sticking to a baseline grid (as close as possible)
- And subtle tweaks to optimize legibility?
CSS nesting seemed like a perfect tool for the job. So, I had a go at codepen.io.
Drumroll—The CSS¶
ol {
padding-left: 0;
line-height: .975rlh;
li {
margin-left: 2ch;
margin-bottom: .125rlh;
}
ol li:first-child {
margin-top: .125rlh;
}
}
Kind of underwhelming, isn’t it? And yet, if I’m not mistaken that’s already it. Guess it makes sense to see it in action, before dissecting it:
In action¶
- We’re curious about this ‘thing'
- This aspect isn’t too fancy
- So, let’s explore this aspect in detail
- Delving deeper, we uncover more nuances
- Continuing the exploration, we focus on a specific aspect
- Extending the discussion, we provide real-world examples
- Finally, we conclude this nested exploration with an extended summary, that must include a line-break
- Continuing the exploration, we focus on a specific aspect
- Returning to the broader topic, we address related concerns
- Delving deeper, we uncover more nuances
- Moving on, we examine another sub-topic within this section
- Sub-sub-section 1.1.2
- Sub-section 1.2
- Exploring a different perspective, we introduce a new concept
- Considering alternative viewpoints, we discuss varying opinions
- Wondering how deep the rabbit hole goes
- And how much further we can nest this list?
- What if we discovered something very important here that needed a lengthy description?
- And oh: yet another discovery awaits!
- With that yet another level, so we’ve have to keep nesting
- And oh: yet another discovery awaits!
- What if we discovered something very important here that needed a lengthy description?
- And how much further we can nest this list?
- Exploring a different perspective, we introduce a new concept
The nested CSS in detail¶
padding-left: 0;
removes the standard padding1rlh
equals the root elements’/global line-height- Removing
.25rlh
>.975lh
subtly:- Helps separating
li
items including line-breaks - Creates opportunity to use the ‘stolen’ .25rlh for margins
- Helps separating
li
selects every list-item that’s a child of olmargin-left: 2ch;
indents the items by two-letters- Centering the counters of nested levels below the first letter of adjacent list-content, creating a trackable horizontal flow
1ch
equals the computed width of the number 0- According to the context, thus font-size in use
margin-bottom: .125lh;
returns the vertical separation, that we nicked from the overall line-height of the ol
ol li
selects every first item of any nested level depthmargin-top: .125rlh;
adds a subtle bit of further vertical separation between the items- Yes, the anally retentive baseline grid approach would be using .1lh for both margins, because we nicked .25rlh from the line-height
- Having fiddled around with many different values, I think this is a good compromise between math and accessibility
The final margin bottom, depending on context¶
Depending on the overall flow of top-, and bottom-margins across the elements of your page, the final list-items margin won’t be set. In case the following paragraphs need vertical spacing:
- Sets a margin-top on the element following the OL
- I didn’t find a non-hacky way of doing it otherwise, yet
Resources for the curious¶
- Getting started with CSS nesting —creatures.dev/Nikolov Lazar
- CSS values and units—Mozilla developer network