React封裝通用Table組件,支持搜索(多條件)、篩選、自動序號、數據量統計等功能。未采用二次封裝調整靈活,包含使用文檔

封裝通用組件

  • 一、封裝思想
  • 二、react代碼
  • 三、css代碼
  • 四、實現效果
  • 五、使用文檔 BasicTableModal 表格模態框組件
    • 1.組件簡介
    • 2.功能特點
    • 3.使用方法
      • 基礎用法
      • 寬度控制示例
      • 帶篩選功能
      • 搜索功能示例
      • 自定義單元格渲染
    • 4.API 說明
      • Props
      • Column 配置項
      • Filter 配置項
    • 5.注意事項

一、封裝思想

1.通用性:可以適用于多種表格展示場景,樣式設計更靈活
2.可配置性:提供豐富的配置選項
3.易用性:使用方式簡單直觀
4.可維護性:代碼結構清晰,邏輯分明
5.可擴展性:預留了自定義渲染等擴展接口

二、react代碼

import React from 'react';
import PropTypes from 'prop-types'; // 通過PropTypes實現數據校驗
import 'src/css/basicTableModal.css';class BasicTableModal extends React.Component {constructor(props) {super(props);this.state = {searchText: '',filterValues: {},filteredData: props.data || [],visible: props.visible || false};}// 添加序號列到columns中getColumnsWithIndex = () => {const indexColumn = {key: '_index',title: '序號',render: (text, record, index) => index + 1};return [indexColumn, ...this.props.columns];}componentDidMount() {this.filterAndSearchData();}componentDidUpdate(prevProps) {if (prevProps.data !== this.props.data) {this.filterAndSearchData();}if (prevProps.visible !== this.props.visible) {this.setState({ visible: this.props.visible });}}// 處理搜索和篩選filterAndSearchData = () => {const { data, searchableKeys = [] } = this.props;const { searchText, filterValues } = this.state;let result = [...data];// 處理搜索if (searchText.trim()) {result = result.filter(item => {return searchableKeys.some(key => {const cellValue = item[key];return cellValue && String(cellValue).toLowerCase().includes(searchText.toLowerCase());});});}// 處理篩選Object.entries(filterValues).forEach(([key, value]) => {if (value) {result = result.filter(item => item[key] === value);}});this.setState({ filteredData: result });}handleSearchChange = (e) => {this.setState({ searchText: e.target.value }, this.filterAndSearchData);}handleFilterChange = (key, value) => {this.setState(prevState => ({filterValues: {...prevState.filterValues,[key]: value}}), this.filterAndSearchData);}handleClose = () => {const { onClose } = this.props;this.setState({ visible: false });if (onClose) {onClose();}}// 渲染篩選下拉框renderFilterDropdown = (column) => {if (!column.filters) return null;return (<selectclassName="filter-select"value={this.state.filterValues[column.key] || ''}onChange={(e) => this.handleFilterChange(column.key, e.target.value)}><option value="">全部</option>{column.filters.map((filter, index) => (<option key={index} value={filter.value}>{filter.text}</option>))}</select>);}render() {const { title, searchPlaceholder = "輸入關鍵字搜索...", width } = this.props;const { searchText, filteredData, visible } = this.state;const columnsWithIndex = this.getColumnsWithIndex();if (!visible) return null;const modalStyle = {width: width || '80%',maxWidth: '1000px'};return (<div className="modal-overlay"><div className="modal-content" style={modalStyle}><div className="modal-header"><h3>{title || '表格詳情'}</h3><button className="close-button" onClick={this.handleClose}>×</button></div><div className="basic-table-container"><div className="table-toolbar">{(this.props.searchableKeys && this.props.searchableKeys.length > 0) && (<inputtype="text"placeholder={searchPlaceholder}value={searchText}onChange={this.handleSearchChange}className="search-input"/>)}<div className="filter-container">{this.props.columns.map(column => (column.filters && (<div key={column.key} className="filter-item"><span className="filter-label">{column.title}:</span>{this.renderFilterDropdown(column)}</div>)))}</div></div><div className="table-content-wrapper"><table className="basic-table"><thead><tr>{columnsWithIndex.map(column => (<th key={column.key} style={{ width: column.width || 'auto' }}>{column.title}</th>))}</tr></thead><tbody>{filteredData.map((item, index) => (<tr key={index} className={index % 2 === 0 ? 'table-row-light' : 'table-row-dark'}>{columnsWithIndex.map(column => (<td key={column.key} style={{ width: column.width || 'auto' }}>{column.render ? column.render(item[column.key], item, index) : item[column.key]}</td>))}</tr>))}</tbody></table></div><div className="table-footer"><span className="data-count">數量({filteredData.length})</span></div></div></div></div>);}
}// 數據格式校驗
BasicTableModal.propTypes = {columns: PropTypes.arrayOf(PropTypes.shape({key: PropTypes.string.isRequired,title: PropTypes.string.isRequired,render: PropTypes.func,width: PropTypes.oneOfType([PropTypes.number,PropTypes.string]),filters: PropTypes.arrayOf(PropTypes.shape({text: PropTypes.string.isRequired,value: PropTypes.any.isRequired}))})).isRequired,data: PropTypes.array.isRequired,visible: PropTypes.bool,onClose: PropTypes.func,title: PropTypes.string,searchableKeys: PropTypes.arrayOf(PropTypes.string),searchPlaceholder: PropTypes.string,width: PropTypes.oneOfType([PropTypes.number,PropTypes.string])
};BasicTableModal.defaultProps = {data: [],visible: false,searchableKeys: [],width: '80%'
};export default BasicTableModal;

