@canvas-components/react-components
@canvas-components/react-components 提供一组为表格适配层和业务表单场景准备的 React 基础组件,包含输入类组件、弹层、过渡、虚拟列表、分页和图片预览等能力。
功能作用
- 提供统一风格的 React 基础交互组件
- 为
@canvas-components/react-list-table提供编辑器、弹层和辅助 UI - 暴露
Popup、Popconfirm、Transition、VirtualList等可独立复用组件
安装方法
pnpm add @canvas-components/react-components react@^16.8 react-dom@^16.8
最低依赖版本:
react >= 16.8.0react-dom >= 16.8.0Node.js >= 18.12.0pnpm >= 9.0.0
使用方法
import {
ReactHomeOutlined,
ReactIcon,
ReactPopconfirm,
ReactPopup,
ReactTransition,
} from "@canvas-components/react-components";
function Demo() {
return (
<>
<ReactIcon name="HomeOutlined" size={20} aria-label="首页" />
<ReactHomeOutlined size={20} aria-hidden="true" />
<ReactPopconfirm
title="确认删除这条记录?"
description="删除后不可恢复"
onConfirm={() => console.log("confirmed")}
>
<button type="button">删除</button>
</ReactPopconfirm>
</>
);
}
表单组件
组件可作为受控输入使用,也可以放进普通 HTML 表单或 ReactForm 中。以下示例组合文本框、可搜索选择器、日期选择器、复选框、按钮和确认气泡:
import { useState } from "react";
import {
ReactButton,
ReactCheckbox,
ReactDatePicker,
ReactFlex,
ReactInput,
ReactPopconfirm,
ReactSelect,
} from "@canvas-components/react-components";
export function ProfileForm() {
const [name, setName] = useState("林晨");
const [team, setTeam] = useState("design");
const [date, setDate] = useState("2026-10-18");
const [subscribed, setSubscribed] = useState(true);
return (
<form onSubmit={(event) => event.preventDefault()}>
<label>
姓名
<ReactInput
value={name}
onChange={(event) => setName(event.currentTarget.value)}
/>
</label>
<label>
团队
<ReactSelect
value={team}
showSearch
options={[
{ value: "design", label: "设计团队" },
{ value: "engineering", label: "研发团队" },
]}
onChange={setTeam}
/>
</label>
<ReactDatePicker value={date} onChange={setDate} />
<ReactCheckbox
checked={subscribed}
onChange={(event) => setSubscribed(event.currentTarget.checked)}
>
接收团队动态
</ReactCheckbox>
<ReactFlex gap={8}>
<ReactButton type="primary" htmlType="submit">
保存
</ReactButton>
<ReactPopconfirm title="确认删除?" onConfirm={() => setName("")}>
<ReactButton danger>删除</ReactButton>
</ReactPopconfirm>
</ReactFlex>
</form>
);
}
文档站「React Components」目录为每个组件提供了独立示例,包含组件用途、属性说明和可复制的 JSX 用法;图标目录也列出全部具名图标。
ReactSelect 的暗色模式通过 ReactConfigProvider 配置。输入框与挂载到页面外层的下拉面板会使用同一组颜色:
import {
ReactConfigProvider,
ReactSelect,
} from "@canvas-components/react-components";
<ReactConfigProvider
theme={{
colorScheme: "dark",
colorText: "#e8ebee",
colorTextSecondary: "#a4adb5",
colorBorder: "#3b4348",
colorBackground: "#24282d",
colorBackgroundSoft: "#2b3035",
colorBackgroundHover: "#30363b",
colorBackgroundActive: "#263e59",
}}
>
<ReactSelect options={[{ label: "选项一", value: "one" }]} />
</ReactConfigProvider>;
组件列表
表单与选择
ReactInputReactInputNumberReactInputRangeReactCheckboxReactRadioReactSelectReactAutoCompleteReactCascaderReactTreeSelectReactColorPickerReactTextAreaReactForm
ReactInputNumber 和 ReactInputRange 默认不使用鼠标滚轮调整数值;需要该行为时传入 changeOnWheel,例如 <ReactInputNumber value={count} onChange={setCount} changeOnWheel />。
日期时间
ReactDatePickerReactDateRangePickerReactDateTimePickerReactDateTimeRangePickerReactTimePickerReactTimeRangePickerReactMonthPickerReactQuarterPickerReactYearPicker
弹层与反馈
ReactPopupReactDropdownReactModalReactDrawerReactPopconfirmReactTooltipReactTransitionreactMessage
展示、布局与交互
ReactPaginationReactVirtualListReactWaterfallReactResizablePanelsReactImagePreviewReactButtonReactTagReactIcon与 831 个内置 SVG 图标(例如ReactHomeOutlined)ReactFlex/ReactRow/ReactColReactFilterPanel
属性说明
ReactPagination
<ReactPagination
current={current}
total={1000}
pageSize={pageSize}
showSizeChanger
allowPageSizeInput
minPageSize={5}
maxPageSize={500}
onChange={setCurrent}
onPageSizeChange={(page, size) => {
setCurrent(page);
setPageSize(size);
}}
/>
allowPageSizeInput 默认关闭。开启后可在每页条数下拉框中输入正整数,按回车或失焦提交;合法值触发 onPageSizeChange(1, size),并在当前组件挂载期间作为去重、升序的候选项保留,切换到其他条数后仍可再次选择。空候选列表也支持输入。自定义选项右侧可点击删除,预设选项和默认每页 10 条不可删除;删除当前选中的自定义项时回到每页 10 条并切回第 1 页,若 10 超出配置范围则取范围内最近的值。删除其他项不改变当前分页,删除后仍可重新输入该值。
minPageSize 默认 1,maxPageSize 默认 Number.MAX_SAFE_INTEGER,上下限均包含边界。非法或越界输入不触发变更,失焦恢复当前值;范围外的候选项不可选择。无效的上下限使用默认值,最大值小于最小值时按最小值处理。组件不会主动修改外部传入的当前 pageSize。
ReactTag
<ReactTag closeLabel="移除标题" onClose={() => removeTag("title")}>
标题
</ReactTag>
children 可放文字或其他 React 内容;省略 onClose 时只展示标签。可用 className、style 和原生 span 属性调整外观。移除按钮使用 type="button",在表单中不会触发提交。
ReactDropdown
<ReactDropdown
items={[
{ key: "json", label: "导出 JSON" },
{ key: "pdf", label: "导出 PDF", description: "实验性功能" },
]}
onSelect={(key) => exportFile(key)}
>
导出
</ReactDropdown>
children 可省略;只传 icon 时触发按钮显示居中的图标,建议同时通过 triggerProps 提供 aria-label。菜单项支持禁用、图标、说明、拖拽事件和指针进入事件。可用 open、defaultOpen、onOpenChange 控制展开状态;支持方向键、Home、End 和 Esc。
ReactPopupProps
| 属性 | 类型 | 说明 |
|---|---|---|
open | boolean | 是否显示 |
anchorRef | RefObject<HTMLElement | null> | 锚点元素引用 |
anchorRect | PopupAnchorRect | null | 外部传入的锚点矩形 |
placement | "bottomLeft" | "bottomRight" | "topLeft" | "topRight" | "rightTop" | "rightBottom" | "leftTop" | "leftBottom" | 弹层位置 |
offset | number | 与锚点间距 |
matchAnchorWidth | boolean | 是否跟随锚点宽度 |
minWidth | number | 最小宽度 |
zIndex | number | 层级 |
className | string | 外层类名 |
surfaceClassName | string | 面板类名 |
style | CSSProperties | 外层样式 |
surfaceStyle | CSSProperties | 面板样式 |
onOpenChange | (open: boolean) => void | 打开状态变化回调 |
children | ReactNode | 弹层内容 |
ReactPopconfirmProps
| 属性 | 类型 | 说明 |
|---|---|---|
children | ReactNode | 触发器内容 |
title | ReactNode | 标题 |
description | ReactNode | 描述文本 |
open / defaultOpen | boolean | 受控 / 非受控打开状态 |
disabled | boolean | 是否禁用 |
placement | ReactPopconfirmPlacement | 弹层位置 |
offset | number | 触发器与弹层间距 |
zIndex | number | 层级 |
icon | ReactNode | 自定义图标,传 null 隐藏默认图标 |
okText / cancelText | ReactNode | 按钮文案 |
showCancel | boolean | 是否显示取消按钮 |
confirmLoading | boolean | 是否强制确认按钮 loading |
okButtonProps / cancelButtonProps | ReactPopconfirmButtonProps | 按钮透传属性 |
onConfirm | (event) => void | Promise<void> | 点击确认回调,支持异步 |
onCancel | (event) => void | 点击取消回调 |
onOpenChange | (open: boolean) => void | 状态变化回调 |
className / style | string / CSSProperties | 触发器样式 |
popupClassName / popupStyle | string / CSSProperties | 弹层面板样式 |
ReactTransitionProps
| 属性 | 类型 | 说明 |
|---|---|---|
show | boolean | 是否显示内容 |
name | string | CSS 类名前缀 |
duration | number | { enter?: number; leave?: number } | 动画时长 |
appear | boolean | 首次显示是否执行进入动画 |
children | (state: ReactTransitionState) => ReactNode | 根据阶段渲染内容 |
ReactVirtualListProps<Item>
| 属性 | 类型 | 说明 |
|---|---|---|
items | Item[] | 数据列表 |
height | number | 视口高度 |
itemHeight | number | 固定项高度 |
overscan | number | 预渲染项数 |
renderItem | (item, index, meta) => ReactNode | 渲染函数 |
itemKey | (item, index) => string | number | 列表 key |
方法说明
ReactTransition
| 导出 | 说明 |
|---|---|
ReactTransition | 无包装过渡组件,离场动画结束后自动卸载 |
useReactTransition | 获取 Vue 风格过渡阶段和 className |
ReactVirtualListRef
| 方法 | 说明 |
|---|---|
scrollTo | 滚动到指定位置 |
scrollToIndex | 滚动到指定索引 |
其他导出
| 导出 | 说明 |
|---|---|
ReactContentScaleProvider / useReactContentScale | 内容缩放上下文 |
REACT_COMPONENT_PREFIX | 统一类名前缀 |
说明
这个包的导出面比较大,输入类组件大多保持接近原生表单语义;如果需要精确字段,请优先查看对应组件的 Props 类型定义。
图标组件使用包内自包含的 SVG 路径数据,不需要安装额外图标运行时或图标数据包。图标名称、尺寸、颜色、旋转和加载动画由 ReactIconProps 提供;也可以直接使用 ReactHomeOutlined 等具名组件。SVG 路径数据的上游许可和版权信息见随包发布的 THIRD_PARTY_NOTICES.md。
通用折叠面板
ReactCollapsePanel 使用现有方向图标,支持鼠标及 Enter / 空格展开折叠。折叠时保留内容节点和输入草稿。
<ReactCollapsePanel title="位置与尺寸" defaultOpen>
<ReactInput placeholder="输入名称" />
</ReactCollapsePanel>
通过 open 与 onOpenChange 控制展开状态;disabled 禁止切换,contentClassName 可定制内容区样式。默认收起。
通用拖拽排序
ReactSortableList 统一提供与 ListTable 工具栏列排序一致的浮动行、实时让位动画、边缘自动滚动和全屏浮层。通过 items(包含 key、parentKey、label)、renderItem(item, handleProps) 和 onOrderChange(parentKey, orderedKeys) 接入;把 handleProps 传给使用现有图标的拖拽手柄。scrollContainerRef 指向滚动容器,disabled 禁止拖拽,dragThreshold 默认 4px。Esc、失焦和指针取消会丢弃排序,放下才提交一次顺序。后续拖拽排序统一复用此组件。
大量节点可传入 virtual={{ height: 360, itemHeight: 34, overscan: 6 }} 启用固定行高虚拟列表;组件使用内部滚动容器自动滚动,拖拽命中按完整列表计算,包含尚未挂载的节点。