概要webサービスを公開するにあったて必ず使われることになるのがブラウザです。ブラウザがユーザーにwebページを表示する仕組みを理解することで、フロントエンド開発に役立てたり、ページ表示までのレスポンスの改善などに役立てていきたいと思い、今回ブラウザのレンダリングの仕組みの基本事項についてまとめました。レンダリングの流れユーザーがwebブラウザにURLを入力すると、ブラウザはURLを元に指定のサーバーにTCP/IPプロトコルに基づいてリクエストを送ります。その後サーバはクライアントに対してレスポンスします。以降のレスポンスとして受け取るHTML,CSS,Javascriptをどう処理して画面に表示するのかをレンダリングと定義して、その処理の流れについてみていきます。pathと呼ばれています)![progressive-rendering.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274080/0f378229-031d-7314-a828-4e9945530fb8.png)https://developers.google.com/web/fundamentals/performance/critical-rendering-path-![レンダリングの流れ.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274080/8db46249-aa8b-eb64-e0ba-0d109f555235.png)+![レンダリングの流れ.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274080/78cd1ed1-dc53-5c23-e5c5-9737e38b00e4.png)++ブラウザがWebページをレンダリングする仕組みは上のような一連の流れになっています。以下でその一つ一つの工程の内容をみていきます。オブジェクトモデルの構築ブラウザはページを描画する前に、DOMとCSSOMツリーを構築する必要があります。このDOMとCSSOMツリーを構築する工程は「オブジェクト構築モデル」といいます。バイト→文字列→トークン→ノード→オブジェクトモデル(DOM/CSSOM)という流れでオブジェクトモデルは構築されます。取得した文字列をトークンに変換します。standard](https://html.spec.whatwg.org/multipage/)によって規則が定められています。字句解析トークンは\<html>や\<head>といったオブジェクトに変換されます。字句解析で作られたオブジェクトはオリジナルのマークアップの定義に基づいた親子関係をもつ木構造に整形されます。\<html>オブジェクトは\<body>オブジェクトの親で、\<body>は\<p>の親でといったようなHTMLのマークアップでみる構成になります。この最後のプロセスの最終的な成果物が描画するページのDOMとなります。CSSOMツリーの構築![cssom-tree.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274080/a3019e6b-676c-270f-ae96-b67dd573721c.png)ブラウザでDOMを構築している際にドキュメントのheadタグで外部のcssスタイルシートを参照しているlinkタグに遭遇すると、ブラウザはページのレンダリングにこのリソースが必要であると解釈してこのリソースに対するリクエストを即座にディスパッチし、CSSを受け取ります。ブラウザがCSSを解釈して処理できるようにするために、受けっとたCSSをHTMLのDOMツリー構築の時と同じように処理していきます。JavaScriptの実行-各種リソースを読み込んだ後は、JavaScriptエンジンによってJavaScriptのコードが解析、実行されます。-まずJavaScriptのコードが字句解析されトークンとなり、次に構文解析され抽象構文木となり、最後にコンパイルされて実行可能なファイルとなり実行されます。レンダリングツリーの構築-コンテンツを記述したDOMツリーとドキュメントに適用するスタイルルールを記述したCSSOMツリーを結合することでレンダリングツリーを構築する必要があります。レンダリングツリーは各表示要素のレイアウトを計算するために使用され、画面にピクセルをレンダリングするペイント処理の入力となります。+DOMツリーとCSSOMツリーを組み合わせることでレンダーツリーを作ります。レンダーツリーは個々の要素のレイアウトの計算し、またピクセルを画面に描画するプロセスである「ペイント」の工程が必要とする値を生成します。-レンダリングツリー構築の手順として、DOMツリーの各要素に対してどのCSSプロパティがマッチするかを計算します。CSSのルールセットにはh1やpのようなCSSセレクタと、widthやcolorのようなCSSプロパティがあり、最初にCSSセレクタによってDOMツリーの要素とCSSルールのマッチングを行います。その後、各DOM要素にどのCSSプロパティがマッチングするかを計算します。レンダーツリーの生成+DOMツリーとCSSOMツリーを合成してレンダーツリーを生成します。ページの描画に使われる全てのDOMと個々のオブジェクトに使われるCSSをそれぞれ組み合わせます。CSSセレクタのマッチンング-レンダリングエンジンはCSSセレクタを右側から順に評価していきます。CSSプロパティのマッチング-どのCSSプロパティがDOM要素に適用されるかをレンダリングエンジンが決定するための詳細度という仕組みがあります。詳細度には3つのレベルがあり、各CSSセレクタとの関連は次のようになっています+これらの工程によりページの描画に必要な全てのノードとスタイル情報を含んだレンダツリーが作成されます。レイアウト+レンダリングツリーの構築まででどの要素が描画されてどんなスタイルが適用されるかが決まりました。Cとなっていて1つでも上位レベルが含まれる場合はそれが優先され、同じレベルでは値が大きい方が優先されます。`color:red`の方が優先されます。詳細度が同じ場合は後に定義されたCSSルールセットが適用されますそのため上の例の`#id`の要素には`font-size:30px`が適用されます。レンダリングツリーのレイアウト-レイアウトの工程では端末ビューボード内での各ノードのレイアウト情報を算出しますレイアウト情報には要素の大きさやmargin/padding、x/y/z軸の位置などが含まれます。-レンダリングエンジンはレンダリングツリーのルート要素から順番に各要素が持つCSSプロパティを元にレイアウト情報を決めていきます。+ページ上での個々の要素の正確なサイズや位置を求めるために、レンダーツリーのルートからブラウザはトラバースします。world!</div></div></body></html>```-上のようなHTMLの場合、`viewport`がデバイスのサイズで倍率が1倍ということに決まります。-ネストされた2つのdivがあり、1つ目のdivがviewportの幅の50%になり、2つ目のネストしたdivの幅は親のdivの50%(全体の25%)になります。+上のページのコンテンツは2つのネスとされたdiv要素をもち、最初のdivはviewportの横幅の50%に位置し、2つ目のdivは親要素のdivの50%の位置となります。![layout-viewport.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274080/7aea1607-b729-279d-2cc4-076d4a2e1ce1.png)+レイアウトプロセスで出力されるものを「ボックスモデル」といいます。ボックスモデルはviewport内での個々の要素の正確な位置とサイズを算出し、相対的な値を画面上でのピクセルの絶対値に変換します。レンダリングツリーの描画-webページの描画にはペイントとコンポジットの2つの工程があります。ペイント-各レイヤごとにテキストや色、画像などをピクセルに書き込みます。ピクセルへの書き込み--の2つの工程からなります。ペイント+最後に、レイアウトプロセスで得ることができた個々の要素のサイズと位置情報を最終的な正確なピクセル値へと変えるペイント(又はラスタライゼイション)の行程が行われます-まず前の手順で構築したレンダリングツリーを元にグラフィックエンジンのための命令リストを作成します。命令リストでは「どのピクセルに何色を入れるのか」という命令が入っているため、その命令を元にグラフィックエンジンがピクセルの描画を行います。-次にピクセルの書き込みを行います(ラスタライゼーション)。ピクセルの書き込みはレイヤ単位で行われ、position:abosolute;やopacityといったCSSプロパティなどz軸を考慮する必要のある要素が存在する場合は新しいレイヤが作成されます。コンポジット-ピクセルを書き出したレイヤを合成してレンダリング結果を出力します。+レンダーツリーの構築、レイアウト、そしてペイントの各工程に要する時間はドキュメントのサイズ、適用されたスタイルそしてデバイスによって様々です。+それぞれの工程の合計時間を最小化することでクリティカルレンダリングパスを最適化することができます。レンダリングエンジンとJavaScriptエンジンブラウザにはレンダリングエンジンとJavaScriptエンジンという2つのエンジンが動作しています。**レンダリングエンジン**HTMLやCSSなどを解析し、実際の画面に描画するためのもの。レンダリングエンジンによってHTMLやCSSの解釈に差があるためデザインがブラウザによって崩れるという問題があります。**JavaScriptエンジン**JavaScriptを実行するためのエンジン。Edgeの新しいversion(Chromiumベース)が来年の1月15日にリリース予定です。まとめブラウザレンダリングの仕組みを各工程ごとにみることで、ページライフサイクルのイベントがどの工程で発生するのかをきちんと理解できるようになりました。レンダリングの仕組みの知識を元に、ブラウザの開発ツールを駆使して開発時にデバッグやパフォーマンスのボトルネックの分析、改善に役立てていきたいと思います。