レンダリング ブロック CSS

デフォルトでは、CSS はレンダリング ブロック リソースとして扱われます。つまり、ブラウザは CSSOM が構築されるまで、処理済みのコンテンツをレンダリングしません。CSS をシンプルに保ち、できるだけ早く配信し、メディアタイプとクエリを使用してレンダリングの問題を解決してください。

レンダリング ツリーの構築では、クリティカル レンダリング パスでレンダリング ツリーを構築するために DOM と CSSOM の両方が必要であることがわかりました。このため、HTML と CSS はどちらもレンダリング ブロック リソースであるため、パフォーマンスに大きく影響します。DOM がなければ何もレンダリングできないので HTML は明白ですが、CSS の要件はわかりにくいかもしれません。CSS でレンダリングをブロックせずに一般的なページをレンダリングしようとすると、どうなるでしょうか。

まとめ

  • デフォルトでは、CSS はレンダリング ブロック リソースとして扱われます。
  • メディアタイプとメディアクエリを使用して、一部の CSS リソースを非レンダリング ブロックとしてマークできます。
  • ブラウザは、ブロック動作の有無にかかわらず、すべての CSS リソースをダウンロードします。
CSS を使った NYTimes
The New York Times with CSS
CSS を使用しない NYTimes
The New York Times without CSS(FOUC)

上記の例では、NYTimes ウェブサイトを CSS の有無にかかわらず表示しています。これは、CSS が利用可能になるまでレンダリングがブロックされる理由を示しています。CSS がないと、ページは比較的使用不能になります。右側の画面は多くの場合、「Flash of Unstyled Content(FOUC)」と呼ばれます。ブラウザは、DOM と CSSOM の両方を取得するまでレンダリングをブロックします。

CSS はレンダリング ブロック リソースです。データをできるだけ早くお客様に提供し、最初のレンダリングまでの時間を最適化します。

しかし、ページを印刷するときや大画面に投影するときなど、特定の条件でのみ使用される CSS スタイルがある場合はどうでしょうか。これらのリソースでのレンダリングをブロックする必要がないと便利です。

CSS の「メディアタイプ」と「メディアクエリ」を使用すると、次のユースケースに対応できます。

<link href="style.css" rel="stylesheet" />
<link href="print.css" rel="stylesheet" media="print" />
<link href="other.css" rel="stylesheet" media="(min-width: 40em)" />

メディアクエリは、メディアタイプと、特定のメディア機能の条件を確認する 0 個以上の式で構成されます。たとえば、最初のスタイルシートの宣言ではメディアタイプやメディアクエリを指定していないため、すべてのケースに適用されます。つまり、常にレンダリング ブロックになります。一方、2 番目のスタイルシート宣言は、コンテンツが印刷されるときにのみ適用されます。たとえば、レイアウトの並べ替えやフォントの変更などを行う場合があるため、このスタイルシートの宣言では、最初に読み込まれたページのレンダリングをブロックする必要はありません。最後に、最後のスタイルシートの宣言で「メディアクエリ」を指定します。これはブラウザによって実行されます。条件が一致する場合、ブラウザはスタイルシートがダウンロードされて処理されるまでレンダリングをブロックします。

メディアクエリを使用することで、表示と印刷などの特定のユースケースや、画面の向きの変化、サイズ変更イベントなどの動的な条件に合わせて表示を調整できます。スタイルシート アセットを宣言する際は、メディアタイプとメディアクエリに十分注意してください。クリティカル レンダリング パスのパフォーマンスに大きく影響します。

実践的な例をいくつか考えてみましょう。

<link href="style.css" rel="stylesheet" />
<link href="style.css" rel="stylesheet" media="all" />
<link href="portrait.css" rel="stylesheet" media="orientation:portrait" />
<link href="print.css" rel="stylesheet" media="print" />
  • 1 つ目の宣言はレンダリング ブロックであり、すべての条件で一致します。
  • 2 つ目の宣言もレンダリング ブロックです。「all」がデフォルトのタイプであるため、タイプを指定しない場合は暗黙的に「all」に設定されます。したがって、1 番目と 2 番目の宣言は実際には同等です。
  • 3 つ目の宣言には、ページの読み込み時に評価されるダイナミック メディアクエリが含まれています。ページの読み込み中のデバイスの向きによって、portrait.css がレンダリング ブロックになる場合とされない場合があります。
  • 最後の宣言はページの印刷時にのみ適用されるため、ページが最初にブラウザで読み込まれるときにレンダリング ブロックは発生しません。

なお、「レンダリング ブロック」とは、ブラウザがそのリソースでページの最初のレンダリングを保留する必要があるかどうかのみを指します。いずれの場合も、ブラウザは CSS アセットをダウンロードしますが、非ブロック リソースの優先度は低くなります。

フィードバック