最終更新日:
公開日:
レシピ
URL
ページ移動せずにアドレスバーのURLを変更する
ページを一定量スクロールしたときなどをきっかけにして、ページ移動しないでアドレスバーのURLを変更する方法について解説します。
この記事のポイント
- アドレスバーのURLだけを更新するときはpushStateメソッドかreplaceStateメソッドを使う
- pushStateメソッドはブラウザの閲覧履歴に1つのページの閲覧履歴として残る
- replaceStateメソッドは閲覧履歴が残らない
アドレスバーのURLだけ変更する
ページを一定量スクロールしたら次のページを表示するなど、ブラウザのページ移動を介さずにアドレスバーのURLだけを更新するときはHistoryオブジェクトのpushStateメソッドかreplaceStateメソッドを使います。
2つのメソッドはパラメータが共通していて非常によく似ていますが、pushStateメソッドはブラウザの閲覧履歴に残り、replaceStateメソッドは残らないという違いがあります。
通常の方法でアクセスしたときと同様にページの閲覧履歴を残すときはpushStateメソッドを使います。
この機能を活用しているサイトの例として、海外ニュースサイトの「Bloomberg.co.jp」があります。
記事ページで下までスクロールすると次の記事が読み込まれて表示され、URLも表示するページに応じて更新されるようになっています。
この仕組みはユーザー側から見ると読み込み時の空白がなく次の記事が表示されるため、まるで紙の新聞において記事から記事へ視点が移動するような、非常に滑らかな閲覧体験を提供することができます。
ここからはコードを使ってアドレスバーのURLを動的に変更する方法を解説していきます。
上記で紹介した2つのメソッドはURLの変更のみでページの読み込みは行わないため、URLの変更にあわせてページを表示するときは別途Ajaxなどでページ読み込みを行う必要があります。
以下の例を実行すると、ページに「ページ1」〜「ページ3」が表示されます。
ページを縦方向に下へスクロールしていくと、アドレスバーのURLが指定したページのURLに動的に切り替わります。
最初のURLは「url4.html」、ページ2が表示されたときは「url3.html」、ページ3が表示されたときは「url2.html」になります。
DEMOページ
ページをスクロールするとアドレスバーのURLが変わっていることを確認することができます。
index.html
<h1>JavaScriptレシピ</h1>
<section>
<h2>ページ1</h2>
</section>
<section>
<h2>ページ2</h2>
</section>
<section>
<h2>ページ3</h2>
</section>
style.css
section {
margin: 0;
padding: 20px;
height: 1000px;
background-color: #a7cfed;
}
section h2 {
margin: 0;
}
section:nth-child(odd) {
background-color: #90bfe4;
}
index.js
var scroll_y = window.scrollY;
var page = [
{
title: 'Page1',
url: 'url4.html'
},
{
title: 'Page2',
url: 'url3.html'
},
{
title: 'Page3',
url: 'url2.html'
}
];
// アドレスバーのURLをページ移動せずに変更する
window.addEventListener('DOMContentLoaded', function(){
window.addEventListener('scroll', function(){
scroll_y = window.scrollY;
if( 2000 < scroll_y ) {
history.pushState('', page[2].title, page[2].url);
} else if( 1000 < scroll_y ) {
history.pushState('', page[1].title, page[1].url);
} else {
history.pushState('', page[0].title, page[0].url);
}
});
});
JavaScriptのコードを解説していきます。
まず最初にスクロール量の初期化とページ情報をそれぞれの変数に代入します。
ページ情報は読み込む予定のページタイトルとURLを用意します。
ページがスクロールされると、イベントリスナーに登録したscrollが発生して内側の処理が実行されます。
外側のif文ではスクロールした量を確認します。
ここではスクロール量が2001px以上のときに「Page3」を表示し、1001px以上のときに「Page2」を表示するように設定しています。
また、スクロールが1000px以下だった場合は一番最初に表示していた「Page1」を表示します。
pushStateメソッドでは3つのパラメータを渡します。
history.pushState( stateObject, title, url);
- stateObject – 新しいページに紐づけるJavaScriptオブジェクト。指定は任意なのでnullも可。
- title – 新しいページのタイトル
- url – 新しいページのURL
今回の例ではstateObjectは渡さず、ページタイトルとURLのみ指定します。
先述の通り、pushStateメソッドはブラウザの閲覧履歴に残すことができます。
もし閲覧履歴には残さない場合はreplaceStateメソッドに全く同じパラメータを指定して実行してください。