大規模なCSSプロジェクトで詳細度の競合に悩んだ経験はありませんか?サードパーティのスタイルを上書きするために!importantを連発したり、カスケードを優先させるためにHTMLを再構築したり — @layerはこうした問題に対する待望の解決策です。CSSの@layerアットルールは、詳細度やソース順序から独立した、明示的なカスケード制御を開発者に提供します。
@layer登場前のカスケード問題
@layer以前は、カスケード管理は完全に慣習に依存していました。BEM命名規則、SMACSSカテゴリ、ITCSSアーキテクチャ — これらはブラウザに強制されない合意ベースのルールでした。
/* @layerなし:詳細度の闘い */
.card { background: blue; } /* 0,1,0 */
body .card { background: red; } /* 0,1,1 — 詳細度で勝利 */
.card { background: blue !important; } /* エスカレーション */
@layerの仕組み
@layerはスタイルを名前付きレイヤーにグループ化し、その優先順位を定義します。後続のレイヤーのスタイルは、内部のセレクタの詳細度に関係なく、以前のレイヤーを上書きします。
@layer reset, base, components, utilities;
@layer reset {
* { margin: 0; padding: 0; box-sizing: border-box; }
}
@layer components {
.btn { background: var(--color-primary); padding: 0.5rem 1rem; }
}
@layer utilities {
.mt-4 { margin-top: 1rem; }
}
| 機能 | 利点 |
|---|---|
| レイヤー優先順位 | 後続レイヤーが先行レイヤーを上書き(詳細度に関係なく) |
| ネストレイヤー | @layer framework.base { }でサブレイヤー階層を構築 |
| 匿名レイヤー | @layer { }でサードパーティコードを名前付けなしで分離 |
@import統合 | @import url(styles.css) layer(framework)で既存ファイルをレイヤー化 |
レイヤーアーキテクチャ戦略
最も一般的で効果的なのは4層モデルです:リセット、ベース、コンポーネント、ユーティリティ。
@layer reset, base, components, utilities;
@layer base {
/* タイポグラフィ、リンク、グローバルスタイル */
}
@layer components {
/* カード、ボタン、フォーム — 再利用可能なパターン */
}
@layer utilities {
/* スペーシング、表示、テキスト配置 — 単一目的クラス */
}
TailwindやBootstrapを使用するプロジェクトでは、フレームワークのスタイルを低優先度レイヤーに配置します。
@import url("tailwind.css") layer(tailwind);
@import url("bootstrap.css") layer(bootstrap);
@layer base, components, tailwind, bootstrap;
これにより、カスタムのベーススタイルとコンポーネントスタイルが、詳細度ハックなしで常にフレームワークのデフォルトを上書きできます。
レイヤー内の詳細度制御
レイヤー内では通常の詳細度ルールが適用されます。レイヤー順序はセレクタの詳細度とは直交する概念です。
@layer components {
.btn { background: blue; }
.btn.primary { background: green; } /* レイヤー内では勝利 */
}
@layer utilities {
.bg-red { background: red; } /* 低詳細度だが後続レイヤーなので優先 */
}
!importantはレイヤー優先順位を逆転させることに注意してください。先行レイヤーの!importantは後続レイヤーの!importantより優先されます。目標は!importantを完全に排除することです。
BEMからの移行
既存コードベースの移行は段階的に行うのが最善です。リセットとベーススタイルからレイヤー化を始め、徐々にコンポーネントとユーティリティに拡大します。
@layer reset { @import url("reset.css"); }
@layer base { @import url("base.css"); }
@layer components { @import url("components.css"); }
@layer utilities { @import url("utilities.css"); }
PostCSSプラグインのpostcss-layerを使用すると、レガシーファイルの自動ラップが可能です。各フェーズ後にビジュアルリグレッションテストを実行し、意図しない変更がないことを確認します。@layerのブラウザサポートは95%以上(Chrome 99+、Firefox 97+、Safari 15.4+)で、2024年には本番環境での使用が十分に安全です。
