Contents

如何在 Web 應用程式中實現無限滾動

與傳統分頁的點擊載入方法不同,無限滾動可以讓內容在使用者向下移動頁面時連續載入。此功能可以提供更流暢的體驗,尤其是在行動裝置上。

探索利用基本 HTML、樣式 CSS 和通用 JavaScript 技術實現無限滾動介面的過程。

設定前端

使用基本的 HTML 框架來展示您的內容。樣例如下:

 <!DOCTYPE html>
<html>
<head>
    <link rel="stylesheet" href="style.css" />
</head>
<body>
    <h1>Infinite Scroll Page</h1>

    <div class="products__list">
      <img src="https://fakestoreapi.com/img/71li-ujtlUL._AC_UX679_.jpg"
           alt="Jacket" />

      <img src="https://fakestoreapi.com/img/71li-ujtlUL._AC_UX679_.jpg"
           alt="Jacket" />

      <img src="https://fakestoreapi.com/img/71li-ujtlUL._AC_UX679_.jpg"
           alt="Jacket" />

      <img src="https://fakestoreapi.com/img/71li-ujtlUL._AC_UX679_.jpg"
           alt="Jacket" />

      <img src="https://fakestoreapi.com/img/71li-ujtlUL._AC_UX679_.jpg"
           alt="Jacket" />

      <img src="https://fakestoreapi.com/img/71li-ujtlUL._AC_UX679_.jpg"
           alt="Jacket" />
    </div>

    <script src="script.js"></script>
</body>
</html>

層疊樣式表 (CSS) 檔案和 JavaScript (JS) 檔案。

可捲動內容的 CSS 樣式

若要以網格狀排列呈現佔位符圖形,請在「style.css」檔案中包含以下樣式規則:

 * {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
}

html { font-size: 62.5%; }

body {
  font-family: Cambria, Times, "Times New Roman", serif;
}

h1 {
  text-align: center;
  font-size: 5rem;
  padding: 2rem;
}

img {
  width: 100%;
  display: block;
}

.products__list {
  display: flex;
  flex-wrap: wrap;
  gap: 2rem;
  justify-content: center;
}

.products__list > * {
  width: calc(33%-2rem);
}

.loading-indicator {
  display: none;
  position: absolute;
  bottom: 30px;
  left: 50%;
  background: #333;
  padding: 1rem 2rem;
  color: #fff;
  border-radius: 10px;
  transform: translateX(-50%);
}

目前,您的網頁外觀應類似於下面提供的佈局和設計:

/bc/images/initial-page-after-html-and-css-added.jpg

JS 核心實現

為了在您的 Web 應用程式中有效地融入無限滾動功能,監控使用者與內容區域底部或整個網頁的接近程度至關重要。這可以透過利用 JavaScript 和 CSS 來觀察滾動事件相對於視窗高度的位置,並相應地觸發適當的操作來實現。

 "use strict";

window.addEventListener("scroll", () => {
  if (
    window.scrollY \+ window.innerHeight >=
      document.documentElement.scrollHeight-100
  ) {
    // User is near the bottom, fetch more content
    fetchMoreContent();
  }
});

首先,我們將開發一個檢索附加佔位符資料的函數。這可以透過實施 API 呼叫或利用資料庫查詢來實現,具體取決於應用程式的特定要求。然後,檢索到的資料將用作進一步處理的輸入並在使用者介面中顯示。

 async function fetchMoreContent() {
  try {
    let response = await fetch("https://fakestoreapi.com/products?limit=3");

    if (!response.ok) {
      throw new Error("Network response was not ok");
    }

    let data = await response.json();
    console.log(data);
  } catch (error) {
    console.error("There was a problem fetching new content:", error);
  } finally {
    console.log("Fetch function fired");
  }
}

對於此項目,您可以使用 fakestoreapi 中的 API。

若要驗證您在捲動頁面時是否正在檢索數據,建議檢查瀏覽器的開發人員控制台是否有任何輸出或檢索資料成功的指示。這可以提供有關腳本功能的有用見解和回饋。

/bc/images/confirming-the-fetch-function-was-called-on-scroll.jpg

為了減輕滾動時重複資料檢索所引起的潛在效能問題,建議建立資訊的初始載入狀態,從而確保設備的高效運作。

 let isFetching = false;

