Andrew's Digital Garden

Cascade layers

Layers are a new functionality in CSS that allows more control of the cascade and specificity of selectors. When using them, a 'stronger' layer will beat a stronger selector in a 'weaker' layer. [[20220801045127-css-specificity]] is only relevant inside a layer.

You can define as many layers as you want, such as a reset, base, theme, etc. This really helps you control how weak certain parts of your styling is, which is great for managing external libraries vs resets vs overrides etc. You can also make sub-layers, such as components and then components.dialog.

There's three ways of defining layers:

  • The @layer statement at-rule, declaring layers using @layer followed by the names of one or more layers. This creates named layers without assigning any styles to them.
  • The @layer block at-rule, in which all styles within a block are added to a named or unnamed layer.
  • The @import rule with the layer keyword or layer() function, which assigns the contents of the imported file into that layer.

Importantly, the order of layers is set by the order in which the layers appear in your CSS. This means that if you use the block at-rule without (or before) the statement at-rule, the order will be the order of your blocks (later created layers winning), even if you use the at-rule after. Therefore you should always define using the at-rule first, and make sure that part of your CSS is loaded first.

You can set the layer order multiple times with an at-rule. If they match, they're harmless, but if they don't match, each layer order at-rule is appended to the previous. Existing layers are not re-ordered.

As explained in https://www.matuzo.at/blog/2023/cascade-layers-are-useless/, Cascade Layers allow you to better control the specificity through cascade layers, rather than specificity or hacks like !important. Adding a class like --error and styling that will work with our without layers, but crucially styling aria-invalid will usually not work as well.

Authors can create layers to represent element defaults, third-party libraries, themes, components, overrides, and other styling concerns—and are able to re-order the cascade of layers in an explicit way, without altering selectors or specificity within each layer, or relying on order of appearance to resolve conflicts across layers.

/* First layer */ @layer base-layer { body#foo { background: tan; } } /* Higher layer, so this wins, despite selector strength */ @layer theme-layer { body.foo { background: #eee; } } /* Careful! Unlayered styles are more powerful than layers, even if the selector is weaker */ body { background: red; }

https://css-tricks.com/cascade-layers/ https://css-tricks.com/organizing-design-system-component-patterns-with-css-cascade-layers/ https://www.smashingmagazine.com/2025/06/css-cascade-layers-bem-utility-classes-specificity-control/

[[css]]

Cascade layers