The cascade

Cascade and specificity

Predict which declaration wins by considering importance, origin, cascade layers, selector specificity, and source order.

9 minute lesson

~~~

Several declarations can target the same property on the same element. The cascade chooses one value before layout begins.

Use this order when debugging:

  1. relevance: does the selector match and does its media condition apply?
  2. origin and importance: browser, user, author, animation, or transition
  3. cascade layer order
  4. selector specificity
  5. scoping proximity, when @scope is involved
  6. source order when everything else ties

Within ordinary author styles, specificity is a useful comparison:

  • IDs outweigh classes.
  • classes, attributes, and pseudo-classes outweigh type selectors.
  • when specificity ties, the later declaration wins.
p { color: black; }
.intro { color: navy; }

The class wins because both declarations are normal author styles in the same layer, and .intro has greater specificity.

Layers can make priority explicit:

@layer reset, components, utilities;

For normal declarations, a later layer beats an earlier one regardless of selector specificity. Normal unlayered author styles beat all normal layered styles. This is useful for containing third-party CSS.

!important changes cascade priority and reverses layer precedence. It is not “more specificity” and should not be a routine override tool. :where() provides the opposite tool: its selector always contributes zero specificity.

Prefer low-specificity component classes and predictable source order. If you are fighting selectors with more selectors, simplify the structure.

In DevTools, find the crossed-out declaration and read why it lost. Change one factor at a time—layer, selector, then order—until you can predict the winner before refreshing.

Lesson completed

Take this course offline

Get every free book and course as PDF and EPUB files.

Get the download library →