Why it matters
"Why isn't my style applied?" is the most common CSS question, and DevTools only half answers it: it strikes through the losing declaration but doesn't say whether it lost on specificity, on a layer, to an !important somewhere else, or because its media query isn't matching. Cascade layers made this harder: a one-class selector in a later layer now beats an ID in an earlier one, and !important flips the layer order.
This resolver parses your CSS with its layers, nesting, @media and @supports, matches every rule against the element you pick in an inert copy of your HTML, and ranks the declarations for each property in the order the CSS Cascading and Inheritance Level 5 spec gives. For every winner it names the step that decided it, such as "unlayered styles beat any layer" or "specificity (1,0,0) beats (0,2,0)"; for every loser it says what beat it; and declarations that don't apply right now, behind a media query, a :hover or a ::before, are listed with the reason. Inherited properties like color and font-family are traced to the ancestor that set them.
How it works
- InputAn element and the CSS that targets it
- In your browserRanked by importance, layers, specificity and order
- OutputEach property's winner and why
Where it fits in a designer's workflow
- Plan
- Design
- Build
- Test
- Launch
By the numbers
Show the numbers as a table
| Property | Declarations | Winner | Why |
|---|---|---|---|
| background | 4 | #buy | Unlayered styles beat any layer, here components. |
| color | 3 | .btn-primary | !important beats normal declarations. |
| margin-top | 2 | .card .btn | Layer components comes after reset in the layer order. |
| padding | 4 | .featured .btn | Unlayered styles beat any layer, here components. |
How to use it
- Paste the HTML and CSS.
- Pick the element that looks wrong (the one with most overridden declarations is picked first).
- Set the viewport width and colour scheme to match.
- Read why each value wins, and what it beat.
FAQ
What order does the cascade use?
First importance (!important beats normal), then inline style attributes over stylesheet rules, then cascade layers, then specificity, then whichever comes last in the source. Each step only matters if the earlier ones tie.
How do @layer rules change things?
Layers are ordered by when their names first appear. For normal declarations, later layers win and unlayered CSS beats every layer, whatever the specificity. For !important it's reversed: the earliest layer wins.
Why does a selector with an ID lose?
Usually because it's inside an earlier layer, or the other declaration is !important or inline. Specificity only compares declarations in the same layer and importance.
Does it handle nested CSS?
Yes. Nested rules are resolved as the spec says: & becomes the parent selector wrapped in :is(), and relative selectors become descendants, so specificity matches the browser.
What can't it see?
Styles added by JavaScript, the browser's default stylesheet, @scope proximity and container query sizes (container queries are assumed to match and marked).