三、css代碼

/* 模態框基礎樣式
-------------------------------------------------- */
.modal-overlay {position: fixed;top: 0;left: 0;right: 0;bottom: 0;background-color: rgba(0, 0, 0, 0.5);display: flex;justify-content: center;align-items: center;z-index: 1000;
}.modal-content {background-color: white;border-radius: 4px;box-shadow: 0 2px 8px rgba(0, 0, 0, 0.15);max-height: 90vh;display: flex;flex-direction: column;position: relative;
}/* 模態框頭部樣式
-------------------------------------------------- */
.modal-header {background-color: #eaeaea;border-bottom: 1px solid #e8e8e8;display: flex;justify-content: space-between;align-items: center;position: relative;border-radius: 4px 4px 0 0;
}.modal-header::before {content: '';position: absolute;top: 9px;left: 10px;height: 14px;border-left: 2px solid #f95e34;
}.modal-header h3 {margin: 0;font-size: 12px;font-family: Microsoft Yahei;color: rgba(0, 0, 0, 0.85);margin-left: 15px;
}.close-button {background: none !important;cursor: pointer;line-height: 33px;
}/* 表格容器布局
-------------------------------------------------- */
.basic-table-container {padding: 5px;flex: 1;display: flex;flex-direction: column;min-height: 0;position: relative;
}.table-content-wrapper {overflow: auto;flex: 1;min-height: 0;
}/* 表格基礎樣式
-------------------------------------------------- */
.basic-table {width: 100%;border-collapse: separate;border-spacing: 0;background-color: #fff;font-size: 12px;font-family: Microsoft Yahei;line-height: 0.5;
}.basic-table th,
.basic-table td {padding: 12px 8px;border: 1px solid #e8e8e8;text-align: left;
}/* 表格頭部樣式
-------------------------------------------------- */
.basic-table thead {position: sticky;top: 0;z-index: 2;background-color: #fafafa;
}.basic-table th {background-color: #fafafa;font-weight: 500;box-shadow: 0 1px 0 #e8e8e8;
}/* 表格內容樣式
-------------------------------------------------- */
.basic-table tbody {overflow-y: auto;
}.table-row-light {background-color: #f0f0f0;
}.table-row-dark {background-color: #ffffff;
}/* 滾動條樣式
-------------------------------------------------- */
.basic-table-container::-webkit-scrollbar {display: none;
}.table-content-wrapper::-webkit-scrollbar {width: 4px;height: 8px;
}.table-content-wrapper::-webkit-scrollbar-thumb {background-color: #c1c1c1;border-radius: 20px;transition: background-color 0.3s;
}.table-content-wrapper::-webkit-scrollbar-thumb:hover {background-color: #a8a8a8;
}.table-content-wrapper::-webkit-scrollbar-track {background: #f1f1f1;border-radius: 20px;
}.table-content-wrapper::-webkit-scrollbar-corner {background: transparent;
}/* 工具欄樣式
-------------------------------------------------- */
.table-toolbar {display: flex;align-items: center;padding: 8px;gap: 16px;position: sticky;top: 0;background-color: white;z-index: 1;border-bottom: 1px solid #e8e8e8;
}/* 搜索框樣式
-------------------------------------------------- */
.search-input {min-width: 200px;max-width: 300px;height: 28px;padding: 4px 8px;border: 1px solid #d9d9d9;border-radius: 2px;font-size: 12px;
}.search-input:focus {border-color: #f95e34;outline: none;box-shadow: 0 0 0 2px rgba(249, 94, 52, 0.2);
}/* 篩選器樣式
-------------------------------------------------- */
.filter-container {display: flex;align-items: center;gap: 12px;flex-wrap: wrap;
}.filter-item {display: flex;align-items: center;gap: 4px;
}.filter-label {font-size: 12px;color: rgba(0, 0, 0, 0.85);
}.filter-select {height: 28px;padding: 4px 8px;border: 1px solid #d9d9d9;border-radius: 2px;font-size: 12px;min-width: 100px;
}.filter-select:focus {border-color: #f95e34;outline: none;box-shadow: 0 0 0 2px rgba(249, 94, 52, 0.2);
}/* 表格底部樣式
-------------------------------------------------- */
.table-footer {padding: 8px;display: flex;align-items: center;position: sticky;bottom: 0;background-color: white;z-index: 1;border-top: 1px solid #e8e8e8;
}.data-count {font-size: 12px;color: rgba(0, 0, 0, 0.65);font-family: Microsoft Yahei;
} 

