1. ホーム
  2. Web制作
  3. html5

ウェブアプリのページスクロールラグの解決策を詳しく解説

2022-02-01 05:24:27

モバイルブラウザが現在のページをスクロールしているとき(場合によってはページのズームも)、デフォルトの動作がブロックされ、ページが強制的に静止するため、ページをスクロールするときに吃音感があり、ユーザーエクスペリエンスが低下します。

具体的には、touchstart イベントオブジェクトは true cancelable プロパティを持っているので、リスナーは preventDefault() メソッドでそのデフォルト動作を阻止できることになります。しかし、ブラウザはリスナーが preventDefault() を呼び出すかどうかを事前に知ることができないため、リスナーが実行を終了するのを待ってデフォルトの動作を強制するしかなく、時間がかかり、場合によっては非常に時間がかかるため、ページの遅延につながる可能性があります。リスナーが空の関数であっても、やはり空の関数の実行には時間がかかるので、多少は吃音になります。

addEventListenerのuseCaptureパラメータは

基本的な考え方: xxx.addEventListener('eventName', function(xxx){xxx}, useCapture)。

第1パラメータはイベント名(onなし、例:"click")、第2パラメータはイベント処理を受け取る関数、第3パラメータはuseCaptureを指定します。

この意味を、より直感的に理解するために、直接的な例を挙げて簡単に説明します。

<div id="level1">
  <div id="level2">
    <div id="level3"> Please click here</div>
  </div>
</div>
<div id="info">
</div>


var level1 = document.getElementById("level1");
var level2 = document.getElementById("level2");
var level3= document.getElementById("level3");
var info = document.getElementById("info");
outDiv.addEventListener("click", function () { info.innerHTML += "level1" + "<br>"; }, false);
middleDiv.addEventListener("click", function () { info.innerHTML += "level2" + "<br>"; }, false);
inDiv.addEventListener("click", function () { info.innerHTML += "level3" + "<br>"; }, false);

上記のコードに基づき、useCaptureをtrueとfalseに設定した場合の効果を確認します。

すべてfalseの場合、トリガーの順番は、level3, level2, level1です。
全てTrueの場合、トリガはレベル1、レベル2、レベル3の順となります。
レベル1が真で他が偽の場合、トリガーはレベル1、レベル3、レベル2の順になります。
レベル2が真、他が偽の場合、トリガはレベル2、レベル3、レベル1の順になります。
レベル3が真、他が偽、トリガ順序は、レベル3、レベル2、レベル1
レベル1が偽、他が真、トリガ順序はレベル2、レベル3、レベル1
レベル2が偽、他が真、トリガ順序は、レベル1、レベル3、レベル2
レベル3が偽で、それ以外が真の場合、トリガーはレベル1、レベル2、レベル3の順となる

以上の結果から、次のような結論が導き出された。

トリガーの順序は、常に真が偽に先行する。
が複数ある場合、外側のレイヤーは内側のレイヤーより先にトリガーされます。
一つ以上が偽の場合、内側のレイヤーのトリガーが外側のレイヤーに優先します。

イベントの動作を制御する受動的な属性

次のように使用します。

addEventListener('eventName', function(xxx){xxx}, {
    capture: false,
    passive: false,
    once: false
})

3つの属性はすべてブーリアン・スイッチで、デフォルト値はすべてfalseである。

capture: 以前の useCapture パラメータと同等です。
once: リスナーが1回限りのイベントであり、1回実行すると自動的に削除されることを意味します。
passive: ウェブアプリのタッチイベント用

モバイルブラウザでイベントを使用する場合、80%のスクロールイベントリスナーがデフォルトの動作を防いでいないことが知られており、ほとんどの場合、ブラウザは無駄に待機していることになります。そこで、パッシブリスナーが生まれました。パッシブとは "submissive" つまり、イベントのデフォルト動作にノーと言わないという意味です。ブラウザはリスナーがパッシブであることを知っているので、リスナー内の JavaScript コードとブラウザのデフォルト動作の両方を、両方のスレッドで実行することが可能です。

この記事がお役に立てれば幸いです。また、Scripting Houseを応援していただければ幸いです。