使用React+exprss+Mockjs开发自适应伸缩响应列表分页组件

使用React+Mockjs开发自适应伸缩列表分页组件


项目预览

在这里插入图片描述

项目技术栈

  • create-react-app脚手架
  • express 后台服务,跨域设置,模拟数据库limit操作
  • mockjs根据指定数据结构生成随机数据

项目目录src目录

|   App.css
|   App.js
|   index.js
|
+---components
   +---Pagination
   |       Pagination.css
   |       Pagination.js
   |
   \---Posts
           Posts.css
           Posts.js

后台服务

在项目目录server下新建server.js核心逻辑如下:

// 获取文章列表
app.get('/posts', (req, res) => {
    let posts_data = [];
    for(let i=0;i<100;i++){
        posts_data.push(
            Mock.mock({
                id: i+1,
                title: Random.cparagraph(1),
                content: Random.cparagraph(2,5),
                author: Random.cname(),
                time: Random.datetime('yyyy-MM-dd hh:mm:ss'),
                'like|1-1000': 1
            })
        )
    }

    // 获取当前页数  以及 每页展示的条数
    let perPageNumber = Number(req.query.perPageNumber ? req.query.perPageNumber : 10);
    let currentPage = Number(req.query.currentPage ? req.query.currentPage : 1);
    let totalPage = Math.ceil(posts_data.length/perPageNumber)

    // 模拟数据库操作 limit 截取数组中对应的数据
    let start = (currentPage-1)*perPageNumber
    let end = perPageNumber*(currentPage) <= posts_data.length ? perPageNumber*(currentPage): posts_data.length
    posts_data = posts_data.slice(start, end )

    res.json({ content: posts_data, currentPage, totalPage })

})

前端展示核心部分

pagination/pagination.js 涉及自动变换分页的形态改变逻辑

import React from 'react'
import './Pagination.css'

const Pagination = ({ totalPage, currentPage, requestPostsByPage }) => {

    let liArr = []
    let allPageArr = []
    let max = 10

    for(let i=0;i<totalPage;i++){
       allPageArr.push(i+1)
    }

    // 首先判断总页数 当总页数小于10时
    if(allPageArr.length <= max){  //[...allPageArr.slice(0,max-3),'…', ...allPageArr.slice(-2)] 
        liArr = allPageArr
    }else{

        // 当总页数大于10 当前页小于5时
        if( currentPage < 5 ){
            liArr = [...allPageArr.slice(0,5),'…', totalPage]
        }else{
             // 当总页数大于10 当前页小于 totalPage-5 时
            if(currentPage <= totalPage-5){
                liArr = [1, '…', ...allPageArr.slice(currentPage-1,currentPage+2),'…', totalPage]
            }else{ // 当总页数大于10 当前页大于 totalPage-5 时
                liArr = [1, '…', ...allPageArr.slice(totalPage-5, totalPage)]
            }
        }
    }

    return (
        <nav>
            <ul className="list-pages">
            <li className="list-pages-item" onClick={() => requestPostsByPage(currentPage-1)}>&lt;</li>
            { liArr.map( (v,index) => (
                <li className={ v !== '…' ? ( currentPage === v ? "list-pages-item list-pages-item-active": 'list-pages-item' ): '' } key={index} onClick={() => requestPostsByPage(v)}>
                    { v }
                </li>
            ))}
            <li className="list-pages-item" onClick={() => requestPostsByPage(currentPage+1)}>&gt;</li>
            </ul>
        </nav>
    )
}

export default Pagination

src/App.js 涉及state定义,分发处理

const [posts, setPosts] = useState([])
  const [loading, setLoading] = useState(false)
  const [currentPage, setCurrentPage] = useState(10)
  const [totalPage, setTotalPage] = useState(1)
  const [perPageNumber, setPerPageNumber] = useState(3)

  useEffect(() => {
    const requestPosts = async () => {
      setLoading(true);
      const res = await axios.get('http://localhost:3001/posts', { params: { currentPage, perPageNumber } } )
      setPosts(res.data.content)
      setTotalPage(res.data.totalPage)
      setLoading(false);
    }
    // 调用请求
    requestPosts()
  }, [currentPage, perPageNumber])

  // console.log(posts)
  
  const requestPostsByPage = (v) => {
    if(v !== '…'){
      // 边界处理
      if( v === 0 || v > totalPage) return;
      setCurrentPage(v)
    }
  }

项目源码仓库

猜你喜欢

转载自blog.csdn.net/WU5229485/article/details/95036036