四、實現效果

在這里插入圖片描述

五、使用文檔 BasicTableModal 表格模態框組件

1.組件簡介

BasicTableModal 是一個表格模態框組件,提供了搜索、篩選、自動序號、數據量統計等功能。它適用于需要在模態框中展示表格數據的場景。

2.功能特點

  • 支持表格數據展示
  • 自動添加序號列
  • 支持關鍵字搜索
  • 支持多列篩選
  • 支持自定義單元格渲染
  • 支持奇偶行樣式區分
  • 響應式設計
  • 支持數據量統計顯示
  • 支持模態框寬度自定義
  • 支持列寬自定義

3.使用方法

基礎用法

import BasicTableModal from './basicTableModal';const columns = [{key: 'name',title: '姓名'},{key: 'age',title: '年齡'}
];const data = [{ name: '張三', age: 25 },{ name: '李四', age: 30 }
];function MyComponent() {return (<BasicTableModal columns={columns}data={data}visible={true}onClose={() => {}}/>);
}

寬度控制示例

// 設置模態框寬度
<BasicTableModal width="90%"columns={columns}data={data}
/>// 設置列寬度
const columns = [{key: 'index',title: '序號',width: 80  // 固定像素寬度},{key: 'name',title: '姓名',width: '150px'  // 帶單位的寬度},{key: 'description',title: '描述',width: '40%'  // 百分比寬度}
];

帶篩選功能

const columns = [{key: 'name',title: '姓名'},{key: 'status',title: '狀態',filters: [{ text: '在線', value: 'online' },{ text: '離線', value: 'offline' }]}
];

搜索功能示例

// 多字段組合搜索示例
const columns = [{key: 'name',title: '姓名'},{key: 'code',title: '編號'},{key: 'description',title: '描述'}
];<BasicTableModal columns={columns}data={data}searchableKeys={['name', 'code', 'description']}  // 可以同時搜索多個字段searchPlaceholder="輸入姓名/編號/描述搜索..."
/>

自定義單元格渲染

const columns = [{key: 'name',title: '姓名',render: (text, record, index) => <span style={{color: 'red'}}>{text}</span>}
];

4.API 說明

Props

參數說明類型必填默認值
columns表格列配置Array-
data表格數據Array[]
visible是否顯示模態框booleanfalse
onClose關閉模態框的回調函數function-
title模態框標題string‘表格詳情’
searchableKeys可搜索的字段鍵名數組string[][]
searchPlaceholder搜索框占位文本string‘輸入關鍵字搜索…’
width模態框寬度number/string‘80%’

Column 配置項

參數說明類型必填默認值
key列數據對應的鍵名string-
title列標題string-
render自定義渲染函數function(text, record, index)-
filters篩選選項配置Array-
width列寬度number/string‘auto’

Filter 配置項

參數說明類型必填
text篩選項顯示文本string
value篩選項對應的值any

5.注意事項

  1. 組件會自動在表格最左側添加序號列
  2. 搜索功能僅在設置 searchableKeys 且不為空數組時顯示搜索框
  3. 篩選和搜索可以同時使用
  4. 表格支持奇偶行樣式區分,便于數據查看
  5. 模態框寬度可以使用數字(默認像素)或帶單位的字符串(如:‘80%’、‘800px’)
  6. 列寬度同樣支持數字和帶單位的字符串,不設置時自動適應內容寬度
  7. 數據總量顯示會實時反映當前篩選/搜索后的數據條數

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/71319.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/71319.shtml
英文地址,請注明出處:http://en.pswp.cn/web/71319.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

React 中 useState 的 基礎使用

概念&#xff1a;useState 是一個React Hook&#xff08;函數&#xff09;&#xff0c;它允許我們向組件添加狀態變量&#xff0c;從而影響組件的渲染結果。 本質&#xff1a;和普通JS變量不同的是&#xff0c;狀態變量一旦發生變化&#xff0c;組件的視圖UI也會跟著變化&…

Html5學習教程,從入門到精通,HTML `<div>` 和 `<span>` 標簽:語法知識點與案例代碼(12)

HTML <div> 和 <span> 標簽&#xff1a;語法知識點與案例代碼 一、語法知識點 1. <div> 標簽 定義: <div> 是一個塊級元素&#xff0c;用于將文檔內容劃分為獨立的、可樣式化的部分。它本身沒有特定的語義&#xff0c;主要用于布局和分組。特點: 塊…

Hbase偽分布安裝教程,詳細版

注意Hbase版本與Hadoop版本的兼容&#xff0c;還有與JDK版本的兼容 本次用到的Hbase為2.4.6版本&#xff0c;Hadoop為3.1.3版本&#xff0c;JDK為JDK8 打開下面的網址查看兼容問題 Apache HBase Reference Guidehttps://hbase.apache.org/book.html#configuration 點擊基礎先…

Python項目】基于Python的圖像去霧算法研究和系統實現

Python項目】基于Python的圖像去霧算法研究和系統實現 技術簡介&#xff1a;采用Python技術、MYSQL數據庫等實現。 系統簡介&#xff1a;圖像去霧系統主要是基于暗通道先驗和逆深度估計技術的去霧算法&#xff0c;系統功能模塊分為&#xff08;1&#xff09;圖像上傳模塊&…

Stable Diffusion Prompt編寫規范詳解

Stable Diffusion Prompt編寫規范詳解 一、語法結構規范 &#xff08;一&#xff09;基礎模板框架 [質量強化] [主體特征] [環境氛圍] [風格控制] [鏡頭參數]質量強化&#xff1a;best quality, ultra detailed, 8k resolution?主體特征&#xff1a;(1girl:1.3), long …

勿以危小而為之勿以避率而不為

《故事匯之&#xff1a;所見/所聞/所歷/所想》&#xff1a;《公園散步與小雨遇記》&#xff08;二&#xff09; 就差一點到山頂了&#xff0c;路上碰到一阿姨&#xff0c;她說等會兒要下大雨了&#xff0c;讓我不要往上走了&#xff0c;我猶豫了一會兒&#xff0c;還是聽勸地返…

wheel_legged_genesis 開源項目復現與問題記錄

Reinforcement learning of wheel-legged robots based on Genesis System Requirements Ubuntu 20.04/22.04/24.04 python > 3.10 開始配置環境&#xff01; 點擊releases后進入&#xff0c;下載對應最新版本的代碼&#xff1a; 將下載后的代碼包解壓到你的自定義路徑下&…

Gin框架從入門到實戰:核心用法與最佳實踐

為什么選擇Gin框架&#xff1f; Gin 是一個基于 Go 語言的高性能 Web 框架&#xff0c;具備以下優勢&#xff1a; 輕量高效&#xff1a;底層依賴 net/http&#xff0c;性能接近原生。簡潔優雅&#xff1a;API 設計友好&#xff0c;支持路由分組、中間件鏈、參數綁定等特性。生…

Leetcode 3468. Find the Number of Copy Arrays

Leetcode 3468. Find the Number of Copy Arrays 1. 解題思路2. 代碼實現 題目鏈接&#xff1a;3468. Find the Number of Copy Arrays 1. 解題思路 這一題的話思路上就是一個范圍考察&#xff0c;顯然&#xff0c;對于指定的copy方式&#xff0c;只要我們確定了第一個元素&…

VirtualBox虛擬機MacOS從Big Sur升級到Sequoia(失敗)

VirtualBox虛擬機里安裝好Big Sur版本&#xff0c;嘗試升級到Sequoia&#xff0c;但是最終失敗了。 軟件升級 直接在系統偏好-軟件更新里可以看到提示&#xff0c;提示可以升級到15版本Sequoia 點擊同意&#xff0c;看能不能升級到Sequoia吧。升級前先用時光做了備份。 升級…

[雜學筆記]HTTP1.0和HTTP1.1區別、socket系列接口與TCP協議、傳輸長數據的時候考慮網絡問題、慢查詢如何優化、C++的垃圾回收機制

目錄 1.HTTP1.0和HTTP1.1區別 2.socket系列接口與TCP協議 3.傳輸長數據的時候考慮網絡問題 4.慢查詢如何優化 5.C的垃圾回收機制 1.HTTP1.0和HTTP1.1區別 在連接方式上&#xff0c;HTTP1.0默認采用的是短鏈接的方式&#xff0c;就建立一次通信&#xff0c;也就是說即使在…

ANI AGI ASI的區別

??ANI、?AGI、?ASI的區別主要體現在定義、特點和應用場景上?&#xff1a; 1. ANI&#xff08;狹義人工智能 Artificial narrow intelligence&#xff09;?&#xff1a; ?定義?&#xff1a;ANI&#xff0c;也被稱為弱人工智能&#xff0c;是指專門設計用于執行特定任務…

用OpenCV寫個視頻播放器可還行?(Python版)

引言 提到OpenCV&#xff0c;大家首先想到的可能是圖像處理、目標檢測&#xff0c;但你是否想過——用OpenCV實現一個帶進度條、倍速播放、暫停功能的視頻播放器&#xff1f;本文將通過一個實戰項目&#xff0c;帶你深入掌握OpenCV的視頻處理能力&#xff0c;并解鎖以下功能&a…

leetcode日記(77)子集Ⅱ

不知道為什么看到這道題就很頭痛…… 其實只要掌握nums不包含重復元素的情況下的代碼就行了。 若nums不能包含重復元素&#xff0c;那么使用回溯很容易就能寫出來&#xff1a; class Solution {void hs(vector<int> v,int x,vector<int> r,vector<vector<…

通俗版解釋:分布式和微服務就像開餐廳

一、分布式系統&#xff1a;把大廚房拆成多個小廚房 想象你開了一家超火爆的餐廳&#xff0c;但原來的廚房太小了&#xff1a; 問題&#xff1a;一個廚師要同時切菜、炒菜、烤面包&#xff0c;手忙腳亂還容易出錯。 解決方案&#xff1a; 拆分成多個小廚房&#xff08;分布式…

StarRocks-fe工程在Cursor中不能識別為Java項目

SR簡介 StarRocks 是一款高性能分析型數據庫&#xff0c;支持實時、多維度、高并發的數據分析。本指南旨在解決在使用 VSCode 或 Cursor 開發 StarRocks 后端項目時遇到的模塊識別問題。 問題描述 使用 Cursor 或 VSCode 打開 StarRocks 的后端工程 fe 時&#xff0c;spark-…

第五節:基于Winform框架的串口助手小項目---串口收發《C#編程》

“路漫漫其修遠兮&#xff0c;吾將上下而求索” &#xff0c; -----------------------WHAPPY 目標任務&#xff1a; 1 從本地設備列表獲取串口。 RegistryKey keyCom Registry.LocalMachine.OpenSubKey("Hardware\DeviceMap\SerialComm"); RegistryKey 是.NET 框…

專題二最大連續1的個數|||

1.題目 題目分析&#xff1a; 給一個數字k&#xff0c;可以把數組里的0改成1&#xff0c;但是只能改k次&#xff0c;然后該變得到的數組能找到最長的子串且都是1。 2.算法原理 這里不用真的把0變成1&#xff0c;因為改了比較麻煩&#xff0c;下次用就要改回成1&#xff0c;這…

25年第四本【認知覺醒】

《認知覺醒》&#xff1a;一場與大腦的深度談判 在信息爆炸的焦慮時代&#xff0c;我們像被拋入湍流的溺水者&#xff0c;拼命抓取各種自我提升的浮木&#xff0c;卻在知識的漩渦中越陷越深。這不是一本簡單的成功學指南&#xff0c;而是一場關于人類認知系統的深度對話&#…

甘特圖開發代碼(測試版)

場景&#xff1a;要實現的功能就是單行數據能左右拖動。 流程五個&#xff1a;ABCDE。&#xff08;對應&#xff1a;Charter開發、概念和計劃、初樣開發、正樣開發、驗證&#xff09; 1、A有開始時間&#xff0c;結束時間。B的開始時間必須是A的結束時間&#xff08;相等或者…