
Ant Design Transfer 穿梭框基本用法完全指南从双栏数据流到源码级原理【免费下载链接】ant-designAn enterprise-class UI design language and React UI library项目地址: https://gitcode.com/gh_mirrors/antde/ant-design本文以 Ant Design本仓库下称 antd中 Transfer 穿梭框的基本用法示例为核心系统讲解穿梭框的组件定位、数据模型、受控用法与渲染扩展并结合组件 API 文档与 index.jsx 源码深入剖析其内部数据流与事件回调帮助读者在真实业务中快速落地左选右移的穿梭选择场景。一、Transfer 是什么双栏穿梭选择框Transfer中文名穿梭框是 antd 表单类组件中的一员见 index.md 头部元信息其定位是用直观的方式在两栏中移动元素完成选择行为。它适用于需要从大量候选项中挑选若干项并归档到结果区的业务场景例如用户角色分配、权限点配置、可见字段勾选、消息订阅对象选择等。组件由三大部分拼装而成见 index.jsx 源码左侧 List源列表展示全部候选数据支持勾选与可选的搜索过滤中间 Operation操作区提供向右移动 / 向左移动两个按钮右侧 List目的列表展示已被选入targetKeys的数据。三者分别由Listlist.jsx、Operationoperation.jsx、Searchsearch.jsx三个内部组件实现并作为静态属性挂载在Transfer上Transfer.List List等见 index.jsx 第 250-252 行。二、基本用法示例拆解核心基本用法 demo 是最小可运行的完整示例原文如下保留原样import { Transfer, Button } from antd; const App React.createClass({ getInitialState() { return { mockData: [], targetKeys: [], }; }, componentDidMount() { this.getMock(); }, getMock() { let targetKeys []; let mockData []; for (let i 0; i 20; i) { const data { key: i, title: 内容${i 1}, description: 内容${i 1}的描述, chosen: Math.random() * 2 1 }; if (data.chosen) { targetKeys.push(data.key); } mockData.push(data); } this.setState({ mockData, targetKeys }); }, handleChange(targetKeys, direction, moveKeys) { console.log(targetKeys, direction, moveKeys); this.setState({ targetKeys }); }, renderFooter() { return ( Button typeprimary sizesmall style{{ float: right, margin: 5 }} onClick{this.getMock} 刷新 /Button ); }, render() { return ( Transfer dataSource{this.state.mockData} targetKeys{this.state.targetKeys} onChange{this.handleChange} render{item item.title} / ); } }); ReactDOM.render(App /, mountNode);这个示例虽然在代码组织上使用了React.createClass的旧式写法组件挂载后通过componentDidMount拉取模拟数据但其传递组件的四个核心属性完全代表了 Transfer 最基本、最常用的用法属性示例中的值作用dataSourcethis.state.mockData全部候选数据源含左右两栏的数据全集targetKeysthis.state.targetKeys右侧框展示数据的 key 集合受控值onChangethis.handleChange穿梭动作发生后的回调用于更新targetKeysrenderitem item.title每行数据的渲染函数决定行内展示文本1. 数据模型key 是穿梭的唯一凭证dataSource中的每个数据对象必须包含唯一的key字段。示例中数据形如{ key: i, title: 内容N, description: 内容N的描述 }。Transfer 通过key完成全部定位工作左右分栏splitDataSource()index.jsx 第 23-45 行遍历targetKeys将dataSource中key命中的项从左侧数据中抠出并放入右侧列表返回{ leftDataSource, rightDataSource }勾选记录内部状态leftCheckedKeys/rightCheckedKeys存储的同样是 key 数组index.jsx 第 16-19 行移动判断moveTo()中向左移动即targetKeys.filter(targetKey !moveKeys.some(...))按 key 做差集index.jsx 第 47-62 行。因此保证dataSource中 key 唯一且稳定是穿梭框正常工作的前提。2. 受控组件targetKeys 与 onChange 配对使用Transfer 是典型的受控组件当前选中结果完全由外部传入的targetKeys决定。用户点击移动按钮后组件并不会自己记住结果而是通过onChange把新状态交还给调用方handleChange(targetKeys, direction, moveKeys) { console.log(targetKeys, direction, moveKeys); this.setState({ targetKeys }); }onChange回调签名见 index.md API 表为Function(targetKeys, direction, moveKeys)三个参数含义targetKeys移动之后完整的右侧 key 集合数组direction移动方向取值为right向右或left向左对应moveTo(direction)的传参index.jsx 第 47 行moveKeys本次实际被移动的 key 数组来自对应侧已勾选的checkedKeysindex.jsx 第 50 行。示例在回调中console.log三个参数正是为了方便观察每次穿梭动作的完整数据轨迹。3. render 函数定制每一行的展示render是一个Function(record)接收数据项、返回渲染内容。示例中render{item item.title}仅展示title字段若想展示更多信息可以像高级用法 demo 那样拼接多字段render{item \${item.title}-${item.description}}。需要注意render的返回值同时被用于搜索过滤——源码filterDataSource()index.jsx 第 87-92 行与列表项渲染list.jsx 第 84-96 行都会调用this.props.render(item)取文本因此若开启搜索框showSearchrender返回的文本将决定搜索匹配命中与否。4. footer 自定义底部示例额外演示了footer属性通过renderFooter返回一个刷新按钮点击后重新执行getMock()随机生成 20 条新数据实现重新随机分配左右两侧的效果。这展示了footer的典型用途——在列表底部放置自定义操作按钮源码在 list.jsx 第 124-126 行 将footer的返回值渲染进-footer容器。三、源码级原理一次点击背后的完整调用链为了理解基本用法中各属性的真实作用不妨追踪一次勾选后向右移动的完整调用链对应 index.jsx用户点击左侧列表某一行List组件内部触发handleSelectlist.jsx 第 31-35 行向上调用Transfer的handleSelect(left, item, checked)handleSelect维护leftCheckedKeys数组勾选则 push、取消则 splice见 index.jsx 第 128-146 行并触发重渲染因为leftCheckedKeys.length 0右侧移动按钮变为可用rightActiveindex.jsx 第 156-157 行按钮的实际禁用逻辑在 operation.jsx 第 20-29 行disabled{!rightActive}图标用Icon typeright/Icon typeleft点击向右移动按钮触发moveTo(right)index.jsx 第 47-62 行把leftCheckedKeys合并进targetKeys得到newTargetKeys清空左侧勾选最后调用this.props.onChange(newTargetKeys, right, moveKeys)外部handleChange收到回调setState({ targetKeys })更新受控值重渲染时splitDataSource()按新targetKeys重新分栏右侧列表出现新移入的条目界面完成穿梭。同一套机制下List内部还实现了全选 / 半选状态getGlobalCheckStatus()index.jsx 第 64-85 行依据当前勾选数与过滤后数据量返回all | part | none对应头部复选框的选中、半选indeterminate与未选状态渲染逻辑见 list.jsx 第 45-64 行。四、API 速查基本用法之外的完整参数表组件 API 文档 给出了全部参数在使用基本用法之外可按需扩展参数说明类型默认值dataSource数据源Array[]render每行数据渲染函数Function(record)-targetKeys显示在右侧框数据的 key 集合Array[]onChange变化时回调函数Function(targetKeys, direction, moveKeys)-listStyle两个穿梭框的自定义样式Object-className自定义类String-titles标题集合顺序从左至右Array[源列表, 目的列表]operations操作文案集合顺序从上至下先右后左Array[]showSearch是否显示搜索框BooleanfalsesearchPlaceholder搜索框的占位提示String请输入搜索内容notFoundContent当列表为空时显示的内容React.nodeNot Foundfooter底部渲染函数Function(props)-这些默认值均可在源码Transfer.defaultProps中找到对应实现index.jsx 第 217-230 行例如titles: [源列表, 目的列表]、operations: []、showSearch: false、searchPlaceholder: 请输入搜索内容、notFoundContent: Not Found。几个在基本用法之上的典型扩展详见同目录 demo开启搜索加showSearch并在dataSource数据上写好可搜索字段如带搜索框 demo同时可自定义notFoundContent如示例中的xxxxxx搜索输入与清空逻辑由 search.jsx 完成过滤匹配基于render返回文本的正则匹配index.jsx 第 94-97 行定制宽高与操作文案通过listStyle如{ width: 250, height: 300 }控制双栏尺寸通过operations如[向右操作文案, 向左操作文案]替换两个移动按钮的文字参考高级用法 demo自定义底部footer返回任意 React 节点如基本用法中的刷新按钮。组件的视觉样式定义于 transfer.less含-list、-operation、-header、-footer等类名约定与源码中的prefixCls: ant-transfer默认值对应需要定制外观时可从这些类名入手。五、小结与实践建议从基本用法 demo 出发可以提炼出使用 Transfer 的四个要点数据以key为纲dataSource每项必须有唯一且稳定的key左右分栏、勾选、移动全部基于它坚持受控写法始终用targetKeysonChange配对管理状态把数据流控制权留在业务组件中善用render一行函数即可定制行展示同时它也是搜索过滤的文本来源按需开启扩展能力showSearch、listStyle、operations、footer、titles等参数默认值见 index.jsx 的 defaultProps可在不改变核心数据流的前提下快速满足搜索、布局与定制化需求。理解上述数据流与 API 后即可将 Transfer 灵活接入表单提交、权限配置等真实业务场景中。【免费下载链接】ant-designAn enterprise-class UI design language and React UI library项目地址: https://gitcode.com/gh_mirrors/antde/ant-design创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考