レッスンに戻る

見える画像を読み込む

importance: 4

低速のクライアントがあり、モバイル通信を節約したいとしましょう。

そのために、画像をすぐに表示せず、次のようにプレースホルダーに置き換えることにしました。

<img src="placeholder.svg" width="128" height="128" data-src="real.jpg">

当初、すべての画像はplaceholder.svgです。ページがユーザーに画像が見える位置までスクロールすると、srcdata-srcにあるものに変更することで、画像がロードされます。

これがiframeの例です。

スクロールして、画像が「オンデマンド」で読み込まれる様子を確認してください。

要件

  • ページがロードされたとき、画面上に表示される画像は、スクロールの前にすぐに読み込まれる必要があります。
  • data-srcのない通常の画像がある場合があります。コードはそれらに触れてはいけません。
  • 画像が読み込まれた後、スクロールイン/アウトしても再読み込みしないようにする必要があります。

P.S. 可能であれば、現在の位置から1ページ下または後に表示される画像を「プリロード」する、より高度なソリューションを作成してください。

P.P.S. 縦スクロールのみを処理し、水平スクロールは処理しません。

このタスク用のサンドボックスを開きます。

onscrollハンドラーは、どの画像が表示されているかを確認し、それらを表示する必要があります。

また、ページが読み込まれたときにも実行して、すぐに表示される画像を検出して読み込むようにします。

ドキュメントがロードされたときにコードを実行する必要があります。これにより、その内容にアクセスできます。

または<body>の下部に配置します。

// ...the page content is above...

function isVisible(elem) {

  let coords = elem.getBoundingClientRect();

  let windowHeight = document.documentElement.clientHeight;

  // top elem edge is visible?
  let topVisible = coords.top > 0 && coords.top < windowHeight;

  // bottom elem edge is visible?
  let bottomVisible = coords.bottom < windowHeight && coords.bottom > 0;

  return topVisible || bottomVisible;
}

showVisible()関数は、isVisible()によって実装された可視性チェックを使用して、表示されている画像を読み込みます。

function showVisible() {
  for (let img of document.querySelectorAll('img')) {
    let realSrc = img.dataset.src;
    if (!realSrc) continue;

    if (isVisible(img)) {
      img.src = realSrc;
      img.dataset.src = '';
    }
  }
}

showVisible();
window.onscroll = showVisible;

P.S. このソリューションには、現在のドキュメントスクロールより1ページ上または下に表示される画像を「プリロード」するisVisibleの変種もあります。

サンドボックスでソリューションを開く