React Table 教程:項(xiàng)目設(shè)置、useTable 和 useFilter
表用戶界面無處不在,最常用且組織良好的 UI 受到用戶和開發(fā)人員的青睞。它使數(shù)據(jù)看起來簡單且易于訪問。作為 ReactJS 開發(fā)人員,您可能聽說過 React Table V7;也可能很少有人實(shí)施了它。如果您正在尋找通過示例解釋 React Table V7 的教程,那么您選擇了正確的博客。今天我們在這里為您提供一個(gè)反應(yīng)表教程。
我理解當(dāng)您嘗試學(xué)習(xí)新事物時(shí)它是多么具有挑戰(zhàn)性,但我也知道那是多么有趣!不是嗎?
React Table 的 5 個(gè)高級(jí)特性
我們已經(jīng)在本博客的開頭討論了一些功能?,F(xiàn)在讓我們討論一些可能對您有很大幫助的高級(jí)功能。
細(xì)胞渲染
假設(shè)您想要為您的客戶顯示個(gè)性化內(nèi)容或在表格內(nèi)執(zhí)行棘手的 UI 元素,如按鈕或復(fù)選框。在這種情況下,React Table 會(huì)幫上大忙。它允許 React 開發(fā)人員個(gè)性化表格中的單個(gè)單元格呈現(xiàn)。
列大小調(diào)整
另一個(gè)很棒的功能是通過 React Table 調(diào)整列的大??;此功能允許開發(fā)人員在方便時(shí)調(diào)整列的寬度。當(dāng)要顯示多個(gè)列并且您需要更多列時(shí),這將是一個(gè)有用的功能。
無限滾動(dòng)
當(dāng)有一個(gè)長表時(shí),它需要滾動(dòng),但它也會(huì)影響性能。有了 React Table,憂慮已成為過去。繼續(xù)滾動(dòng)而不用擔(dān)心性能故障,因?yàn)轫撁鏁?huì)隨著您的移動(dòng)而加載并且不會(huì)同時(shí)加載,從而節(jié)省內(nèi)存。
自定義插件
如果你想為你的 React Table 添加新功能,自定義插件允許你這樣做。這些插件還可用于添加非??岬墓δ埽绶猪?、過濾、排序以及個(gè)性化表格的外觀和行為。
服務(wù)器端渲染
由于表格需要時(shí)間來加載,服務(wù)器端渲染將極大地幫助您。它在后端加載表格并將其作為 HTML 發(fā)送到客戶端。這樣做會(huì)提高性能,因?yàn)樗鼫p少了客戶端的加載時(shí)間。
請參閱下一節(jié),其中包括本教程中涵蓋的要點(diǎn) – React Table 教程– 項(xiàng)目設(shè)置、安裝、useTable 和 useFilter。
React Table 教程目標(biāo):useTable 和 useFilter
在開始開發(fā)過程之前,讓我們先看一下下面的視頻,以便您了解我們正在構(gòu)建什么。
反應(yīng)表 v7
React Table 的創(chuàng)建者 Tanner Linsley 于 2020 年 3 月推出了 React Table v7。我們可能還記得使用 react-table 的類組件,但現(xiàn)在該庫提供了基于 Hooks 的 API 和插件來創(chuàng)建一個(gè)無障礙的 React Table。該版本被認(rèn)為是一個(gè)重大變化,因?yàn)閯?chuàng)建表格的方法、表格 UI 和樣式都發(fā)生了變化。
React Table v7 中的新特性
考慮到 React Table 發(fā)行說明,以下是 React Table v7 中的新功能:
無頭(100% 可定制,自帶 UI)
輕量級(jí)(5kb – 14kb+ 取決于使用的特性和 tree-shaking)
排序(多重和穩(wěn)定)
過濾器
動(dòng)畫化
行擴(kuò)展
列排序
可虛擬化
服務(wù)器端/受控?cái)?shù)據(jù)/狀態(tài)
自動(dòng)開箱即用,完全可控的API
可通過基于掛鉤的插件系統(tǒng)進(jìn)行擴(kuò)展
行選擇
可調(diào)整大小
旋轉(zhuǎn)和聚合
項(xiàng)目設(shè)置
使用以下命令創(chuàng)建 ReactJS 項(xiàng)目。
安裝 react-table 和 Axios
安裝反應(yīng)表和 axios。
正在尋找 Reactjs 開發(fā)公司?與業(yè)內(nèi)影響深遠(yuǎn)的ReactJS 開發(fā)公司
之一一起構(gòu)建具有動(dòng)態(tài) UI 的實(shí)時(shí) Web 應(yīng)用程序。
React 表示例入門
完成項(xiàng)目設(shè)置和安裝后,請按照以下步驟實(shí)施 React Table Example。我將把整個(gè)代碼寫在兩個(gè)文件中,即
App.js——主文件
TableContainer.js – 有一個(gè)表格組件。
導(dǎo)入 Axios 和 Hooks
使用 useState 初始化狀態(tài)
使用 Axios 獲取數(shù)據(jù)
使用效果(()=> {
axios("http://api.tvmaze.com/search/shows?q=girls")
.then((res) => {
設(shè)置數(shù)據(jù)(資源。數(shù)據(jù));
})
.catch((err) => console.log(err))
}, []);
我打電話給“http://api.tvmaze.com/search/shows?q=girls”
如果承諾得到解決,它將執(zhí)行 then 塊,我們將在其中使用 setData(res.data) 將響應(yīng)存儲(chǔ)在狀態(tài)中
如果promise 被拒絕,它將執(zhí)行 catch 塊并控制錯(cuò)誤。
定義列
準(zhǔn)備好數(shù)據(jù)后,讓我們定義表的列。列結(jié)構(gòu)將包括 -
標(biāo)題 - 列的名稱
存取器——輸入數(shù)據(jù)。
就優(yōu)化而言,我們將把它包裝在 hook useMemo 中。
常量列 = useMemo(
()=>[
{
標(biāo)題:“電視節(jié)目”,
列: [
{
標(biāo)頭:“姓名”,
存取器:“show.name”
},
{
標(biāo)題:“類型”,
存取器:“show.type”
},
{
標(biāo)題:“語言”,
存取器:“show.language”
},
{
標(biāo)題:“官方網(wǎng)站”,
存取器:“show.officialSite”,
單元格:({單元格:{值}})=>值?{價(jià)值} : ”-”
},
{
標(biāo)題:“評(píng)級(jí)”,
存取器:“show.rating.average”,
單元格:({單元格:{值}})=>值|| “——”
},
{
標(biāo)題:“狀態(tài)”,
存取器:“顯示狀態(tài)”,
},
{
標(biāo)頭:“首映”,
存取器:“show.premiered”,
單元格:({單元格:{值}})=>值|| “——”
},
{
標(biāo)題:“時(shí)間”,
存取器:“show.schedule.time”,
單元格:({單元格:{值}})=>值|| “——”
},
]
}
]
)
你可能想知道為什么我寫了“show.name”、“show.type”、“show.rating.average”等等。這是因?yàn)閿?shù)據(jù)在 show 對象中,為了訪問數(shù)據(jù),我們將使用 show。作為前綴。這是數(shù)據(jù)樣本-
自定義單元格
{
標(biāo)頭:“官方網(wǎng)站”,
存取器:“show.officialSite”,
細(xì)胞:(道具)=> {
返回 < YourComponent { ...props } / >
}},
我們可以為每一行設(shè)置自定義單元格,如上所示。一個(gè)單元格可以訪問每一行的值;您可以控制臺(tái)道具以查看它由什么組成。
我們的演示將實(shí)現(xiàn)自定義單元格以檢查 show.officalSite 是否具有值。如果它有值,那么它將返回或“-”
在 React Table 教程中實(shí)現(xiàn) useTable Hook
我們將創(chuàng)建另一個(gè)名為 TableContainer.js 的文件,我們將在其中使用 useTable 掛鉤構(gòu)建我們的 Table 組件。
它需要兩個(gè)屬性:數(shù)據(jù)和列,我們在上面的部分中已經(jīng)定義了它們。
數(shù)據(jù)由 API 響應(yīng)的數(shù)據(jù)組成
Columns 是用于定義表列的對象數(shù)組。
從“反應(yīng)”導(dǎo)入反應(yīng);從“反應(yīng)表”導(dǎo)入{useTable};
導(dǎo)出默認(rèn)函數(shù)表({列,數(shù)據(jù)}){
常數(shù) {
獲取表格道具,
getTableBodyProps,
標(biāo)頭組,
行,
準(zhǔn)備行,
} = 使用表格({
列,
數(shù)據(jù),
})
返回 (
<表{...getTableProps()}>
<頭>
{headerGroups.map(headerGroup => (
< tr {...headerGroup.getHeaderGroupProps()} >
{headerGroup.headers.map(列 = > (
< th {...column.getHeaderProps()}>{column.render('Header')}</th >
))}
))}
< /頭>
< tbody {...getTableBodyProps()} >
{rows.map((row, i) => {
準(zhǔn)備行(行)
返回 (
< tr {...row.getRowProps()} >
{row.cells.map(細(xì)胞 => {
返回 <td {...cell.getCellProps()}>{cell.render('Cell')}</td>
})}
</tr>
)
})}
</t正文>
< /表>
)}
渲染反應(yīng)表
從 TableContainer.js 導(dǎo)入表格,然后使用
從“./TableContainer”導(dǎo)入表
< div className="應(yīng)用程序" >
< h1 >< center >React 表演示< /center > > </h1 >
<表列={列}數(shù)據(jù)={數(shù)據(jù)}/></div>
執(zhí)行上述代碼片段后,您的 App.js 和 TableContainer.js 將如下所示 -
// 應(yīng)用程序.js
import React, { useState, useEffect, useMemo } from "react";從“axios”導(dǎo)入 axios;從“反應(yīng)表”導(dǎo)入{useTable};
導(dǎo)入'./App.css';
功能表({列,數(shù)據(jù)}){
常數(shù) {
獲取表格道具,
getTableBodyProps,
標(biāo)頭組,
行,
準(zhǔn)備行,
} = 使用表格({
列,
數(shù)據(jù),
})
返回 (
<表{...getTableProps()}>
<頭>
{headerGroups.map(headerGroup => (
< tr {...headerGroup.getHeaderGroupProps()}>
{headerGroup.headers.map(列 => (
< th {...column.getHeaderProps()}>{column.render('Header')}</th >
))}
</tr>
))}
< /頭>
< tbody {...getTableBodyProps()}>
{rows.map((row, i) => {
準(zhǔn)備行(行)
返回 (
< tr {...row.getRowProps()}>
{row.cells.map(細(xì)胞 => {
返回 {cell.render('Cell')}
})}
</tr>
)
})}
</t正文>
< /表>
)}
功能應(yīng)用程序(){
const [數(shù)據(jù), setData] = useState([]);
使用效果(()=> {
axios("http://api.tvmaze.com/search/shows?q=girls")
.then((res) => {
設(shè)置數(shù)據(jù)(資源。數(shù)據(jù));
})
.catch((err) => console.log(err))
}, []);
常量列 = useMemo(
()=>[
{
標(biāo)題:“電視節(jié)目”,
列: [
{
標(biāo)頭:“姓名”,
存取器:“show.name”
},
{
標(biāo)題:“類型”,
存取器:“show.type”
},
{
標(biāo)題:“語言”,
存取器:“show.language”
},
{
標(biāo)題:“官方網(wǎng)站”,
存取器:“show.officialSite”,
單元格:({單元格:{值}})=>值?{價(jià)值} : ”-”
},
{
標(biāo)題:“評(píng)級(jí)”,
存取器:“show.rating.average”,
單元格:({單元格:{值}})=>值|| “——”
},
{
標(biāo)題:“狀態(tài)”,
存取器:“顯示狀態(tài)”,
},
{
標(biāo)頭:“首映”,
存取器:“show.premiered”,
單元格:({單元格:{值}})=>值|| “——”
},
{
標(biāo)題:“時(shí)間”,
存取器:“show.schedule.time”,
單元格:({單元格:{值}})=>值|| “——”
},
]
}
]
)
返回 (
< div className="應(yīng)用程序" >
< h1 >< center >React 表演示< /center > > </h1 >
<表列={列}數(shù)據(jù)={數(shù)據(jù)}/>
</div>
);}導(dǎo)出默認(rèn)應(yīng)用程序;
// 表容器.js
從“反應(yīng)”導(dǎo)入反應(yīng);從“反應(yīng)表”導(dǎo)入{useTable};
導(dǎo)出默認(rèn)函數(shù)表({列,數(shù)據(jù)}){
常數(shù) {
獲取表格道具,
getTableBodyProps,
標(biāo)頭組,
行,
準(zhǔn)備行,
} = 使用表格({
列,
數(shù)據(jù),
})
返回 (
<表{...getTableProps()}>
<頭>
{headerGroups.map(headerGroup => (
< tr {...headerGroup.getHeaderGroupProps()}>
{headerGroup.headers.map(列 => (
< th {...column.getHeaderProps()}>{column.render('Header')}
))}
</tr>
))}
< /頭>
< tbody {...getTableBodyProps()} >
{rows.map((row, i) => {
準(zhǔn)備行(行)
返回 (
< tr {...row.getRowProps()}>
{row.cells.map(細(xì)胞 => {
返回 {cell.render('Cell')}
})}
</tr>
)
})}
</t正文>
< /表>
)}
運(yùn)行命令 npm run start 后,您將看到類似這樣的內(nèi)容 -
實(shí)現(xiàn) useFilter Hook
現(xiàn)在,繼續(xù)在我們的應(yīng)用程序中使用 useFilter 和 useGlobalFilter。根據(jù)我們的 UI,這將是我們的項(xiàng)目結(jié)構(gòu)。
我們將實(shí)現(xiàn)默認(rèn)過濾器和選擇列過濾器。為此,我們將
更新 App.js
TableContainer.js
創(chuàng)建一個(gè)名為 Filter.js 的新文件(它將具有 Filter 視圖的功能組件)
事不宜遲,讓我們創(chuàng)建 Filter.js 并為 Filter UI 定義 React 表組件。
為 UI 定義過濾器組件
在這個(gè) React Table 演示中,我們將實(shí)現(xiàn)三個(gè)過濾器視圖 –
列的默認(rèn)過濾器:它將呈現(xiàn)文本輸入,并根據(jù)輸入的文本過濾列數(shù)據(jù)。
全局過濾器:它將呈現(xiàn)文本輸入,但不僅僅是列;根據(jù)輸入的文本過濾整個(gè)表格數(shù)據(jù)。
Select Filter for Column:它將呈現(xiàn)選擇輸入,并根據(jù)從列表中選擇的選項(xiàng)過濾列數(shù)據(jù)。
我們將創(chuàng)建一個(gè)名為 Filter.js(或任何合適的名稱)的通用文件,我們將從中導(dǎo)出上述功能組件以提高可讀性。
// 過濾器.js
import { React, useMemo, useState } from "react";從“反應(yīng)表”導(dǎo)入{useAsyncDebounce};從“reactstrap”導(dǎo)入{標(biāo)簽,輸入};
// 全局過濾器組件導(dǎo)出函數(shù) GlobalFilter({
全局過濾器,
設(shè)置全局過濾器}) {
const [值, setValue] = useState(globalFilter);
const onChange = useAsyncDebounce((值) => {
setGlobalFilter(值 || 未定義);
}, 200);
返回 (
<分區(qū)>
<Label>搜索表:</Label>
<輸入
值={值|| “”}
onChange={(e) => {
設(shè)置值(e.target.value);
onChange(e.target.value);
}}
占位符=“輸入值”
類名="w-25"
樣式={{
字體大?。骸?.1rem”,
保證金:“15px”,
顯示:“內(nèi)聯(lián)”,
}}
/>
</div>
);}
// 默認(rèn)列過濾器的組件導(dǎo)出函數(shù) DefaultFilterForColumn({
柱子: {
過濾值,
preFilteredRows:{長度},
設(shè)置過濾器,
},}) {
返回 (
<輸入
值={過濾值|| “”}
onChange={(e) => {
// 設(shè)置未定義以完全刪除過濾器
setFilter(e.target.value || undefined);
}}
placeholder={`搜索 ${length} 條記錄..`}
style={{ marginTop: "10px" }}
/>
);}
// 自定義選擇過濾器的組件導(dǎo)出函數(shù) SelectColumnFilter({
列:{ filterValue, setFilter, preFilteredRows, id },}) {
// 使用 preFilteredRows 計(jì)算選項(xiàng)
const options = useMemo(() => {
常量選項(xiàng)=新設(shè)置();
preFilteredRows.forEach((row) => {
options.add(row.values[id]);
});
返回 [...options.values()];
}, [id, preFilteredRows]);
// 多選框的 UI
返回 (
<選擇
值={過濾器值}
onChange={(e) => {
setFilter(e.target.value || undefined);
}}
>
<option value="">全部</option>
{options.map((option, i) => (
<選項(xiàng)鍵={i}值={選項(xiàng)}>
{選項(xiàng)}
</選項(xiàng)>
))}
</選擇>
);}
解釋
useAsyncDebounce有什么用?– React table 提供 useAsyncDebounce 來避免由于副作用導(dǎo)致的多次重新渲染并使用最新的。背靠背狀態(tài)的副作用會(huì)觸發(fā)多個(gè)渲染。因此,React Table 不是手動(dòng)處理它,而是提供了一個(gè)鉤子來消除快速副作用。
在這里,我們的數(shù)據(jù)很少,所以我們不會(huì)意識(shí)到 useAsyncDebounce 的重要性。但是,考慮一下,如果我們過濾了數(shù)千個(gè)數(shù)據(jù),那么持續(xù)的狀態(tài)變化和副作用比這個(gè)演示應(yīng)用程序的成本要高得多。即使在為演示應(yīng)用程序編碼時(shí),優(yōu)秀的開發(fā)人員也會(huì)關(guān)注性能。盡量避免垃圾編碼。
setfilter、filterValue 和 preFilterRows 是用于特定列的列屬性。我們已經(jīng)解構(gòu)了 column prop 并使用它們來獲取各個(gè)列的過濾器值。
渲染過濾器組件
對于 GlobalFilter 和 DefaultFilterForColumn
打開TableContainer.js并導(dǎo)入組件和掛鉤 -
從“反應(yīng)表”導(dǎo)入{useTable,useFilters,useGlobalFilter};從“./Filter”導(dǎo)入 { GlobalFilter, DefaultFilterForColumn};
將 DefaultFilterForColumn 傳遞給 useTable 掛鉤作為所有列的默認(rèn)過濾器。因此,默認(rèn)情況下,除非您提供自定義過濾器或禁用過濾器,否則您的列會(huì)將這些組件作為過濾器。
現(xiàn)在要渲染 UI,請使用以下代碼 -
您的整個(gè)TableContainer.js將如下所示 -
// 表容器.js
從“反應(yīng)”導(dǎo)入{反應(yīng)};從“反應(yīng)表”導(dǎo)入{useTable,useFilters,useGlobalFilter};從“./Filter”導(dǎo)入 { GlobalFilter, DefaultColumnFilter };
導(dǎo)出默認(rèn)函數(shù)表({列,數(shù)據(jù)}){
常數(shù) {
獲取表格道具,
getTableBodyProps,
標(biāo)頭組,
行,
狀態(tài),
可見列,
準(zhǔn)備行,
設(shè)置全局過濾器,
preGlobalFilteredRows,
} = 使用表(
{
列,
數(shù)據(jù),
defaultColumn: { 過濾器: DefaultFilterForColumn },
},
使用過濾器,
使用全局過濾器
);
返回 (
<表{...getTableProps()}>
<頭>
<tr>
<第
colSpan={visibleColumns.length}
樣式={{
textAlign: "居中",
}}
>
{/* 渲染全局過濾器 */}
<全局過濾器
preGlobalFilteredRows={preGlobalFilteredRows}
globalFilter={state.globalFilter}
setGlobalFilter={setGlobalFilter}
/>
</th>
</tr>
{headerGroups.map((headerGroup) => (
<tr {...headerGroup.getHeaderGroupProps()}>
{headerGroup.headers.map((列) => (
<th {...column.getHeaderProps()}>
{column.render("標(biāo)題")}
{/* 呈現(xiàn)默認(rèn)列過濾器 */}
<分區(qū)>
{column.canFilter ?column.render("過濾器")
:無效的}
</div>
</th>
))}
</tr>
))}
</thead>
<tbody {...getTableBodyProps()}>
{rows.map((row, i) => {
準(zhǔn)備行(行);
返回 (
<tr {...row.getRowProps()}>
{row.cells.map((cell) => {
返回 <td {...cell.getCellProps()}>
{cell.render("單元格")}
</td>;
})}
</tr>
);
})}
</tbody>
</表>
);}
對于使用SelectColumnFilter,
打開我們定義列數(shù)組的App.js。
導(dǎo)入SelectColumnFilter。
添加過濾器:SelectColumnFilter到列的特定對象。
如果您在任何特定列上禁用過濾器,請?zhí)砑右韵麓a行 -
React Table 中的 Column Filter 是如何工作的?
你還記得我們添加了一行來實(shí)現(xiàn)列過濾器嗎?
“過濾器”是列定義中的屬性。它將呈現(xiàn)作為 Filter 鍵值的任何組件。
這里我們使用了defaultcolumn,所以不需要為所有列定義 Filter 但我們必須為自定義過濾器定義 Filter 鍵(例如SelectColumnFilter)
column.canFilter的條件將被執(zhí)行,它將呈現(xiàn)定義為關(guān)鍵過濾器的組件。
這里我們在對象中提到了自定義過濾器 SelectColumnFilter并將DefaultFilterForColumn設(shè)置為默認(rèn)顯示的過濾器。
Github 存儲(chǔ)庫:react-table-example
歡迎訪問演示應(yīng)用程序react-table-example的源代碼。
結(jié)論
所以,這是關(guān)于如何使用 useFilter 掛鉤過濾表數(shù)據(jù)的。我希望 React Table 教程對您有所幫助。如果您有任何問題或建議,請隨時(shí)在下方發(fā)表評(píng)論。
如果您是 ReactJs 愛好者,請查看包含更多教程的 ReactJS 教程頁面及其各自的 github 存儲(chǔ)庫。
在 河南言鼎,開發(fā)人員盡最大努力提出最佳解決方案和負(fù)擔(dān)得起的問題解決方法。如果您正在為您的項(xiàng)目尋找?guī)椭?,請立即?lián)系我們聘請React 開發(fā)人員。
言鼎科技主做軟件開發(fā),微信小程序,網(wǎng)站開發(fā),軟件外包,手機(jī)APP開發(fā)。如有需要記得聯(lián)系我們!