Style Previous Sibling Elements with CSS

December 20, 2017

After having to look this up a couple of times now, I figured I’d share my approach. While you currently can’t technically style previous sibling elements, I’ve figured out a pretty handy workaround.

Suppose you have a progress bar with steps that you want to style. You want the active step to be highlighted and all the steps before it as well (to denote that those steps are completed). Prettying up the active step is easy, but how do you handle the previous steps? You actually style the previous steps by styling the following steps.

Let me show you what I mean….

The Setup

First, let’s get our step navigation built and styled.

https://codepen.io/mburnette/pen/b6a725037f207882ae0463e4c4edcd5d/

The HTML is simply an unordered list with five list items – the first of which has an “active” class. The line between them is actually one solid line that goes behind all of the steps, added using the CSS “:before” pseudo-element and positioning it in place.

Now that the HTML and basic CSS are in place, we can think about how to style the active and completed steps.

A Tiny Bit of Javascript (jQuery)

You could change the active class of these steps in many different ways, but I’m going to keep it simple for this example.

https://codepen.io/mburnette/pen/87865b15f0d0a94180baf838911c63cd/

When you click on one of the steps, the “active” class is removed from all of them and then re-added to the one that was clicked.

Again, you could change this class position in many, many different ways, but I’m trying to keep it simple.

The Real Magic

Here’s the real secret to this whole process: you actually need to style the steps following the “active” step, not the previous ones.

Using the “~” sibling selector, we can style all the elements after the “active” element. All we need to do is style ALL of the elements as though they’re active, and then go back and style all the elements after the “active” one as though they are the normal state.

Here’s what I mean:

https://codepen.io/mburnette/pen/eeb200690ff4b6ad161e951d987d138e

And that’s all there is to it. Styling previous elements to an element by actually styling all elements after it. *mind-blown*

Bonus

This is exactly what I did (although a bit more complex) with my CSS-only star rating pen.

https://codepen.io/mburnette/pen/eNNZbm

Wanna chat about this article or any others? Feel free to DM me or mention me on Twitter @marcusdburnette to start a conversation!

Leave a Reply

Your email address will not be published. Required fields are marked *