コンテナクエリしたい(@container)
/* 監視対象のコンテナーを宣言する */
.card-list {
container-type: inline-size;
}
/* .card-list の幅が 400px 以上のとき、中の .card を横並びにする */
@container (min-width: 400px) {
.card {
display: block flex;
gap: 1rem;
}
}
@containerルールは、@mediaと似ていますが、条件に使うのが「画面の幅」ではなく「親要素(コンテナー)の幅」です。
同じ部品をサイドバーとメインの両方に置くような場合、 置かれた場所の幅に応じて見た目を変えられるので、部品を使い回しやすくなります。 ページ全体のレイアウトはメディアクエリ、その中の部品はコンテナクエリ、と使い分けます。
コンテナーを宣言したい(container-type)
.card-list {
container-type: inline-size;
}
@containerで幅を見てもらうには、親要素にcontainer-typeを指定して「これがコンテナーだ」と宣言します。
inline-size… 横幅だけを監視する。ほとんどの場合これを使うsize… 横幅と高さの両方を監視する。高さの計算が必要になるので使いどころは限られるnormal… 監視しない(初期値)
@containerのクエリは、いちばん近い「コンテナー宣言された祖先要素」を基準にします。
その要素自身ではなく、中の子要素にスタイルが当たります。
名前をつけて指定したい(container-name)
.sidebar {
container-type: inline-size;
container-name: sidebar;
}
.main {
container-type: inline-size;
container-name: main;
}
/* sidebar コンテナーの幅だけを見る */
@container sidebar (min-width: 300px) {
.card {
font-size: 1.1rem;
}
}
コンテナーが入れ子になっていると、@containerがどのコンテナーを見るのか分かりにくくなります。
container-nameで名前を付け、@container 名前 (条件)と書くと、その名前のコンテナーだけを対象にできます。
/* container-type と container-name をまとめて書く */
.sidebar {
container: sidebar / inline-size;
}
containerショートハンドで名前 / タイプをまとめて指定することもできます。
コンテナーの幅を単位に使いたい(cqi)
@container (min-width: 400px) {
.card h2 {
font-size: max(1.25rem, 4cqi);
}
}
コンテナクエリ専用の長さの単位があり、コンテナーの大きさに対する割合で指定できます。
cqw… コンテナーの幅の1%cqh… コンテナーの高さの1%cqi… コンテナーのインライン方向(横書きなら幅)の1%cqb… コンテナーのブロック方向(横書きなら高さ)の1%
4cqiなら「コンテナー幅の4%」です。
コンテナーが広がると文字も一緒に大きくなる、といった調整ができます。
ブラウザ対応
コンテナクエリはモダンブラウザで使えます(Chrome / Edge 105、Firefox 110、Safari 16 以降)。
古い環境も対象にする場合は、@mediaで近い挙動のフォールバックを書いておくと安全です。