為了確保以有效的方式獲取數據,有必要修改 fetch 函數的實現,以便只有在其前一個成功完成後才繼續檢索資訊。這可以透過在程式碼中引入額外的邏輯來監視和管理多個並發請求的執行流程來實現,從而防止由於對共享資源的同時操作而可能出現的任何潛在瓶頸或延遲。

 async function fetchMoreContent() {
  if (isFetching) return; // Exit if already fetching

  isFetching = true; // Set the flag to true

  try {
    let response = await fetch("https://fakestoreapi.com/products?limit=3");

    if (!response.ok) {
      throw new Error("Network response was not ok");
    }

    let data = await response.json();
  } catch (error) {
    console.error("There was a problem fetching new content:", error);
  } finally {
    console.log("Fetch function fired");
    isFetching = false; // Reset the flag to false
  }
} 

顯示新內容

為了在用戶滾動新聞源時動態更新新聞源的視覺表示,一種方法是定義一個函數,該函數修改包含表示源中每個帖子的列表項的父元素。這可以透過當使用者進一步向下捲動頁面時將新的圖像元素附加到該容器來實現,從而用較新的帖子有效地更新提要的顯示部分。

首先,選擇父元素:

 const productsList = document.querySelector(".products__list");

然後,建立一個函數來附加內容。

 function displayNewContent(data) {
  data.forEach((item) => {
    const imgElement = document.createElement("img");
    imgElement.src = item.image;
    imgElement.alt = item.title;
    productsList.appendChild(imgElement); // Append to productsList container
  });
}

總之,需要修改fetch函數,將檢索到的資訊轉送給append方法。

 async function fetchMoreContent() {
  if (isFetching) return;

  isFetching = true;

  try {
    let response = await fetch("https://fakestoreapi.com/products?limit=3");

    if (!response.ok) {
      throw new Error("Network response was not ok");
    }

    let data = await response.json();
    displayNewContent(data);
  } catch (error) {
    console.error("There was a problem fetching new content:", error);
  } finally {
    console.log("Fetch function fired");
    isFetching = false;
  }
}

事實上,無限滾動功能的實現已成功集成,從而允許在頁面向下移動時無縫導航看似無窮無盡的內容。

/bc/images/infinite-scroll-working.jpg

無限滾動增強

為了改善使用者體驗,建議在檢索新鮮內容時顯示載入指示器。這可以透過合併以下 HTML 程式碼來完成。

 <h1 class="loading-indicator">Loading...</h1>

然後選擇載入元素。

 const loadingIndicator = document.querySelector(".loading-indicator");

綜上所述,利用JavaScript實現兩個控制載入指示器顯示狀態的函數。

 function showLoadingIndicator() {
  loadingIndicator.style.display = "block";
  console.log("Loading...");
}

function hideLoadingIndicator() {
  loadingIndicator.style.display = "none";
  console.log("Finished loading.");
}

然後,將它們加入 fetch 函數中。

 async function fetchMoreContent() {
  if (isFetching) return; // Exit if already fetching

  isFetching = true;
  showLoadingIndicator(); // Show loader

  try {
    let response = await fetch("https://fakestoreapi.com/products?limit=3");

    if (!response.ok) {
      throw new Error("Network response was not ok");
    }

    let data = await response.json();
    displayNewContent(data);
  } catch (error) {
    console.error("There was a problem fetching new content:", error);
  } finally {
    console.log("Fetch function fired");
    hideLoadingIndicator(); // Hide loader
    isFetching = false;
 }
}

這使:

您的瀏覽器不支援影片標籤。

無限滾動的良好實踐

需要遵循的一些最佳實踐包括:

建議避免一次請求過多的項目,因為這可能會導致瀏覽器陷入困境並降低整體效率。

為了緩解在偵測到滾動事件時立即獲取內容而引起的頻繁網路請求的問題,一種方法是利用去抖動機制。透過採用這種技術,內容獲取操作將在滾動事件發生後延遲一段時間。因此,它有助於減少不必要的網路請求數量並提高整體效能。

雖然某些用戶可能會欣賞無限滾動的便利性,但重要的是要認識到並非每個人都有這種偏好。以分頁組件的形式提供替代選項對於那些發現它更有效率或用戶友好的人來說可能是有益的。最終,提供這兩種選項可以讓個人根據自己的需求和偏好來客製化瀏覽體驗。

當沒有更多內容要載入時通知使用者會更合適,而不是重複嘗試檢索其他資料。

掌握無縫內容加載

在網站設計中融入無限滾動可以提供無縫的用戶體驗,尤其是在行動裝置上,這在當今的數位環境中變得越來越普遍。透過遵守本文中提供的指南,開發人員可以有效地將此功能整合到他們的 Web 專案中。

設計網站時,考慮與之互動的使用者的情緒非常重要。為了提供正面的體驗,請顯示進度指示器並提供清晰的錯誤訊息,告知使用者在與網站互動期間可能出現的任何問題。