No Login Data Private Local Save

CSS Cascade Layers (@layer) Playground - Online Editor

11
0
0
0
CSS Cascade Layers Playground
@layer
Presets:
CSS with @layer
Layer Priority Order low → high priority
No @layer detected — all styles are unlayered (highest priority)
Lower Priority Higher Priority
HTML
Live Preview Live
Frequently Asked Questions about CSS Cascade Layers

CSS Cascade Layers, introduced with the @layer at-rule, allow developers to explicitly control the cascade order of styles. Instead of relying solely on specificity and source order, layers let you group styles into named buckets and define which bucket takes precedence. A layer declared later in the stylesheet wins over earlier layers — regardless of selector specificity. This solves long-standing pain points like overriding framework styles without resorting to !important or high-specificity selectors.

Within a single layer, normal specificity rules apply. But across layers, specificity is irrelevant — the layer order alone determines which style wins. A low-specificity selector in a higher-priority layer will always beat a high-specificity selector in a lower-priority layer. This is the fundamental power of cascade layers: you can write simple, low-specificity selectors knowing they'll win if they're in the right layer.

Unlayered styles are CSS rules declared outside any @layer block. In the cascade, unlayered styles always have the highest priority — they override styles from all layers, regardless of layer order. This is intentional by design: it ensures that existing stylesheets without @layer continue to work as expected, and developers can opt into the layering system gradually. Think of unlayered styles as sitting in an implicit "top layer" above all named layers.

Yes! You can nest layers using dot notation (e.g., @layer framework.base { }) or by placing @layer rules inside another layer block. Nested layers inherit their parent's priority position relative to other top-level layers. Within the same parent, nested layers follow the same rule: later-declared nested layers win. This is great for organizing large codebases — for example, a framework layer containing framework.reset, framework.components, and framework.utilities sub-layers.

Use the statement @layer reset, base, components, utilities; at the top of your stylesheet. This single line defines the priority order: utilities wins over components, which wins over base, which wins over reset. The order is determined by the sequence in the comma-separated list — later names = higher priority. This approach is recommended because it makes the layer hierarchy immediately obvious to anyone reading your code.

Interesting behavior: !important reverses the layer priority. A style marked !important in a lower-priority layer will beat a normal style in a higher-priority layer. However, an !important in a higher-priority layer still beats !important from a lower-priority layer. In other words, !important within layers behaves consistently — it elevates the declaration, but layer order still matters among important declarations. This is one of the trickier aspects of cascade layers.

Cascade Layers are supported in all modern browsers: Chrome 99+, Firefox 97+, Safari 15.4+, and Edge 99+. As of 2024, global support exceeds 93% of users. For older browsers, @layer rules are simply ignored and styles fall back to normal cascade behavior, making it safe to use as a progressive enhancement. There's no polyfill needed — unsupported browsers just get the unlayered cascade.

This is one of the best use cases! Place your framework (Bootstrap, Tailwind, etc.) inside a lower-priority layer: @layer framework { /* all framework CSS */ }. Then put your custom styles in a higher-priority layer or leave them unlayered. This way, your custom styles always override the framework without specificity battles. You can even use @import url('framework.css') layer(framework); to assign an external stylesheet to a layer in one line.

Absolutely! The syntax is @import url('styles.css') layer(layer-name); — this imports the entire stylesheet into the specified layer. You can also use @import url('styles.css') layer; to assign it to an anonymous layer. Importing into layers is a clean way to organize third-party CSS without modifying the source files. Note: @import with layer() must come before any other CSS rules (except other @imports and @layer order declarations).

In Chrome and Firefox DevTools, the Styles panel now shows which layer a rule belongs to, with a small layer badge next to the selector. You can also see overridden declarations with a strikethrough, along with an indicator of which layer overrode them. The Computed tab shows the final cascade winner. Additionally, the @layer panel in Chrome DevTools (under the CSS overview) gives a visual map of all layers and their order. Use these tools to understand why a particular style isn't applying as expected.