【JS】DOMContentLoadedとloadの違いについて学ぼう!
公開日 :
- コーディング
こんにちは!AndHAエンジニアチーム、新入社員のイガラシです。
コーディング初学者の私はJavaScriptを勉強している真っ只中。そんな折、addEventListenerメソッドの引数として使用される「DOMContentLoaded」と「load」って何が違うの?と疑問に思い、この2つの違いについて調べてみました。
初学者にも分かりやすいようにまとめてみたので、同じ疑問を抱いている方は是非参考にしてみてください!
目次
そもそもDOMってなに?
DOM(Document Object Model)は、簡単に言うと「ブラウザがHTMLを解析する際に生成するデータ構造」のことです。各要素は階層構造(ツリー構造)で表現され、それをDOMツリーと呼びます。
JavaScriptを使ってWebページに動きをつけたい時、JavaScript単体ではソースコード上から直接HTMLを操作することはできません。そこでDOMにアクセスしてHTMLを操作します。これをDOM操作と言います。
DOMを通すことで、HTMLファイルの中身をそれぞれオブジェクトとして捉え、JavaScriptから特定のオブジェクトにアクセスすることで、Webページの見た目を変更することができます。
例えば、document.bodyは、bodyタグを表すオブジェクトということになります。
// HTML側のbodyの背景を青に変える
document.body.style.background = 'blue';
上記は、HTML側の背景色を青色に変えるコードですが、これはDOM操作と言えます。
つまりDOMとは、JavaScriptからHTMLの「どこ」に「何」をするのかを実現するための仕組みということになります。
Webページの読み込み順
細かいところは省略させていただき、Webページの読み込み順を大きく2段階で表現すると、
- DOMツリーを読み込む
- 画像、CSSなどの外部ファイルを読み込む
となります。
1のタイミングでHTMLタグを樹形図のように表し、その構造を書き出します。つまり、全体の骨組みづくりをしています。
2では、骨組み完成後、使われている画像やCSSを読み込んでページに肉付けをして完成させていきます。
このように、Webページを構成している要素には読み込まれる順序が決まっています。
DOMContentLoadedはDOMツリー読み込み後に発火
DOMContentLoadedはDOMツリーの読み込み完了後に発火します。
つまり、HTML文書の読み込みと解析が完了したタイミングで動き出すため、外部ファイルの読み込み完了を待ちません。
document.addEventListener('DOMContentLoaded',
function() {
console.log('DOMツリーの読み込み完了');
}
);
上記の場合、画像やCSSの外部ファイルが読み込まれる前に「DOMツリーの解析完了」とコンソールに表示されることになります。
loadはページ全体の読み込み完了で発火
loadはDOMツリーの読み込み完了後、画像やCSSの外部ファイルの読み込みも全て完了した時点で発火します。
そのため、「load」の方が「DOMContentLoaded」よりイベントの発火が遅いのです。
window.addEventListener('load',
function() {
console.log('ページ全体の読み込み完了');
}
);
この場合、外部ファイルを含むすべてのリソースの読み込みが完了してから「ページ全体の読み込み完了」と表示されることになります。
発火タイミングの比較
実際にソースコードを動かして比較してみました。
想定
window.addEventListener('load',
function() {
console.log('ページ全体の読み込み完了');
}
);
document.addEventListener('DOMContentLoaded',
function() {
console.log('DOMツリーの読み込み完了');
}
);
上記のように記載すると、本来は上から順に実行されるので、
- ページ全体の読み込み完了
- DOMツリーの読み込み完了
の順に表示されると思いますよね。
ですが、実際はDOMツリーの解析後に画像やCSSの解析を行うため、ページ読み込み完了の方が時間がかかるので、
- DOMツリーの読み込み完了
- ページ全体の読み込み完了
の順で表示されるはずです。
検証結果
想定通りの結果になっていますね!
また、DOMContentLoadedは「document」オブジェクト、loadは「window」オブジェクトで発生するという点も異なっているので、記述する際は注意が必要です。
document と window
Windowオブジェクトは、最上位(グローバル)オブジェクトで、JavaScriptが動作しているブラウザのWindowを指します。
Documentオブジェクトは、Windowオブジェクトの下に位置し、主にDOMツリーへのアクセスに使用します。
documentプロパティは「window.document」を「document」と省略して記述します。
最後に
ここまで解説してきたDOMContentLoadedとloadの違いですが、理解していればきちんと使い分けることができるはずです!
本記事が、JavaScriptを使ってコーディングしている初学者の皆さんにとって参考になれば幸いです。
それではまた!