Published at
Updated at
Reading time
2min

Jim Nielsen blogged about a mind-boggling feature of the new :has() pseudo-class. The pseudo-class isn't cross-browser supported yet, but this CSS addition unlocks countless use cases that Frontend engineers have been dreaming of for years.

Here's the current browser support according to MDN.

MDN Compat Data (source)
Browser support info for :has()
chromechrome_androidedgefirefoxfirefox_androidsafarisafari_iossamsunginternet_androidwebview_android
10510510512112115.415.420.0105

When I heard first about :has(), I thought it's only the long-awaited "parent selector", but Jim shared that it's the "previous sibling selector", too! 🤯

/* 
  Select every <a> element that's a child of 
  a <p> element that directly precedes an <hr> element.
*/
p:has(+ hr) a { /* ... */ }

With :has() entering the web platform, we can select elements in all directions — we wanted the "parent selector" but will soon have a selector to match the entire family.

Styling the next and previous siblings becomes a nifty one liner. Let's look at a few examples!

Select the following element siblings

Before getting into the new and fancy things, let's recap how to select next (or following) DOM elements.

To select an element's next sibling, use the adjacent sibling selector (+). The selector will match the element that immediately follows another element.

/* Select the center element's next sibling */
.center + * {
  background: var(--red);
}
Preview
C

Similarly, the general sibling selector (~) allows you to select all following elements.

/* Select all the center element's next siblings */
.center ~ * {
  background: var(--red);
}
Preview
C

Are you ready for the :has() selector beauty?

Select the previous element siblings

We can now invert these selectors with :has() and match elements in the other direction to select previous siblings. 🤯

Use :has() with the adjacent sibling selector (+) to select the immediately previous element...

/* Select the center element's previous siblings */
*:has(+ .center) {
  background: var(--red);
}
Preview
C
You can't see the selected elements because your browser doesn't support :has() yet.

... or the general sibling selector (~) to match all previous siblings.

/* Select all the center element's previous siblings */
*:has(~ .center) {
  background: var(--red);
}
Preview
C
You can't see the selected elements because your browser doesn't support :has() yet.

:has() is a pretty big deal in CSS land and I can't wait until it finally lands in all browsers, so we can match elements in all directions. Up and down! And left and right — the CSS future's bright!

Was this snippet helpful?
Yes? Cool! You might want to check out Web Weekly for more snippets. The last edition went out 8 days ago.
Stefan standing in the park in front of a green background

About Stefan Judis

Frontend nerd with over ten years of experience, freelance dev, "Today I Learned" blogger, conference speaker, and Open Source maintainer.

Related Topics

Related Articles