Table
表格用于通过行和列展示表格数据。它们允许用户快速扫描、排序、比较大量数据并对其执行操作。
安装
The above command is for individual installation only. You may skip this step if @heroui/react is already installed globally.
导入
HeroUI 导出了 6 个与表格相关的组件:
- Table: 用于显示表格的主要组件。
- TableHeader: 表格的头部。
- TableBody: 表格的主体。
- TableColumn: 表格的列。
- TableRow: 表格的行。
- TableCell: 表格的单元格。
用法
动态渲染
要动态渲染表格,您可以使用 columns 属性传递列信息,使用 items 属性传递数据。
为什么不使用数组 map?
使用 items 属性并提供渲染函数允许 react-aria 自动缓存每个项目的渲染结果,并在仅其中一个项目更改时避免重新渲染集合中的所有项目。这对于大型集合具有显著的性能优势。
您也可以使用 Array.map 来渲染项目,但它的性能不如使用 items 和 columns 属性。
示例:
注意: 要了解更多关于 React Aria 集合及其使用方法,请查看 React Aria Collections。
空状态
您可以使用 emptyContent 属性在表格为空时渲染自定义组件。
无表头
如果您不想渲染表头,可以使用 hideHeader 属性。
无包装器
默认情况下,表格被包装在一个带有小阴影效果和边框半径的 div 元素中。
您可以使用 removeWrapper 属性移除包装器,只渲染表格。
但是,removeWrapper 属性对虚拟化表格无效,因为需要包装器来管理其高度。
自定义单元格
您可以在表格单元格内渲染任何组件。在下面的示例中,我们根据列的 key 渲染不同的组件。
条纹行
您可以使用 isStriped 属性渲染条纹行。
单行选择
可以使表格行可选择。为此,您可以使用 selectionMode 属性。使用 defaultSelectedKeys 来提供默认的选中行集合。
注意: 选中键的值必须与行的 key 属性匹配。
多行选择
您也可以通过使用 selectionMode="multiple" 属性来选择多行。使用 defaultSelectedKeys 来提供默认的选中行集合。
注意: 使用多选时,可选择的复选框将呈现在表格的第一列。
禁止空选择
表格还支持 disallowEmptySelection 属性,该属性强制用户必须始终在表格中至少选中一行。
在此模式下,如果选中了单行并且用户按下它,它将不会被取消选中。
受控选择
要以编程方式控制行选择,请使用 selectedKeys 属性配合 onSelectionChange 回调。
当行被按下时,所选行的 key 属性将被传递给回调,允许您相应地更新状态。
注意:
selectedKeys属性必须是一个Set对象。
禁用行
您可以使用 disabledKeys 属性禁用行。这将阻止行被选择,如下例所示。
选择行为
默认情况下,表格使用 toggle 选择行为,其行为类似于复选框组:
单击、点击或按下 空格键 或 回车键 会切换焦点行的选择状态。
当 selectionBehavior 属性设置为 replace 时,用鼠标单击某行会将该行替换为唯一选中的行。
使用箭头键会同时移动焦点和选择。
要选择多行,可以使用修饰键,如 Ctrl、Cmd 和 Shift。
行操作
表格通过 onRowAction 回调支持行操作。在默认的 toggle 选择行为中,当没有选中任何内容时,单击或点击行会触发行操作。
在 replace 选择行为中,此行为略有不同,其中单击选择行,而操作通过双击执行。
排序行
当按下列标题时,表格支持对其数据进行排序。要指定某个 Column 应支持排序,请为其提供 allowsSorting 属性。
表格接受一个 sortDescriptor 属性,该属性定义了当前要排序的列键和排序方向(升序/降序)。
当用户按下可排序的列标题时,该列的键和排序方向会传递给 onSortChange 回调,允许您相应地更新 sortDescriptor。
我们推荐使用 @react-stately/data 中的 useAsyncList 钩子来管理数据排序。因此,在使用排序功能之前请确保安装它。
注意,我们向
TableBody传递了isLoading和loadingContent属性,以便在获取数据时呈现加载状态。
排序图标
您可以通过指定 sortIcon 来覆盖默认的排序图标。此属性仅在 allowsSorting 为 true 时应用。
加载更多数据
表格允许您在表格末尾添加自定义组件,在下面的示例中,我们使用一个按钮来加载更多数据。
注意: 我们向
Table组件传递了isHeaderSticky以使表头具有粘性。
分页表格
您可以使用 Pagination 组件对表格进行分页。
异步分页
也可以使用 Pagination 组件对表格进行异步分页。为了获取数据,我们使用了来自 SWR 的 useSWR 钩子。
无限分页
表格也支持无限分页。为此,您可以使用 @react-stately/data 中的 useAsyncList 钩子和 @heroui/use-infinite-scroll 钩子。
虚拟化
表格支持虚拟化,它通过仅渲染视口中可见的项目来实现大型列表的高效渲染。您可以通过将 isVirtualized 属性设置为 true 来启用虚拟化。
注意: 虚拟化策略基于 @tanstack/react-virtual 包,该包通过仅渲染视口中可见的项目来实现大型列表的高效渲染。
一万个项目
这是一个使用虚拟化处理 10,000 个项目的示例。
最大表格高度
maxTableHeight 属性用于设置表格的最大高度。使用虚拟化时需要此属性。默认情况下,它设置为 600。
自定义行高
rowHeight 属性用于设置表格中每行的高度。使用虚拟化时需要此属性。默认情况下,它设置为 40。
用例示例
创建表格时,您通常需要排序、分页和过滤等核心功能。在下面的示例中,我们结合了所有这些功能来创建一个完整的表格。
插槽
- base: 为表格组件定义灵活的列布局和相对定位。
- wrapper: 应用于最外层的包装器,提供内边距、灵活布局、相对定位、视觉样式和可滚动的溢出处理。
- table: 将表格设置为具有完整的最小宽度和自动调整的高度。
- thead: 为表头中的第一个子行指定圆角。
- tbody: 表格主体没有应用特定样式。
- tr: 表格行的样式,包括组焦点、轮廓属性以及一组未定义的焦点可见类。
- th: 表头单元格的样式,包括内边距、文本对齐、字体属性以及可排序列的特殊样式。
- td: 应用于表格单元格,具有内边距、对齐和相对定位的属性,以及为第一个子元素、选择指示和禁用单元格的特殊样式。
- tfoot: 表格页脚没有应用特定样式。
- sortIcon: 排序图标的样式,具有基于排序方向和悬停状态的边距、不透明度和过渡效果属性。
- emptyWrapper: 为空表格定义样式,包括文本对齐、颜色和指定的高度。
- loadingWrapper: 表格加载时应用的样式,在其容器中居中定位。
自定义样式
您可以通过向组件插槽传递自定义的 Tailwind CSS 类来定制 Table 组件。
数据属性
TableBody 具有以下属性:
- data-empty: 当表格为空时。
- data-loading:
当表格数据正在加载时。基于
TableBody的isLoading和loadingContent属性。
TableRow 具有以下属性:
- data-selected:
当行被选中时。基于
Table的selectedKeys属性。 - data-disabled:
当行被禁用时。基于
Table的disabledKeys属性。 - data-hover: 当行被悬停时。基于 useHover
- data-focus-visible: 当行通过键盘获得焦点时。基于 useFocusRing。
- data-first: 当行是第一行时。
- data-middle: 当行在中间时。
- data-odd: 当行是奇数行时。
- data-last: 当行是最后一行时。
TableCell 具有以下属性:
- data-selected:
当单元格所在行被选中时。基于
Table的selectedKeys属性。 - data-focus-visible: 当单元格通过键盘获得焦点时。基于 useFocusRing。
无障碍性
- 使用 ARIA 作为网格暴露给辅助技术。
- 通过箭头键在列、行、单元格和单元格内可聚焦元素之间进行键盘导航。
- 通过鼠标、触摸或键盘交互支持单选、多选或不选行。
- 支持禁用行,这些行无法被选择。
- 支持列排序。
- 支持异步加载、无限滚动、过滤和排序。
- 支持切换和替换两种选择行为。
- 支持为无障碍性添加标签。
- 确保使用 ARIA 实时区域播报选择情况。
- 支持将列标记为行标题,在使用屏幕阅读器导航行时会朗读出来。
- 可选支持在每个行中显示用于选择的复选框,以及在标题中显示用于选择所有行的复选框。
- 键盘导航期间支持自动滚动。
- 通过双击、回车键或点击支持行操作。
- 支持通过键入文本进行输入搜索以聚焦行。
- 在触摸设备上长按可进入选择模式(当同时存在选择和行操作时)。
API
Table 属性
| Prop | Type | Default |
children* | | |
color | | "default" |
layout | | "auto" |
radius | | "lg" |
shadow | | "sm" |
maxTableHeight | | "600" |
rowHeight | | "40" |
isVirtualized | | "undefined" |
hideHeader | | false |
isStriped | | false |
isCompact | | false |
isHeaderSticky | | false |
fullWidth | | true |
removeWrapper | | false |
BaseComponent | | "div" |
topContent | | |
bottomContent | | |
topContentPlacement | | "inside" |
bottomContentPlacement | | "inside" |
showSelectionCheckboxes | | |
sortDescriptor | | |
selectedKeys | | |
defaultSelectedKeys | | |
disabledKeys | | |
disallowEmptySelection | | |
selectionMode | | "none" |
selectionBehavior | | "toggle" |
disabledBehavior | | "selection" |
allowDuplicateSelectionEvents | | |
disableAnimation | | false |
checkboxesProps | | |
classNames | | |
isKeyboardNavigationDisabled | | false |
Table 事件
| Prop | Type | Default |
onRowAction | | |
onCellAction | | |
onSelectionChange | | |
onSortChange | |
TableHeader 属性
| Prop | Type | Default |
children* | | |
columns | |
TableColumn 属性
| Prop | Type | Default |
children* | | |
align | | "start" |
hideHeader | | false |
allowsSorting | | |
sortIcon | | |
isRowHeader | | |
textValue | | |
width | | |
minWidth | | |
maxWidth | |
TableBody 属性
| Prop | Type | Default |
children* | | |
items | | |
isLoading | | |
loadingState | | |
loadingContent | | |
emptyContent | |
TableBody 事件
| Prop | Type | Default |
onLoadMore | |
TableRow 属性
| Prop | Type | Default |
children* | | |
textValue | |
TableCell 属性
| Prop | Type | Default |
children* | | |
textValue | |

