更新记录

1.0.0(2026-04-21)

首次发布

  • 基于 Canvas 2D 的高性能表格组件,支持 H5 和微信小程序
  • 支持固定列(fixed: 'left' | 'right')与固定行(fixedRows
  • 支持列宽 / 行高拖拽调整(useColRowResize
  • 支持虚拟滚动:行虚拟(超过阈值自动开启)、列虚拟(列数 > 10 自动开启)
  • 支持单元格合并(options.spanMethod
  • 支持多级表头(ColumnNode.children
  • 支持行选择:复选框 / 单选(rowSelection
  • 支持区域框选(enableSelection
  • 支持排序(ColumnNode.sortable,受控 / 非受控模式)
  • 支持树形数据展开 / 折叠(treeProps)及懒加载
  • 支持分页配置(pagination
  • 支持 Tooltip 悬浮提示(ColumnNode.tooltip
  • 支持自定义单元格渲染(ColumnNode.cellRender
  • 支持操作按钮列(ColumnNode.actionButtons
  • 支持加载状态(loading)与空状态(EmptyLayer
  • 支持条纹行、悬停高亮、列悬停高亮
  • 支持文本溢出处理:截断 / 省略号 / 自动折行(cellOverflow
  • 支持自定义 Overlay 绘制(bodyOverlayDraw / fixedTopOverlayDraw / fixedBottomOverlayDraw
  • 暴露 Ref 方法:scrollToscrollToRowscrollToColumngetSelectionRangeclearSelectiongetSelectedRowKeysclearRowSelectiongetSortStateresetSortgetExpandedKeyssetExpandedKeysredraw

平台兼容性

uni-app(3.7.6)

Vue2 Vue3 Chrome Safari app-vue app-nvue Android iOS 鸿蒙
- - - - - -
微信小程序 支付宝小程序 抖音小程序 百度小程序 快手小程序 京东小程序 鸿蒙元服务 QQ小程序 飞书小程序 小红书小程序 快应用-华为 快应用-联盟
- - - - - - - - - - -

其他

多语言 暗黑模式 宽屏模式
× ×

# pro-table

pro-table 是一个基于单 canvas 分层渲染的高性能表格组件,面向 uni-app + Vue 3 场景,兼容 H5 和小程序端。

它不是 DOM 表格,而是把表头、表体、固定列、固定行、阴影、选区、tooltip、拖拽指示线等内容拆成多个 layer 绘制到同一张 canvas 上,因此更适合大数据量、固定列、虚拟滚动、复杂自定义绘制等场景。

特性

  • 单 canvas 分层渲染
  • H5 / 小程序双端适配
  • 固定表头、固定列、固定行
  • 行虚拟滚动、主区列虚拟滚动
  • 单元格选区
  • 行选择 checkbox / radio
  • 列宽拖拽、行高拖拽
  • 树形数据展开 / 折叠 / 懒加载
  • 客户端排序
  • 分页数据切片
  • 悬浮提示 tooltip
  • 自定义单元格绘制、覆盖层绘制、操作按钮
  • 单元格横向 / 纵向合并

快速开始

<template>
  <view class="table-wrap">
    <pro-table
      ref="tableRef"
      :columns="columns"
      :data="data"
      :options="options"
      @cell-click="onCellClick"
    />
  </view>
</template>

<script setup lang="ts">
import { ref } from 'vue'
import ProTable from '@/uni_modules/pro-table/components/pro-table/pro-table.vue'
import type {
  ColumnNode,
  ProTableOptions,
  RowData,
} from '@/uni_modules/pro-table'

interface UserRow extends RowData {
  id: number
  name: string
  dept: string
  salary: number
}

const tableRef = ref<any>(null)

const columns: ColumnNode[] = [
  { key: 'id', title: 'ID', width: 80, cellAlign: 'center', headerAlign: 'center' },
  { key: 'name', title: '姓名', width: 120 },
  { key: 'dept', title: '部门', width: 140 },
  { key: 'salary', title: '薪资', width: 120, cellAlign: 'right', sortable: true },
]

const data = ref<UserRow[]>([
  { id: 1, name: '张三', dept: '研发', salary: 12000 },
  { id: 2, name: '李四', dept: '产品', salary: 15000 },
])

const options: ProTableOptions = {
  fontSize: 13,
  padding: [8, 10],
  stripedBgColor: '#fafafa',
}

function onCellClick(payload: any) {
  console.log('cell-click', payload)
}
</script>

<style scoped>
.table-wrap {
  height: 600px;
}
</style>

组件参数

Props

参数 类型 默认值 说明
columns ColumnNode[] 必填 列定义,支持多级表头、固定列、排序、tooltip、自定义 render、单元格合并
data T[] [] 表体数据
options ProTableOptions undefined 视觉和交互选项
fixedRows FixedRowDef[] undefined 固定行定义,同时支持顶部和底部固定行
enableStriped boolean false 是否启用斑马纹
enableHover boolean true 是否启用行 hover
enableColHover boolean false 是否启用列 hover
enableSelection boolean false 是否启用单元格框选
rowSelection RowSelectionConfig undefined 行选择配置,启用后会自动注入选择列
selectedRowKeys number[] undefined 受控行选择值。注意这里实际是“当前页行索引数组”,不是业务 rowKey
bodyOverlayDraw (payload: OverlayDrawPayload) => void undefined 表体覆盖层自定义绘制
fixedTopOverlayDraw (payload: OverlayDrawPayload) => void undefined 顶部固定行覆盖层自定义绘制
fixedBottomOverlayDraw (payload: OverlayDrawPayload) => void undefined 底部固定行覆盖层自定义绘制
loading boolean false 加载态,开启后显示 loading layer 并阻止滚动交互
treeProps TreeConfig undefined 树形表格配置
pagination PaginationConfig undefined 分页配置。组件只负责分页逻辑和事件,不内置分页器 UI

Props 详细说明

columns

  • 作用:描述整张表的列结构,是最核心的输入参数
  • 影响范围:表头结构、列宽、固定列、排序、tooltip、自定义单元格绘制、单元格合并都由它决定
  • 使用建议:key 必须稳定且唯一,避免在运行时频繁修改列对象结构

data

  • 作用:表格主体行数据
  • 数据要求:每一项都是一个对象,字段名通常与列 key 对应
  • 额外能力:除业务字段外,还可以内联 __resizable____minHeight____maxHeight__ 等控制字段
  • 更新建议:优先替换数组引用,而不是原地深改对象

options

  • 作用:统一控制视觉样式和部分交互细节
  • 典型用途:边框颜色、背景色、hover 色、字体大小、内边距、选区颜色、拖拽手柄显示
  • 适用场景:想整体换风格时优先改这里,而不是在每列里单独覆盖

fixedRows

  • 作用:定义固定在表头下方或底部的特殊行
  • 典型用途:汇总行、合计行、说明行、固定提示行
  • 数据结构:每一项都要显式声明 position: 'top' | 'bottom'
  • 能力范围:支持按列覆写渲染,也支持固定行内部单元格合并

enableStriped

  • 作用:开启后按奇偶行绘制斑马纹背景
  • 注意:只是视觉层面的辅助识别,不影响数据和事件

enableHover

  • 作用:是否高亮当前悬浮行
  • 平台差异:H5 主要响应鼠标悬浮,小程序依赖触摸交互流程

enableColHover

  • 作用:是否高亮当前悬浮列
  • 适用场景:强调列阅读对齐,例如财务表、对比表

enableSelection

  • 作用:开启后可拖拽选择单元格区域
  • 注意:这是“单元格框选”,和 rowSelection 的“行勾选”是两套独立能力

rowSelection

  • 作用:开启行级单选或多选能力
  • 具体行为:组件会自动在最左侧插入一列选择列
  • 注意:当前实现返回的是“当前页索引”,不是业务主键

selectedRowKeys

  • 作用:行选择的受控值
  • 实际含义:这里的数组成员不是 rowKey,而是当前分页结果中的行下标
  • 适用场景:父组件完全接管行选择状态时使用

bodyOverlayDraw / fixedTopOverlayDraw / fixedBottomOverlayDraw

  • 作用:在既有表格绘制完成后,再追加一层自定义图形
  • 适用场景:趋势线、热点标记、角标、辅助线、状态点、业务注释
  • 区别:三个回调分别作用于表体、顶部固定行、底部固定行区域

loading

  • 作用:显示加载层,并阻止常规交互
  • 适用场景:接口请求中、局部数据切换中、懒加载等待中

treeProps

  • 作用:开启树形表格能力
  • 适用场景:目录树、组织架构、层级账目、主从明细
  • 能力范围:支持默认展开、指定展开、懒加载、缩进列配置

pagination

  • 作用:开启组件内部的数据切片逻辑
  • 注意:它不渲染分页器,只保存分页状态并对当前数据做 slice
  • 适用场景:你自己在页面外部渲染分页栏,再通过 ref 方法或响应式配置联动

Events

事件名 回调参数 说明
cell-click { row, rowIndex, colKey, value, isHeader, fixedRow?, localX?, localY? } 点击单元格或表头时触发。点击表头排序列时,会先切换排序再触发该事件
selection-change { range: SelectionRange \| null } 选区拖拽过程中持续触发
selection-end { range: SelectionRange \| null } 选区拖拽结束时触发
row-select-change { indices: number[]; rows: T[] } 行选择变化。indices 为当前分页切片内的索引
update:selectedRowKeys number[] 配合 v-model:selectedRowKeys 使用
col-resize { key: string; width: number } 列宽拖拽结束时触发
row-resize { rowIndex: number; height: number } 行高拖拽结束时触发
sort-change SortState 排序变化
load-more 滚动到底部附近或内容不足填满容器时触发
page-change { page: number; pageSize: number } 调用分页方法或切换页大小时触发

事件参数详细说明

cell-click

{
  row: T | null
  rowIndex: number
  colKey: string
  value: any
  isHeader: boolean
  fixedRow?: 'top' | 'bottom'
  localX?: number
  localY?: number
}
字段 含义
row 被点击的行数据。点击表头时为 null
rowIndex 行索引。表头点击时通常为 -1,表体点击时为当前数据索引
colKey 被点击列的 key
value 当前单元格的值,等价于 row?.[colKey]
isHeader 是否点击的是表头
fixedRow 如果点击的是固定行单元格,这里会标记 'top''bottom'
localX 指针在当前单元格内部的相对 X 坐标,可用于判断点到了单元格内部哪个子区域
localY 指针在当前单元格内部的相对 Y 坐标

适用场景:

  • 统一处理普通单元格点击
  • 区分表头点击和表体点击
  • 在自定义 render 中根据 localX/localY 做更细粒度交互

selection-change / selection-end

{
  range: SelectionRange | null
}
字段 含义
range 当前选区。为 null 代表没有有效选区

区别:

  • selection-change 在拖拽过程中持续触发,适合实时展示状态
  • selection-end 只在拖拽完成后触发,适合做最终提交或复制逻辑

row-select-change

{
  indices: number[]
  rows: T[]
}
字段 含义
indices 当前页中被选中的行索引数组
rows indices 对应的行数据数组

注意:这里不是全量数据索引,也不是业务 id。

col-resize

{
  key: string
  width: number
}
字段 含义
key 被调整宽度的列 key
width 调整结束后的列宽

row-resize

{
  rowIndex: number
  height: number
}
字段 含义
rowIndex 被调整高度的 body 行索引
height 调整结束后的最终行高

sort-change

排序回调返回 SortState

  • key:当前参与排序的列 key
  • order:当前排序方向,可能是 'asc''desc'null

page-change

{
  page: number
  pageSize: number
}
字段 含义
page 切换后的页码,从 1 开始
pageSize 切换后的每页条数

Ref 方法

组件通过 defineExpose 暴露了一组实例方法,推荐配合模板 ref 调用。

interface ProTableInstance {
  scheduleRender(): void
  recalcLayout(): void
  scrollToRow(rowIndex: number): void
  scrollToColumn(colKey: string): void
  scrollTo(x?: number, y?: number): void

  selectRows(indices: number[]): void
  deselectRows(indices: number[]): void
  selectAll(): void
  deselectAll(): void
  getSelectedRowIndices(): number[]

  getSelection(): SelectionRange | null
  clearSelection(): void

  getSortState(): SortState
  setSortState(state: SortState): void

  getScrollLeft(): number
  getScrollTop(): number

  toggleExpand(rowKey: string | number): void
  expandAll(): void
  collapseAll(): void
  getExpandedKeys(): Array<string | number>

  goTo(page: number): void
  prevPage(): void
  nextPage(): void
  setPageSize(size: number): void
  getCurrentPage(): number
  getPageCount(): number
  getTotal(): number
}

方法说明

方法 参数 返回值 说明
scheduleRender void 手动请求下一帧重绘
recalcLayout void 重新计算布局,并自动夹紧滚动位置
scrollToRow rowIndex: number void 滚动到指定 body 行,使该行进入可视区
scrollToColumn colKey: string void 滚动到指定主区列。固定列不会参与横向滚动
scrollTo x?: number, y?: number void 直接设置横纵滚动位置
selectRows indices: number[] void 追加选中指定索引
deselectRows indices: number[] void 取消指定索引
selectAll void 全选当前页数据
deselectAll void 清空选择
getSelectedRowIndices number[] 获取当前已选中的当前页索引
getSelection SelectionRange \| null 获取当前单元格选区
clearSelection void 清空选区
getSortState SortState 获取当前排序状态
setSortState state: SortState void 直接设置排序状态并重绘
getScrollLeft number 获取当前横向滚动位置
getScrollTop number 获取当前纵向滚动位置
toggleExpand rowKey: string \| number void 切换树节点展开状态
expandAll void 展开全部树节点
collapseAll void 折叠全部树节点
getExpandedKeys Array<string \| number> 获取当前已展开 rowKey 集合
goTo page: number void 翻到指定页
prevPage void 上一页
nextPage void 下一页
setPageSize size: number void 设置每页条数,并重置到第 1 页
getCurrentPage number 获取当前页码
getPageCount number 获取总页数
getTotal number 获取总条数

方法参数与行为说明

scheduleRender()

  • 含义:请求组件在下一帧重新绘制
  • 什么时候用:外部数据没有变,但你知道自定义覆盖层或内部显示状态需要刷新时
  • 注意:它只负责重绘,不负责重新计算布局

recalcLayout()

  • 含义:重新计算列宽、行高、总宽高、固定区宽度等布局信息
  • 什么时候用:容器尺寸变化、列定义变化、你手动修改了需要影响布局的数据时
  • 补充:内部会顺带把滚动位置限制到合法范围,避免空白区域

scrollToRow(rowIndex)

  • 参数含义:rowIndex 是 body 区数据索引,从 0 开始
  • 行为:若目标行已在可视区内,不会多余滚动;若越界则直接忽略
  • 注意:这里不支持传固定行索引,也不是业务主键

scrollToColumn(colKey)

  • 参数含义:colKey 是你在 columns 中定义的列 key
  • 行为:只会滚动主区列;如果目标列本身是固定列,不会产生横向滚动效果
  • 适用场景:表单校验后快速跳到某一列、联动定位某列

scrollTo(x, y)

  • 参数含义:x 是横向滚动值,y 是纵向滚动值,单位都是像素
  • 行为:任一参数传 undefined 表示该方向保持不变
  • 补充:内部会自动夹紧到合法滚动范围

selectRows(indices)

  • 参数含义:indices 是当前页内需要追加选中的行索引数组
  • 行为:是“追加选中”,不会先清空已有选择

deselectRows(indices)

  • 参数含义:indices 是当前页内需要取消选择的行索引数组
  • 行为:只移除指定项,不影响其它已选行

selectAll()

  • 含义:选中当前分页切片中的全部行
  • 注意:不是全量数据全选

deselectAll()

  • 含义:清空当前组件维护的行选中状态

getSelectedRowIndices()

  • 返回值含义:返回当前页中已选行索引,结果会按从小到大排序

getSelection()

  • 返回值含义:返回当前单元格框选范围
  • 结果解释:若返回 null,表示当前没有有效选区

clearSelection()

  • 含义:清空当前单元格选区,不影响行选择状态

getSortState() / setSortState(state)

  • getSortState():获取当前排序列和排序方向
  • setSortState(state):直接改排序状态并重绘
  • state.key:排序列 key
  • state.order'asc''desc'null
  • 注意:这里是直接设置内部排序状态,适合做外部排序同步

getScrollLeft() / getScrollTop()

  • 返回值含义:当前实际滚动位置,单位是像素

toggleExpand(rowKey)

  • 参数含义:rowKey 是树节点业务主键,对应 treeProps.rowKey 指定的字段值
  • 行为:已展开则折叠,未展开则展开
  • 懒加载场景:首次展开时可能触发 loadChildren

expandAll() / collapseAll()

  • 含义:一次性展开或折叠全部树节点
  • 注意:只对树形模式有效

getExpandedKeys()

  • 返回值含义:返回当前所有已展开节点的 rowKey 数组

goTo(page)

  • 参数含义:目标页码,从 1 开始
  • 行为:内部会自动限制在合法页码范围内

prevPage() / nextPage()

  • 含义:翻到上一页或下一页
  • 行为:到达边界时不会继续超出

setPageSize(size)

  • 参数含义:新的每页条数
  • 行为:更新后会把当前页重置到第 1

getCurrentPage() / getPageCount() / getTotal()

  • getCurrentPage():当前页码
  • getPageCount():按 total / pageSize 计算出的总页数
  • getTotal():当前总条数,优先取 pagination.total

核心类型说明

类型定义位于 components/pro-table/types.ts

RowMeta / RowData

interface RowMeta {
  __checkable__?: boolean
  __resizable__?: boolean
  __minHeight__?: number
  __maxHeight__?: number
  __level__?: number
  __expanded__?: boolean
  __hasChildren__?: boolean
  __isLeaf__?: boolean
  __loading__?: boolean
}

type RowData = RowMeta & Record<string, any>
字段 类型 说明
checkable boolean 类型中定义为“是否允许勾选”。但当前源码未在行选择逻辑中消费该字段,如需禁选需自行扩展
resizable boolean 设为 true 后,该行底边会出现行高拖拽手柄
minHeight number 行高拖拽最小值,默认 20
maxHeight number 行高拖拽最大值,默认 4000
level number 树形模式下自动注入的层级
expanded boolean 树形模式下自动注入的展开状态
hasChildren boolean 树形模式下自动注入,表示是否有子节点
isLeaf boolean 树形模式下自动注入,表示是否叶子节点
loading boolean 懒加载树形节点时的加载中状态

CellSpan

interface CellSpan {
  colspan?: number
  rowspan?: number
}

用于描述单元格合并:

  • colspan 表示向右合并几列
  • rowspan 表示向下合并几行
  • 列合并不能跨固定区,fixedLeft、主区、fixedRight 各自独立

ColumnNode

interface ColumnNode {
  key: string
  title: string
  width?: number
  minWidth?: number
  maxWidth?: number
  resizable?: boolean
  headerAlign?: 'left' | 'center' | 'right'
  cellAlign?: 'left' | 'center' | 'right'
  fixed?: 'left' | 'right'
  cellBgColor?: string
  render?: (params: CellRenderParams) => void
  children?: ColumnNode[]
  sortable?: boolean
  sorter?: (a: RowData, b: RowData) => number
  defaultSortOrder?: 'asc' | 'desc' | null
  cellOverflow?: 'clip' | 'ellipsis' | 'wrap'
  maxLines?: number
  tooltip?: boolean
  span?: (row: RowData, rowIndex: number) => CellSpan | null | undefined
}
字段 类型 说明
key string 列唯一标识,必须唯一
title string 表头标题
width number 列宽
minWidth number 最小列宽,拖拽时生效,默认 30
maxWidth number 最大列宽,拖拽时生效,默认 4000
resizable boolean 是否允许拖拽调整列宽
headerAlign TextAlign 表头文字对齐
cellAlign TextAlign 单元格文字对齐
fixed 'left' \| 'right' 固定列方向。父列设置后子列会继承
cellBgColor string 当前列的单元格背景色
render (params: CellRenderParams) => void 自定义单元格绘制函数。有该函数时默认文本不再绘制
children ColumnNode[] 多级表头子列
sortable boolean 是否支持排序
sorter (a, b) => number 自定义排序函数
defaultSortOrder 'asc' \| 'desc' \| null 初始排序状态
cellOverflow 'clip' \| 'ellipsis' \| 'wrap' 文本溢出处理方式
maxLines number 折行时最大行数,0 表示不限
tooltip boolean H5 悬浮或小程序点击时显示完整内容
span (row, rowIndex) => CellSpan body 单元格动态合并配置

CellRenderParams

自定义列 render 和固定行 cellRender 会收到以下参数:

interface CellRenderParams {
  ctx: IRenderer
  x: number
  y: number
  width: number
  height: number
  row: RowData
  value: any
  rowIndex: number
  align: TextAlign
  fontSize: number
  paddingX: number
  textColor: string
  isHovered: boolean
  hoveredLocalX: number
  hoveredLocalY: number
  pressedAreaKey: string | null
  drawCircle(fillColor: string, text?: string, textColor?: string): void
  drawText(text: string | number, color?: string): void
  drawButtons(buttons: ActionButtonConfig[]): void
  registerClickArea(
    key: string,
    x: number,
    y: number,
    w: number,
    h: number,
    onClick: (row: RowData, rowIndex: number) => void,
  ): void
}

几个常用能力:

  • drawText:按列对齐和内边距绘制文本
  • drawCircle:绘制圆形徽标
  • drawButtons:绘制操作按钮并自动接管点击态
  • registerClickArea:注册当前单元格内部的局部点击区域

字段含义补充:

字段 含义
ctx 当前渲染器实例,可直接调用绘图 API
x / y 单元格左上角坐标
width / height 单元格宽高
row 当前行数据对象
value 当前列在该行上的值
rowIndex 当前行索引
align 当前列最终文本对齐方式
fontSize 当前实际字号
paddingX 当前单元格水平内边距
textColor 当前默认文字颜色
isHovered 当前单元格所在行是否处于 hover 状态
hoveredLocalX / hoveredLocalY 指针位于单元格内部的相对坐标,未 hover 时通常为 -1
pressedAreaKey 当前被按下的内部点击区域 key,没有则为 null

ActionButtonConfig

interface ActionButtonConfig {
  key: string
  label: string
  type?: 'button' | 'link'
  color?: string
  textColor?: string
  hoverColor?: string
  onClick?: (row: RowData, rowIndex: number) => void
}
字段 类型 说明
key string 按钮唯一标识
label string 按钮文案
type 'button' \| 'link' 展现样式,默认 link
color string 主色,默认 #1890ff
textColor string 按钮文字色,仅 button 模式下有效
hoverColor string hover 时颜色
onClick (row, rowIndex) => void 点击回调

FixedRowDef

interface FixedRowDef {
  position: 'top' | 'bottom'
  data: RowData
  cellRender?: Record<string, (params: CellRenderParams) => void>
  spans?: Record<string, CellSpan>
}
字段 类型 说明
position 'top' \| 'bottom' 固定行位置
data RowData 固定行数据
cellRender Record<string, (params) => void> 指定列 key 的固定行自定义绘制,优先级高于列级 render
spans Record<string, CellSpan> 固定行单元格合并配置

ProTableOptions

interface ProTableOptions {
  borderColor?: string
  headerBgColor?: string
  bodyBgColor?: string
  hoverRowBgColor?: string
  hoverColBgColor?: string
  stripedBgColor?: string
  textColor?: string
  fontSize?: number
  padding?: number | [number, number]
  rowBgColor?: (row: RowData, rowIndex: number) => string | undefined
  cellBgColor?: (row: RowData, rowIndex: number, colKey: string) => string | undefined
  selectionFillColor?: string
  selectionBorderColor?: string
  resizeHandleVisible?: boolean
}

实际默认值如下:

{
  borderColor: '#e8e8e8',
  headerBgColor: '#fafafa',
  bodyBgColor: '#ffffff',
  hoverRowBgColor: '#f5f5f5',
  hoverColBgColor: '#f0f7ff',
  stripedBgColor: '#fafafa',
  textColor: '#333333',
  fontSize: 13,
  padding: [8, 8],
  selectionFillColor: 'rgba(24,144,255,0.12)',
  selectionBorderColor: '#1890ff',
  resizeHandleVisible: false,
}

说明:

  • padding 支持 number[paddingY, paddingX]
  • 行高会按 ceil(fontSize * 1.2) + paddingY * 2 自动推导
  • rowBgColor 是行级背景色回调
  • cellBgColor 优先级高于 rowBgColor 和列级 cellBgColor
  • resizeHandleVisible 当前实际默认值是 false

字段含义补充:

字段 含义
borderColor 单元格网格线颜色
headerBgColor 表头背景色
bodyBgColor 表体默认背景色
hoverRowBgColor 行 hover 时覆盖的背景色
hoverColBgColor 列 hover 时覆盖的背景色
stripedBgColor 斑马纹行背景色
textColor 默认文字颜色
fontSize 默认字号,会参与行高计算
padding 单元格内边距,控制内容与边框的距离
rowBgColor 按行动态返回背景色的回调
cellBgColor 按单元格动态返回背景色的回调
selectionFillColor 选区内部填充色
selectionBorderColor 选区边框颜色
resizeHandleVisible 是否绘制列宽/行高拖拽手柄指示条

RowSelectionConfig

interface RowSelectionConfig {
  type?: 'checkbox' | 'radio'
  columnTitle?: string
  columnWidth?: number | string
  fixed?: boolean
  hideSelectAll?: boolean
}
字段 类型 说明
type 'checkbox' \| 'radio' 选择模式,默认 checkbox
columnTitle string 选择列表头标题。设置后表头不再绘制默认全选框
columnWidth number \| string 选择列宽,默认 40。传字符串时会用 parseInt 解析
fixed boolean 是否固定到左侧,默认 true
hideSelectAll boolean 隐藏表头全选框,仅 checkbox 模式且未设置 columnTitle 时有效

注意事项:

  • selectedRowKeysrow-select-change.indices 使用的是当前分页切片内的索引,不是业务主键
  • selectAll() 也只作用于当前页数据

SelectionRange

interface SelectionRange {
  startRow: number
  endRow: number
  startColIndex: number
  endColIndex: number
}

SelectionRange 中的行索引是统一虚拟行索引:

  • 负值:固定顶部行
  • 0 ~ data.length - 1:body 行
  • 大于等于 data.length:固定底部行

列索引对应 layout.leafColumns 顺序,也就是“固定左列 -> 主区列 -> 固定右列”。

字段含义补充:

字段 含义
startRow 选区起始行
endRow 选区结束行
startColIndex 选区起始列索引
endColIndex 选区结束列索引

说明:起止值不要求一定是左上到右下,消费时建议自己做一次 min/max 归一化。

SortState

type SortOrder = 'asc' | 'desc' | null

interface SortState {
  key: string
  order: SortOrder
}
字段 类型 说明
key string 当前排序列 key
order 'asc' \| 'desc' \| null 排序方向

TreeConfig

interface TreeConfig {
  childrenKey?: string
  indent?: number
  defaultExpandAll?: boolean
  defaultExpandedKeys?: Array<string | number>
  rowKey?: string
  treeColumnKey?: string
  lazy?: boolean
  loadChildren?: (row: RowData) => Promise<RowData[]>
  hasChildrenField?: string
}
字段 类型 说明
childrenKey string 子节点字段名,默认 children
indent number 每级缩进像素,默认 8
defaultExpandAll boolean 初始是否展开全部
defaultExpandedKeys Array<string \| number> 初始展开的 rowKey 列表
rowKey string 行唯一键字段,默认 id
treeColumnKey string 显示树形缩进和展开图标的列 key,默认第一列叶子列
lazy boolean 是否启用懒加载树
loadChildren (row) => Promise<RowData[]> 懒加载时首次展开节点所调用的异步方法
hasChildrenField string 标识可展开节点的字段名,默认 hasChildren

行为说明:

  • 懒加载模式下,首次展开某个节点时会调用 loadChildren
  • 加载过程中会给该行注入 __loading__ = true
  • toggleExpand(rowKey) 传的是 rowKey 值,不是行索引

PaginationConfig

interface PaginationConfig {
  current: number
  pageSize: number
  total: number
  pageSizeOptions?: number[]
}
字段 类型 说明
current number 当前页码,从 1 开始
pageSize number 每页条数
total number 总条数。服务端分页时可传后端总数
pageSizeOptions number[] 每页条数备选值,仅作为配置数据保存,组件本身不渲染分页器

行为说明:

  • 不传 pagination 时,组件直接使用全量数据
  • 传入 pagination 时,组件对当前数据执行切片
  • 组件提供分页方法和 page-change 事件,但不提供内置分页栏 UI

OverlayDrawPayload

bodyOverlayDrawfixedTopOverlayDrawfixedBottomOverlayDraw 会收到以下 payload:

interface OverlayDrawPayload {
  renderer: IRenderer
  helper: any
  getColIndexByKey(key: string): number
  getCellCenter(colIndex: number, rowIndex: number): { x: number; y: number }
  getCellRadius(colIndex: number): number
  drawCircle(x: number, y: number, r: number, color: string, text?: string, textColor?: string): void
  drawPolyline(points: Array<{ x: number; y: number }>, color: string, lineWidth?: number): void
  drawCellBg(colIndex: number, rowIndex: number, color: string): void
  drawText(
    text: string,
    x: number,
    y: number,
    opts?: {
      color?: string
      fontSize?: number
      align?: 'left' | 'center' | 'right'
      baseline?: 'top' | 'middle' | 'bottom'
    },
  ): void
}

这个 payload 适合做趋势线、角标、额外装饰、热力区块等高阶绘制。

字段含义补充:

字段 含义
renderer 底层渲染器实例,适合做更底层的自定义绘图
helper 内部坐标辅助对象,封装了单元格定位和常用绘制能力
getColIndexByKey 根据列 key 找到叶子列索引
getCellCenter 获取某个单元格中心点坐标
getCellRadius 获取某列单元格适合绘圆点时的推荐半径
drawCircle 在指定位置绘制一个圆,可附带居中文字
drawPolyline 根据点集绘制折线
drawCellBg 给指定单元格补一层背景色
drawText 在任意坐标绘制文字,可指定颜色、字号、对齐和基线

常见用法

1. 行选择

<pro-table
  v-model:selectedRowKeys="selectedRowKeys"
  :columns="columns"
  :data="data"
  :row-selection="{ type: 'checkbox', columnWidth: 48 }"
  @row-select-change="onRowSelectChange"
/>
const selectedRowKeys = ref<number[]>([])

function onRowSelectChange(payload: { indices: number[]; rows: RowData[] }) {
  console.log(payload.indices, payload.rows)
}

2. 树形表格

<pro-table
  :columns="columns"
  :data="treeData"
  :tree-props="{
    rowKey: 'id',
    childrenKey: 'children',
    treeColumnKey: 'name',
    indent: 12,
    defaultExpandAll: true,
  }"
/>

3. 固定行

const fixedRows: FixedRowDef[] = [
  {
    position: 'top',
    data: { name: '顶部汇总', salary: 300000 },
  },
  {
    position: 'bottom',
    data: { name: '底部合计', salary: 280000 },
    spans: {
      name: { colspan: 2 },
    },
  },
]

4. 自定义单元格绘制

const columns: ColumnNode[] = [
  {
    key: 'progress',
    title: '进度',
    width: 120,
    render: ({ ctx, x, y, width, height, value, drawText }) => {
      const percent = Number(value) || 0
      ctx.setFillStyle('#f0f0f0')
      ctx.fillRect(x + 8, y + height / 2 - 4, width - 16, 8)

      ctx.setFillStyle('#1890ff')
      ctx.fillRect(x + 8, y + height / 2 - 4, ((width - 16) * percent) / 100, 8)

      drawText(`${percent}%`)
    },
  },
]

使用注意事项

1. data 变更建议替换引用

组件对 data 使用的是引用级 watch,而不是深度 watch。这样做是为了避免大数组深遍历的性能开销。

推荐:

data.value = [...data.value, newRow]

不推荐依赖深层属性原地修改后自动触发布局重算。

2. 行选择索引是“当前页索引”

无论是 selectedRowKeysrow-select-change.indicesgetSelectedRowIndices(),当前实现返回的都是分页切片内索引,而不是业务主键。

如果你的业务需要稳定主键选择,建议在外层把索引映射成真实 id 存储。

3. 分页是逻辑分页,不是完整分页组件

pagination 只负责:

  • 当前页切片
  • 页码状态
  • 对外暴露翻页方法
  • 触发 page-change

它不负责渲染页码器、页大小切换器、总数展示。

4. resizeHandleVisible 当前默认是 false

源码合并默认值时,resizeHandleVisible 的实际默认行为是 false。如果你希望显示列宽 / 行高拖拽手柄,需要显式设置:

const options: ProTableOptions = {
  resizeHandleVisible: true,
}

建议的类型导入方式

import type {
  RowData,
  ColumnNode,
  ProTableOptions,
  FixedRowDef,
  RowSelectionConfig,
  SelectionRange,
  SortState,
  TreeConfig,
  PaginationConfig,
  CellRenderParams,
  ActionButtonConfig,
  OverlayDrawPayload,
} from '@/uni_modules/pro-table'

隐私、权限声明

1. 本插件需要申请的系统权限列表:

无特殊权限

2. 本插件采集的数据、发送的服务器地址、以及数据用途说明:

不采集任何数据

3. 本插件是否包含广告,如包含需详细说明广告表达方式、展示频率:

无广告

暂无用户评论。