CSS 封じ込め
========

Baseline 2023
-------------

Newly availableSince February 2023, this feature works across the latest devices and browser versions. This feature might not work in older devices or browsers.

* Learn more
* See full compatibility
* Report feedback

 CSS 封じ込め (CSS Containment) 仕様の目的は、ウェブページの表示性能を向上させるために、開発者がページの任意のサブツリーをページのそれ以外の部分から独立させることができるようにすることです。もしページの一部が独立していることをブラウザーが知っていれば、レンダリングを最適化し、表示性能を向上させることができます。この仕様では、単一の CSS プロパティ `contain` を定義しています。この文書では、その仕様の基本的な目的を説明しています。
基本的な例
-----

多くのウェブページは、互いに独立したいくつかのセクションで構成されています。例えば、記事の見出しと内容の一覧が、以下のようなマークアップで存在していたとします。


```html
<h1>私のブログ</h1>
<article>
  <h2>良い記事の見出し</h2>
  <p>内容はこちら。</p>
</article>
<article>
  <h2>他の記事の他の見出し</h2>
  <p>さらなる内容はこちら。</p>
</article>
```


それぞれの記事には CSS で `contain` プロパティに `content` という値が設定されています。


```css
article {
  contain: content;
}
```


それぞれの記事は、ページ上の他の記事と独立していますので、 `contain: content` がこのことをブラウザーに伝えるために指定されています。それでブラウザーはこの情報を使用して、どのようにして内容を描画するかを決定します。例えば、表示される領域の外側にある記事は描画しない場合があります。

それぞれの `<article>` の `contain` プロパティを `content` の値に設定すると、新しい要素が挿入されたとき、ブラウザーはそれを含む要素のサブツリー以外の領域を再レイアウトまたは再描画する必要がないことを判断します。ただし、もし `<article>` が（`height: auto` の場合のように）そのコンテンツによってサイズが変わるようスタイル付けされている場合は、ブラウザーがサイズの変化に対応する必要があるかもしれません。

各記事が独立していることを `contain` プロパティで伝えています。

`content` の値は `contain: layout paint` の短縮形です。これはブラウザーに、要素の内部レイアウトがページの他の部分と完全に分離しており、要素に関するすべてがその境界の内側で描画されることを伝えます。視覚的にはみ出るようなものはありません。

この情報は、ページを作成するウェブ開発者にとっては、通常知っていることであり、実際、非常に明白なことです。しかし、ブラウザーはその意図を推測することができず、記事が完全に自己完結していると仮定することはできません。したがって、このプロパティは、この事実をブラウザーに説明し、その知識に基づいて表示性能を最適化することを可能にする良い方法を提供します。

主要概念と用語
-------

この仕様では `contain` というプロパティのみを定義しています。このプロパティの値には、封じ込めの種類を指定します。

### レイアウトの封じ込め


```css
article {
  contain: layout;
}
```


レイアウトは通常、文書全体がスコープになっています。つまり、文書全体の中から 1 つの要素を動かしただけで、すべてが動かされたかのように扱われます。 `contain: layout` を使うことで、ブラウザーに対して必要な要素のみを伝えることができます。このプロパティを指定した要素の中の全てがその要素によって封じ込められ、その他の要素には影響せず、そしてその包含ブロックは独立した整形コンテキストになります。

加えて、以下の点に注意する必要があります。

* `float` レイアウトはこのプロパティとは独立して作用します。
* レイアウトの封じ込めの境界でマージンが相殺されることはありません。
* レイアウトのコンテナーは `absolute`/`fixed` による位置指定の子要素の包含ブロックになります。
* この包含ボックスは重ね合わせコンテキストを作ります。従って `z-index` を使用することができます。
### ペイントの封じ込め


```css
article {
  contain: paint;
}
```


ペイントの封じ込めは、基本的に、ボックスを主要ボックスのパディングエッジでクリッピングします。視覚的なはみ出しは許されません。 `paint` 封じ込めにも `layout` 封じ込めと同じことが当てはまります（上記を参照）。

もうひとつの利点は、包含ボックスが画面外にある場合、ブラウザーはその内包する要素を描く必要がないことです — これらはそのボックスによって完全に内包されているので、画面外にあるに違いないからです。

### サイズの封じ込め


```css
article {
  contain: size;
}
```


サイズの封じ込めを単独で使用した場合、表示性能の最適化はあまり期待できません。しかし、要素の子のサイズが要素自体のサイズに影響しないことを意味し、そのサイズは子がないものとして計算されます。

もし、`contain: size` をオンにした場合は、これを適用した要素のサイズも指定する必要があります。もし、手動でサイズを指定しない場合は、ほとんどの場合、サイズがゼロになってしまいます。

### スタイルの封じ込め


```css
article {
  contain: style;
}
```


名前に反して、スタイルの封じ込めは、 Shadow DOM で得られるようにスタイルを封じ込めるわけではありません。主な使用例は、 CSS カウンター がある要素で変更され、それがツリーの残りの部分に影響する可能性がある状況を防ぐことです。

`contain: style` を使用すると、`counter-increment` と `counter-set` プロパティがそのサブツリーにのみ限定された新しいカウンターを作成することを保証します。

**メモ:** `style` の封じ込め仕様上「リスクがあり」、どこでも対応しているとは限りません (現在 Firefox は対応していません)。

### 特殊な値

封じ込めの特殊な値が 2 つあります。

* `content`
* `strict`

1 つ目は上記の例で既に見ました。 `contain: content` を使用すると、 `layout` と `paint` の封じ込めが有効になります。仕様書では、この値を「広く適用してもそれなりに安全である」と説明しています。この値は `size` の封じ込めを適用しないので、子要素のサイズに依存して、ボックスのサイズがゼロになる危険性はありません。

できるだけ多くの封じ込めを得るには、 `contain: strict` を使用します。これは `contain: size layout paint` と同じ動作をしますが、おそらく以下のようにすると、 `style` に対応しているブラウザーでは封じ込めを追加することができます。


```css
contain: strict;
contain: strict style;
```

リファレンス
------

### CSS プロパティ

* `contain`
* `content-visibility`
仕様書
---

| Specification |
| --- |
| CSS Containment Module Level 2 # contain-property |
| CSS Containment Module Level 2 # content-visibility |

ブラウザーの互換性
---------

### css.properties.contain

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

### css.properties.content-visibility

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

### css.properties.contain

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

### css.properties.content-visibility

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

外部リソース
------

* An Introduction to CSS Containment
* Everything You Need to Know About the CSS `will-change` Property