本文完整版:《React Table 表格组件应用教程 排序、分页、搜寻过滤筛选性能实战开发》
在日常开发中,特地是外部应用的后盾零碎时,咱们经常会须要用表格来展现数据,同时提供一些操作用于操作表格内的数据。简略的表格间接用原生 HTML table 就好,但如果要在 React 中实现一个功能丰富的表格,其实是十分不容易的。
在本站之前的文章《最好的 6 个 React Table 组件具体亲测举荐》 中有提到过 react-table 这个库,如果对这个库不太理解的同学能够先理解一下,这里不再赘述。
简而言之,react-table 是一个十分弱小的库,它与常见的表格组件不同,它不负责渲染 HTML 和 CSS,而是提供了一系列的 hooks 让咱们能够灵便地构建功能强大的表格组件。
因而应用 react-table 进行开发具备肯定的难度,而本文将由浅入深地解说如何在 React 我的项目中应用 react-table 实现各种常见的需要,例如:排序、分页、搜寻过滤筛选等;同时还会联合一个残缺的案例给大家解说如何搭配应用 Material-UI 以及模仿从后端获取数据进行分页等性能。
如果你正在搭建后盾管理工具,又不想解决前端问题,举荐应用卡拉云 ,卡拉云是新一代低代码开发工具,可一键接入常见数据库及 API,内置表格等常见的前端组件,无需懂前端,仅需拖拽即可疾速搭建属于你本人的后盾管理工具,一周工作量缩减至一天,详见本文文末。
追随本文你将学到
- 如何应用 react-table 在 React 中搭建表格组件
- 如何应用 react-table 表格组件进行数据的分页、排序、搜寻过滤筛选
- react-table 实战案例:手把手教你应用 react-table 表格组件实战分页、排序、搜寻过滤筛选
扩大浏览:《顶级好用的 React 表单设计生成器,可拖拽生成表单》
react-table 装置和应用
首先,让咱们先来创立一个 React 我的项目:
npx create-react-app react-table-democd react-table-demo
而后咱们装置一下 react-table:
接下来咱们通过一个简略的示例,解说如何在 React 我的项目中应用 react-table。
假如咱们有一个订单表:
订单编号 | 姓名 | 收货地址 | 下单日期 |
---|---|---|---|
1596694478675759682 | 蒋铁柱 | 北京市海淀区西三环中路19号 | 2022-07-01 |
1448752212249399810 | 陈胜利 | 湖北武汉武昌区天子家园 | 2022-06-27 |
1171859737495400477 | 宋阿美 | 湖北武汉武昌区天子家园 | 2022-06-21 |
1096242976523544343 | 张小乐 | 北京市海淀区北航南门 | 2022-06-30 |
1344783976877111376 | 马国庆 | 北京市海淀区花园桥西北 | 2022-06-12 |
1505069508845600364 | 小果 | 广州天河机场西侧停车场 | 2022-06-07 |
咱们应用 react-table 时,须要通过一个叫做 useTable
的 hooks 来构建表格。
import { useTable } from 'react-table'
而 useTable
接管两个必填的参数:
- data:表格的数据
- columns:表格的列
所以让咱们先来定义这个订单表的 data 和 columns:
import React, { useMemo } from 'react'function App() { const data = useMemo( () => [ { name: '蒋铁柱', address: '北京市海淀区西三环中路19号', date: '2022-07-01', order: '1596694478675759682' }, { name: '陈胜利', address: '湖北武汉武昌区天子家园', date: '2022-06-27', order: '1448752212249399810' }, { name: '宋阿美', address: '湖北武汉武昌区天子家园', date: '2022-06-21', order: '1171859737495400477' }, { name: '张小乐', address: '北京市海淀区北航南门', date: '2022-06-30', order: '1096242976523544343' }, { name: '马国庆', address: '北京市海淀区花园桥西北', date: '2022-06-12', order: '1344783976877111376' }, { name: '小果', address: '广州天河机场西侧停车场', date: '2022-06-07', order: '1505069508845600364' } ], [] ) const columns = useMemo( () => [ { Header: '订单编号', accessor: 'order' }, { Header: '姓名', accessor: 'name' }, { Header: '收货地址', accessor: 'address' }, { Header: '下单日期', accessor: 'date' } ], [] ) return ( <div> <h1>React Table Demo —— 卡拉云(https://kalacloud.com)</h1> <Table columns={columns} data={data}></Table> </div> )}
你可能会留神到这里咱们应用 useMeno
来申明数据,这是因为 react-table 文档中阐明传入的 data 和 columns 必须是 memoized 的,简略来说就是能够缓存的,仅当依赖项数组外面的依赖发生变化时才会从新计算,如果对 useMemo
不相熟的同学倡议间接看 React 文档。
接着咱们构建一个 Table 组件接管 columns 和 data,并传入到 useTable
中,它会返回一系列属性,咱们就能够利用这些属性来构建 HTML table:
function Table({ columns, data }) { const { getTableProps, getTableBodyProps, headerGroups, rows, prepareRow, } = useTable({ columns, data, }) return ( <table {...getTableProps()}> <thead> {headerGroups.map((headerGroup) => ( <tr {...headerGroup.getHeaderGroupProps()}> {headerGroup.headers.map((column) => ( <th {...column.getHeaderProps()}>{column.render('Header')}</th> ))} </tr> ))} </thead> <tbody {...getTableBodyProps()}> {rows.map((row, i) => { prepareRow(row) return ( <tr {...row.getRowProps()}> {row.cells.map((cell) => { return <td {...cell.getCellProps()}>{cell.render('Cell')}</td> })} </tr> ) })} </tbody> </table> )}
因为是应用原生的 HTML table,因而是没有任何款式的, 这也是 react-table 的特点,益处是咱们能够随便自定义咱们想要的款式,比方咱们引入 github-markdown-css
:
npm i github-markdown-css
而后在我的项目中应用即可:
import React, { useMemo } from 'react'import { useTable } from 'react-table'import './App.css'+ import 'github-markdown-css'function App() { return (- <div>+ <div className="markdown-body" style={{ padding: '20px' }}> <h1>React Table Demo —— 卡拉云(https://kalacloud.com)</h1> <Table columns={columns} data={data}></Table> </div> )}
react-table 款式成果:
接下来咱们给这个表格增加更多常见的性能:排序、搜寻过滤筛选、分页等。
扩大浏览:《7 款最棒的开源 React 挪动端 UI 组件库和模版框架 - 特地针对国内应用场景举荐》
React Table 表格排序功能
如果只是想设置默认排序,咱们能够通过配置 initialState
来实现:
useTable({ columns, data, initialState: { sortBy: [ { id: 'order', desc: true } ] }})
如果要实现手动排序,就须要通过 useSortBy
这个 hooks 实现:
import { useTable, useSortBy } from 'react-table'
而后在 useTable
中传入 useSortBy
:
const { getTableProps, getTableBodyProps, headerGroups, rows, prepareRow,} = useTable( { columns, data, },+ useSortBy,)
而后咱们能够在 columns 中的某个列指定 sortType
属性,它接管 String 或 Function,对于 Function 的应用形式按下不表,而对于 String 类型,它能够接管以下三种:
- alphanumeric:字母或数字进行排序(默认值)
- basic:0 到 1 之间的数字排序
- datetime:日期排序,值必须为 Date 类型
比方在咱们这个例子中,咱们心愿能够容许对「订单编号」进行排序,那咱们则批改:
const columns = useMemo( () => [ { Header: '订单编号', accessor: 'order',+ sortType: 'basic' }, { Header: '姓名', accessor: 'name' }, { Header: '收货地址', accessor: 'address' }, { Header: '下单日期', accessor: 'date', } ], [])
接着咱们在表头处中增加排序相干的逻辑,并且依据当前列的排序状况别离显示对应的箭头,或者在没有任何排序时不显示:
<thead> {headerGroups.map((headerGroup) => ( <tr {...headerGroup.getHeaderGroupProps()}> {headerGroup.headers.map((column) => (- <th {...column.getHeaderProps()}>+ <th {...column.getHeaderProps(column.getSortByToggleProps())}> {column.render('Header')}+ <span>+ {column.isSorted ? (column.isSortedDesc ? ' ' : ' ') : ''}+ </span> </th> ))} </tr> ))}</thead>
展现成果如下:
通过上图咱们发现了一个问题:即使咱们没有对「姓名」这一列配置 sortType
,却仍然能够进行排序,这是因为一旦在 useTable
传入了 useSortBy
,则默认所有列都可进行排序,如果咱们须要对特定的列禁用排序,能够这样:
const columns = useMemo( () => [ { Header: '订单编号', accessor: 'order', sortType: 'basic' }, { Header: '姓名', accessor: 'name',+ disableSortBy: true, }, { Header: '收货地址', accessor: 'address' }, { Header: '下单日期', accessor: 'date', } ], [])
对于排序功能更多具体细节参见文档:useSortBy。
扩大浏览:《7 款最棒的开源 React UI 组件库和模版框架测评 - 特地针对国内应用场景举荐》
React Table 表格搜寻过滤筛选性能
咱们能够通过 useFilters
来实现筛选性能:
import { useTable, useFilters } from 'react-table'
同样地,须要在 useTable
中传入:
const { getTableProps, getTableBodyProps, headerGroups, rows, prepareRow,} = useTable( { columns, data, },+ useFilters,)
PS:留神 useFilters
必须位于 useSortBy
后面,否则会报错。
而后在表头中渲染筛选输入框:
<th {...column.getHeaderProps()}> {column.render('Header')}+ <div>{column.canFilter ? column.render('Filter') : null}</div></th>
这个筛选输入框的 UI 须要咱们自定义,所以咱们定义一个 TextFilter
组件:
function TextFilter({ column: { filterValue, preFilteredRows, setFilter } }) { const count = preFilteredRows.length return ( <input value={filterValue || ''} onChange={(e) => { setFilter(e.target.value || undefined) }} placeholder={`筛选 ${count} 条记录`} /> )}
这个组件接管三个参数:
- filterValue:用户输出的筛选值
- preFilteredRows:筛选前的行
- setFilter:用于设置用户筛选的值
定义完筛选组件后,咱们还将 TextFilter
传入到一个 defaultColumn
中:
const defaultColumn = React.useMemo( () => ({ Filter: TextFilter, }), [])
接着再把 defaultColumn
传入 useTable
:
const { getTableProps, getTableBodyProps, headerGroups, rows, prepareRow,} = useTable( { columns, data,+ defaultColumn, }, useFilters,)
展现成果如下:
这里咱们发现了一个问题:当点击筛选输入框时,会扭转排序形式,这是因为扭转排序的点击事件是放在 <th>
,因而咱们要阻止这个输入框的点击事件向外层冒泡:
- <div>+ <div onClick={(e) => e.stopPropagation()}> {column.canFilter ? column.render('Filter') : null}</div>
同样地,如果想要禁用某一个列的筛选,能够设置 disableFilters
:
const columns = useMemo( () => [ { Header: '订单编号', accessor: 'order', sortType: 'basic' }, { Header: '姓名', accessor: 'name',+ disableFilters: true, }, { Header: '收货地址', accessor: 'address' }, { Header: '下单日期', accessor: 'date', } ], [])
对于筛选性能更多具体细节参见文档:useFilters。
扩大浏览:《最好用的 8 款 React Datepicker 工夫日期选择器测评举荐》
React Table 表格分页性能
分页性能应用 usePagination
这个 hooks 实现:
import { useTable, usePagination } from 'react-table'
而后在 useTable
中增加分页相干的参数:
const { getTableProps, headerGroups, getRowProps,- rows + state: { pageIndex, pageSize },+ canPreviousPage,+ canNextPage,+ previousPage,+ nextPage,+ pageOptions,+ page } = useTable( { columns, data,+ initialState: { pageSize: 2 }, },+ usePagination, )
而后咱们 tbody
中的 rows
将从 page
变量中获取:
<tbody {...getTableBodyProps()}>- {rows.map((row) => {+ {page.map((row) => { prepareRow(row) return ( <tr {...row.getRowProps()}> {row.cells.map((cell) => { return <td {...cell.getCellProps()}>{cell.render('Cell')}</td> })} </tr> )})}</tbody>
咱们还须要构建一个分页器:
function Pagination({ canPreviousPage, canNextPage, previousPage, nextPage, pageOptions, pageIndex}) { return ( <div> <button onClick={() => previousPage()} disabled={!canPreviousPage}> 上一页 </button>{' '} <button onClick={() => nextPage()} disabled={!canNextPage}> 下一页 </button> <div> 第{' '} <em> {pageIndex + 1} / {pageOptions.length} </em>{' '} 页 </div> </div> )}
在 table 前面应用这个分页器:
<> <table {...getTableProps()}>... </table> <Pagination canPreviousPage={canPreviousPage} canNextPage={canNextPage} previousPage={previousPage} nextPage={nextPage} pageOptions={pageOptions} pageIndex={pageIndex} /></>
展现成果如下:
更简单的分页能够参考官网示例:Examples: Pagination。
扩大浏览:《最好用的 5 个 React select 多选下拉菜单组件测评举荐》
React table 排序、搜寻过滤筛选、分页示例代码
通过前文咱们曾经把 react-table 的根本应用都演示了一遍,你能够在此获取示例代码。
React table 实战案例
然而理论开发中的需要天然不会满足于本地数据,因而接下来咱们演示一个更加实在、残缺的例子,它将蕴含以下性能:
- 模仿从远端申请数据,并且通过服务端进行分页、筛选、排序。
- 搭配 Material-UI 构建组件
首先创立一个新的我的项目:
npx create-react-app react-table-examplecd react-table-example
而后装置相干依赖:
npm i react-table mockjs axios lodash.orderbynpm i axios-mock-adapter --save-devnpm i @material-ui/core @material-ui/icons
模仿 API
而后咱们生成 200 条订单数据,同时模仿 API 的筛选、排序和分页性能:
// mock.jsimport axios from 'axios'import MockAdapter from 'axios-mock-adapter'import Mock from 'mockjs'import _orderby from 'lodash.orderby'const { Random, mock } = Mockconst orders = new Array(200).fill(null).map(() => { return mock({ order: Random.natural(), name: Random.cname(), address: Random.province() + '-' + Random.city() + '-' + Random.county(), date: Random.date() })})const mockAPI = { start() { const mock = new MockAdapter(axios) mock.onGet('/api/orders').reply((config) => { let { filter, sortBy, page = 0, size = 10 } = config.params || {} let mockOrders = [...orders] if (filter) { mockOrders = orders.filter((order) => { return Object.values(order).some((value) => value.includes(filter)) }) } if (sortBy.length) { sortBy.forEach((sort) => { mockOrders = _orderby( mockOrders, [sort.id], [sort.desc ? 'desc' : 'asc'] ) }) } const offset = page * size mockOrders = mockOrders.slice(offset, offset + size) return new Promise((resolve) => { setTimeout(() => { resolve([ 200, { data: mockOrders, total_count: orders.length } ]) }, 500) }) }) }}export default mockAPI
而后在 App.js
中引入并开始 mock 数据:
import mockAPI from './mock'mockAPI.start()
构建根底 React Table 组件
有了下面的教训,咱们很快就能够构建一个根底的表格组件:
// components/Table.jsimport React from 'react'import { useTable } from 'react-table'import MaUTable from '@material-ui/core/Table'import TableBody from '@material-ui/core/TableBody'import TableCell from '@material-ui/core/TableCell'import TableContainer from '@material-ui/core/TableContainer'import TableHead from '@material-ui/core/TableHead'import TableRow from '@material-ui/core/TableRow'function Table({ columns, data }) { const { getTableProps, headerGroups, prepareRow, rows } = useTable({ columns, data }) return ( <TableContainer> <MaUTable {...getTableProps()}> <TableHead> {headerGroups.map((headerGroup) => ( <TableRow {...headerGroup.getHeaderGroupProps()}> {headerGroup.headers.map((column) => ( <TableCell {...column.getHeaderProps()}> {column.render('Header')} </TableCell> ))} </TableRow> ))} </TableHead> <TableBody> {rows.map((row, i) => { prepareRow(row) return ( <TableRow {...row.getRowProps()}> {row.cells.map((cell) => { return ( <TableCell {...cell.getCellProps()}> {cell.render('Cell')} </TableCell> ) })} </TableRow> ) })} </TableBody> </MaUTable> </TableContainer> )}export default Table
而后在 App.js
中申请 API 并展现:
import React, { useState, useMemo, useEffect } from 'react'import axios from 'axios'import Table from './components/Table'import mockAPI from './mock'mockAPI.start()function App() { const fetchOrders = async (params = {}) => { return axios.get('/api/orders', { params }).then((res) => { const resp = res.data setOrders(resp.data) }) } const [orders, setOrders] = useState([]) const data = useMemo(() => { return [...orders] }, [orders]) const columns = useMemo( () => [ { Header: '订单编号', accessor: 'order' }, { Header: '姓名', accessor: 'name' }, { Header: '收货地址', accessor: 'address' }, { Header: '下单日期', accessor: 'date' } ], [] ) useEffect(() => { fetchOrders() }, []) return ( <div style={{ padding: '20px' }}> <h1>React Table Example —— 卡拉云(https://kalacloud.com)</h1> <Table data={data} columns={columns} /> </div> )}export default App
展现成果如下:
服务端分页
接着咱们增加分页性能,首先增加 TablePaginationActions
组件:
// components/TablePaginationActions.jsimport React from 'react'import FirstPageIcon from '@material-ui/icons/FirstPage'import IconButton from '@material-ui/core/IconButton'import KeyboardArrowLeft from '@material-ui/icons/KeyboardArrowLeft'import KeyboardArrowRight from '@material-ui/icons/KeyboardArrowRight'import LastPageIcon from '@material-ui/icons/LastPage'import { makeStyles, useTheme } from '@material-ui/core/styles'const useStyles = makeStyles((theme) => ({ root: { flexShrink: 0, marginLeft: theme.spacing(2.5) }}))const TablePaginationActions = (props) => { const classes = useStyles() const theme = useTheme() const { count, page, rowsPerPage, onPageChange } = props const handleFirstPageButtonClick = (event) => { onPageChange(event, 0) } const handleBackButtonClick = (event) => { onPageChange(event, page - 1) } const handleNextButtonClick = (event) => { onPageChange(event, page + 1) } const handleLastPageButtonClick = (event) => { onPageChange(event, Math.max(0, Math.ceil(count / rowsPerPage) - 1)) } return ( <div className={classes.root}> <IconButton onClick={handleFirstPageButtonClick} disabled={page === 0} aria-label="first page" > {theme.direction === 'rtl' ? <LastPageIcon /> : <FirstPageIcon />} </IconButton> <IconButton onClick={handleBackButtonClick} disabled={page === 0} aria-label="previous page" > {theme.direction === 'rtl' ? ( <KeyboardArrowRight /> ) : ( <KeyboardArrowLeft /> )} </IconButton> <IconButton onClick={handleNextButtonClick} disabled={page >= Math.ceil(count / rowsPerPage) - 1} aria-label="next page" > {theme.direction === 'rtl' ? ( <KeyboardArrowLeft /> ) : ( <KeyboardArrowRight /> )} </IconButton> <IconButton onClick={handleLastPageButtonClick} disabled={page >= Math.ceil(count / rowsPerPage) - 1} aria-label="last page" > {theme.direction === 'rtl' ? <FirstPageIcon /> : <LastPageIcon />} </IconButton> </div> )}export default TablePaginationActions
而后在 Table.js
中批改如下:
import React, { useEffect } from 'react'import { useTable, usePagination } from 'react-table'+ import TableFooter from '@material-ui/core/TableFooter'+ import TablePagination from '@material-ui/core/TablePagination'+ import TablePaginationActions from './TablePaginationActions'- function Table({ columns, data }) {+ function Table({ columns, data, totalCount, onStateChange }) { const { getTableProps, headerGroups, prepareRow,- rows, + page,+ gotoPage,+ setPageSize,+ state: { pageIndex, pageSize } } = useTable( { columns, data,+ manualPagination: true,+ pageCount: totalCount },+ usePagination )+ useEffect(() => {+ onStateChange({ pageIndex, pageSize })+ }, [pageIndex, pageSize, onStateChange])+ const handleChangePage = (event, newPage) => {+ gotoPage(newPage)+ }+ const handleChangeRowsPerPage = (event) => {+ setPageSize(Number(event.target.value))+ } return ( <TableContainer> <MaUTable {...getTableProps()}>... <TableBody>- {rows.map((row, i) => {+ {page.map((row, i) => {... </TableBody>+ <TableFooter>+ <TableRow>+ <TablePagination+ rowsPerPageOptions={[5, 10, 15, 20]}+ colSpan={3}+ count={totalCount}+ rowsPerPage={pageSize}+ page={pageIndex}+ SelectProps={{+ inputProps: { 'aria-label': 'rows per page' },+ native: true+ }}+ onPageChange={handleChangePage}+ onRowsPerPageChange={handleChangeRowsPerPage}+ ActionsComponent={TablePaginationActions}+ />+ </TableRow>+ </TableFooter> </MaUTable> </TableContainer> )}export default Table
在 App.js
中减少管制分页的逻辑:
const [totalCount, setTotalCount] = useState(0)const fetchOrders = async (params = {}) => { return axios.get('/api/orders', { params }).then((res) => { const resp = res.data setOrders(resp.data) setTotalCount(resp.total_count) })}const onStateChange = useCallback(({ pageIndex, pageSize }) => { fetchOrders({ page: pageIndex, size: pageSize })}, [])
因为 Table 组件外部会触发 onStateChange
,因而不须要在 useEffect
中获取数据 ,而后传入 Table 相干属性:
- useEffect(() => {- fetchOrders()- }, [])<Table data={data} columns={columns}+ totalCount={totalCount}+ onStateChange={onStateChange}/>
展现成果如下:
服务端排序
接着咱们增加排序功能,首先批改 Table.js
:
- import { useTable, usePagination } from 'react-table'+ import { useTable, usePagination, useSortBy } from 'react-table'+ import TableSortLabel from '@material-ui/core/TableSortLabel'function Table({ columns, data, totalCount, onStateChange }) { const { getTableProps, headerGroups, prepareRow, page, gotoPage, setPageSize,- state: { pageIndex, pageSize } + state: { pageIndex, pageSize, sortBy } } = useTable( { columns, data, manualPagination: true,+ manualSortBy: true, pageCount: totalCount },+ useSortBy, usePagination ) - useEffect(() => {- onStateChange({ pageIndex, pageSize })- }, [pageIndex, pageSize, onStateChange])+ useEffect(() => {+ onStateChange({ pageIndex, pageSize, sortBy })+ }, [pageIndex, pageSize, sortBy, onStateChange]) <TableCell- {...column.getHeaderProps()}+ {...column.getHeaderProps(column.getSortByToggleProps())} > {column.render('Header')}+ <TableSortLabel+ active={column.isSorted}+ direction={column.isSortedDesc ? 'desc' : 'asc'}+ /> </TableCell>}
React table 排序功能展现成果如下:
扩大浏览:《React 实现 PDF 文件在线预览 - 手把手教你写 React PDF 预览性能》
服务端搜寻过滤筛选
而后咱们增加筛选性能,通常筛选器都是位于表格以外的,在本例子中,咱们期待在筛选框中输出的搜寻值利用在所有的列,这里咱们创立一个 TableFilter
组件:
// components/TableFilter.jsimport React from 'react'import InputBase from '@material-ui/core/InputBase'import { fade, makeStyles } from '@material-ui/core/styles'import SearchIcon from '@material-ui/icons/Search'const useStyles = makeStyles((theme) => ({ search: { position: 'relative', borderRadius: theme.shape.borderRadius, backgroundColor: fade(theme.palette.common.white, 0.15), '&:hover': { backgroundColor: fade(theme.palette.common.white, 0.25) }, marginRight: theme.spacing(2), marginLeft: 0, width: '100%', [theme.breakpoints.up('sm')]: { width: 'auto' } }, searchIcon: { width: theme.spacing(7), height: '100%', position: 'absolute', pointerEvents: 'none', display: 'flex', alignItems: 'center', justifyContent: 'center' }, inputRoot: { color: 'inherit' }, inputInput: { padding: theme.spacing(1, 1, 1, 7), transition: theme.transitions.create('width'), width: '100%', [theme.breakpoints.up('md')]: { width: 200 } }}))const GlobalFilter = ({ globalFilter, setGlobalFilter }) => { const classes = useStyles() return ( <div className={classes.search}> <div className={classes.searchIcon}> <SearchIcon /> </div> <InputBase value={globalFilter || ''} onChange={(e) => { setGlobalFilter(e.target.value || undefined) }} placeholder={`在此输出搜寻值`} classes={{ root: classes.inputRoot, input: classes.inputInput }} inputProps={{ 'aria-label': 'search' }} /> </div> )}export default GlobalFilter
而后在 Table.js
中应用这个组件,并增加筛选逻辑:
- import { useTable, usePagination, useSortBy } from 'react-table'+ import { useTable, usePagination, useSortBy, useGlobalFilter } from 'react-table'+ import TableFilter from './TableFilters'function Table({ columns, data, totalCount, onStateChange }) { const { getTableProps, headerGroups, prepareRow, page, gotoPage, setPageSize,- state: { pageIndex, pageSize, sortBy } + state: { pageIndex, pageSize, sortBy, globalFilter },+ setGlobalFilter } = useTable( { columns, data, manualPagination: true, manualSortBy: true,+ manualGlobalFilter: true, pageCount: totalCount },+ useGlobalFilter, useSortBy, usePagination ) useEffect(() => {- onStateChange({ pageIndex, pageSize, sortBy })+ onStateChange({ pageIndex, pageSize, sortBy, filter: globalFilter })- }, [pageIndex, pageSize, sortBy, onStateChange])+ }, [pageIndex, pageSize, sortBy, onStateChange, globalFilter]) <TableContainer>+ <TableFilter+ globalFilter={globalFilter}+ setGlobalFilter={setGlobalFilter}+ />
在 App.js
中接管 filter 值并传递给 API:
const onStateChange = useCallback(- ({ pageIndex, pageSize, sortBy }) => {+ ({ pageIndex, pageSize, sortBy, filter }) => { fetchOrders({ page: pageIndex, size: pageSize, sortBy,+ filter }) }, [])
react-table 搜寻过滤筛选展现成果如下:
扩大浏览:《5款 React 实时音讯提醒告诉(Message/Notification)组件举荐与测评》
React Table 组件与卡拉云
后面咱们展现了如何在 react-table 中搭配 Material-UI 构建一个残缺的表格组件,置信你曾经上手 react-table 的用法,而这只是 react-table 性能的冰山一角,还有更多例如:动静展现列、分组开展、动画、拖拽、行内编辑、虚构列表等,所以 react-table 的弱小能够让你搭配出更多自定义性能。
其实如果你只想专一在解决问题,而不想把工夫节约在调试前端问题上的话,举荐应用卡拉云,卡拉云是新一代低代码开发工具,不仅能够拖拽生成带有排序、分页、搜寻性能的表格组件等多种你须要的前端组件。与各类前端框架相比,卡拉云齐全不必写前端代码,极大晋升了开发效率,1 周的工作量,当初只有 30 分钟即可实现。卡拉云间接注册即可开始应用,后盾搭建实现后,还能一键分享给共事一起应用。
可一键分享给共事一起应用:https://my.kalacloud.com/apps/q6p23cqa29/published
卡拉云可帮你疾速搭建企业外部工具,下图为应用卡拉云搭建的外部广告投放监测零碎,无需懂前端,仅需拖拽组件,10 分钟搞定。你也能够疾速搭建一套属于你的后盾管理工具。
卡拉云是新一代低代码开发平台,与前端框架 Vue、React等相比,卡拉云的劣势在于不必首先搭建开发环境,间接注册即可开始应用。开发者齐全不必解决任何前端问题,只需简略拖拽,即可疾速生成所需组件,可一键接入常见数据库及 API,依据疏导简略几步买通前后端,数周的开发工夫,缩短至 1 小时。立刻收费试用卡拉云。