使用ReactJS构建一个具有无限滚动的图像搜索应用程序

使用ReactJS构建一个具有无限滚动的图像搜索应用程序

在本文中,我们将探讨如何使用React创建一个具有无限滚动的图像搜索应用程序。该应用程序将允许用户根据给定的查询搜索图像,并在滚动时获取和显示更多的图像。我们将使用Unsplash API来搜索和获取图像。通过本教程的最后,您将获得一个具有无限滚动功能的功能性图像搜索应用程序。

让我们来看看最终应用程序的样子:

使用ReactJS构建一个具有无限滚动的图像搜索应用程序

先决条件

  • ReactJS
  • CSS
  • JSX

方法

我们将使用Unsplash API根据用户的搜索查询来获取图像。我们将包括一个防抖动的搜索输入框,以延迟API请求到用户暂停输入。当用户滚动到页面底部时,我们还将实现无限滚动以获取更多图像。在获取图像时会显示一个预加载的旋转器。使用useState,useEffect和useRef钩子将帮助我们管理状态和执行必要的操作。

创建React应用的步骤

步骤1: 使用以下命令创建项目文件:

npx create-react-app <<Name_of_project>>

步骤2: 使用命令导航到该文件夹

cd <<Name_of_project>>

步骤3: 安装以下软件包

npm install unsplash-js lodash react-spinners

模块:

  • unsplash-js: 与Unsplash交互的 **** API。
  • lodash: 使用防抖功能的工具函数。
  • react-spinners: 在获取图片时显示加载动画。

package.json中更新的依赖项将如下所示:

"dependencies": {  
    "@testing-library/jest-dom": "^5.16.5",  
    "@testing-library/react": "^13.4.0",  
    "@testing-library/user-event": "^13.5.0",  
    "lodash": "^4.17.21",  
    "react": "^18.2.0",  
    "react-dom": "^18.2.0",  
    "react-scripts": "5.0.1",  
    "react-spinners": "^0.13.8",  
    "unsplash-js": "^7.0.18",  
    "web-vitals": "^2.1.4"  
}

项目结构

它将会如下所示。

使用ReactJS构建一个具有无限滚动的图像搜索应用程序

注意:https://unsplash.com/获取你的Unsplash API密钥。

示例: 在相应文件中编写以下代码。

  • App.js :这个文件包含了主要的逻辑。
  • App.css :这个文件包含了样式。
// App.js  
import "./App.css"; 
import { useState, useEffect, useRef } from "react"; 
import { createApi } from "unsplash-js"; 
import { debounce } from "lodash"; 
import { BounceLoader } from "react-spinners"; 
  
const unsplash = createApi({ 
    accessKey: << use your API Key>>, 
}); 
  
function App() { 
  
    // State variable to store the search phrase 
    const [phrase, setPhrase] = useState(""); 
  
    // Ref to hold the current value of the search phrase 
    const phraseRef = useRef(phrase); 
  
    // State variable to store the fetched images 
    const [images, setImages] = useState([]); 
  
    // Ref to hold the current value of the fetched images 
    const imagesRef = useRef(images); 
  
    // State variable to indicate if images are being fetched 
    const [fetching, setFetching] = useState(false); 
  
    // Ref to hold the current value of the fetching state 
    const fetchingRef = useRef(fetching); 
  
    function getUnsplashImages(query, page = 1) { 
        setFetching(true); 
        fetchingRef.current = true; 
        return new Promise((resolve, reject) => { 
            unsplash.search 
                .getPhotos({ 
                    query, 
                    page, 
                    perPage: 5, 
                }) 
                .then((result) => { 
                      
                    // Update fetching state to indicate  
                    //that images fetching is completed 
                    setFetching(false); 
                    fetchingRef.current = false; 
                    resolve(result.response.results.map((result) => 
                        result.urls.regular)); 
                }); 
        }); 
    } 
  
    useEffect(() => { 
        phraseRef.current = phrase; 
        if (phrase !== "") 
            debounce(() => { 
                setImages([]); 
                getUnsplashImages(phrase, 1).then((images) => { 
                    setImages(images); 
                }); 
                imagesRef.current = images; 
            }, 1000)(); 
    }, [phrase]); 
  
    function handleScroll(e) { 
        const { scrollHeight, scrollTop, clientHeight } = 
            e.target.scrollingElement; 
        const isBottom = scrollHeight - scrollTop <= clientHeight; 
        if (isBottom && !fetchingRef.current) { 
            getUnsplashImages( 
                phraseRef.current, 
                imagesRef.current.length / 5 + 1 
            ).then((newImages) => { 
                imagesRef.current = [...imagesRef.current, ...newImages]; 
                setImages(imagesRef.current); 
            }); 
        } 
    } 
    useEffect(() => { 
        document.addEventListener("scroll", handleScroll, { passive: true }); 
        return () => 
            document.removeEventListener("scroll", handleScroll); 
    }, []); 
  
    return ( 
        <div> 
            <input 
                type="text"
                value={phrase} 
                onChange={(e) => setPhrase(e.target.value)} 
            /> 
            <br /> 
            {images.length > 0 && images.map((url) => 
                <img src={url} />)} 
            <div> 
                {fetching && ( 
                    <div style={{ textAlign: "center" }}> 
                        <BounceLoader speedMultiplier={5} 
                            color="#000000" /> 
                    </div> 
                )} 
            </div> 
        </div> 
    ); 
} 
  
export default App;

CSS

/* App.css  */
img { 
  max-width: 100%; 
}

运行应用程序的步骤

步骤1: 在您的项目目录的终端中输入以下命令

npm start

步骤2: 在您的网页浏览器中输入以下 URL。

http://localhost:3000/

输出:

使用ReactJS构建一个具有无限滚动的图像搜索应用程序

Python教程

Java教程

Web教程

数据库教程

图形图像教程

大数据教程

开发工具教程

计算机教程