[RFC] 新组件:TextSelection 文本划词操作 #58231
ZQDesigned
started this conversation in
RFCs
Replies: 4 comments 10 replies
|
一期api太多了吧;缩减点保证最小可用;陆续添加; |
5 replies
|
给 Popover/Dropdown 新增一种交互形式如何? |
1 reply
|
3 replies
|
如果参与浮层控制的确会后 Popover 感觉有点重复,语义上似乎又不应该和 Popover 合并。感觉可以参考一下 Tour 的形式,它也是非 vdm 绑定的。 |
1 reply
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Summary
计划在后续版本中新增一个
TextSelection组件。TextSelection用于在一段普通内容区域内选择可见文本,并在选区附近弹出上下文操作浮层。它主要服务于企业后台里常见的文本二次操作场景,例如关键词标记、脱敏、搜索、复制、批注入口等。本 RFC 提议的第一版只聚焦以下能力:
open受控与非受控模式Motivation
在很多中后台场景中,用户并不是只“阅读”文本,而是需要直接对选中的文本执行操作。尤其是在长文档、HTML 内容、审查页面、日志页面、知识库页面中,这类需求会反复出现。
典型场景包括:
今天用户当然可以通过浏览器
SelectionAPI 配合Popover自己拼装这套行为,但它并不简单:Range的定位细节容易踩坑相关 issue:#58165
我认为这类能力已经具备足够通用性,适合抽象为一个原子组件,同时保持足够轻量,不把业务数据模型和持久化状态内建进去。
Non-Goals
第一版不打算包含以下能力:
input、textarea、contenteditable内的文本选择如果第一版验证下来价值明确,这些能力可以在后续继续讨论。
API
TextSelection
(originNode, info) => ReactNodetrim()后的最小长度number1booleanfalsebooleanbooleanfalsePick<PopoverProps, 'placement' | 'arrow' | 'getPopupContainer' | 'autoAdjustOverflow' | 'destroyOnHidden' | 'zIndex'>(info: SelectionInfo | null) => void(open, info) => voidSelectionInfo
OpenChangeInfo
Basic Example
Custom Popup Example
Detailed Design
组件定位
TextSelection应该是一个独立组件,而不是Typography的新 prop。原因:
TypographyTypography继续聚焦于copyable、editable、ellipsis等文本展示能力选区范围
组件只响应自身子树内的有效选区。
一个“有效选区”需要满足:
trim()后不为空Range的起点和终点都在组件根节点内部minLengthinput、textarea或contenteditable内浮层行为
当产生有效选区时,浮层自动打开。
默认情况下,组件会渲染一个非常轻量的默认浮层,用来承载当前选中的文本内容。它的目标是提供稳定的选区锚定和最小展示约定,而不是内建完整业务动作。
浮层在以下情况下关闭:
Escapeopen变为false渲染策略
默认浮层会展示一份最小内容约定,第一版不提供可配置的
actions数据结构。当提供
popupRender时,会收到:originNode:默认浮层节点info:当前选区信息与辅助方法辅助方法包括:
close():关闭当前浮层update():基于最新选区重新计算浮层位置这套设计与 antd 现有的
popupRender、panelRender、actionsRender等自定义模式保持一致。浮层定位
浮层应基于选区
Range的矩形信息进行定位,而不是依赖一个普通触发元素。内部实现建议维护一个基于当前选区几何信息的虚拟锚点,并尽量复用现有 popup 的定位能力。
无障碍
第一版至少需要保证:
Escape可以关闭浮层classNames与stylesSemantic DOM
建议暴露以下语义槽位:
roottoolbaractionpopup.rootpopup.containerDemos
建议至少提供以下 demo:
可选后续 demo:
How we teach this
TextSelection新增组件文档页popupRender扩展用法示例input/textarea选区Adoption Strategy
第一版可以先完全实现在
antd内部,不急着拆出新的rc-*包。如果后续需求演进到以下方向:
再考虑下沉为更底层的包会更合适。
Alternatives Considered
方案一:给 Typography 增加
selectable当前不优先选择。
虽然
Typography已经有copyable和editable,但“划词后动作”比文本装饰和文本编辑更宽,会让Typography语义继续变重。方案二:只提供 Hook
当前不优先选择。
Hook 当然更灵活,但它无法提供标准化的 antd 浮层行为、语义 DOM 和一致的 API 体验。对于一个准备面向社区推广的新能力来说,组件化更符合预期。
方案三:给 Popover / Dropdown 增加一种基于文本选区的交互形式
当前不优先选择。
这个方向看起来可以减少新组件数量,但这里的复杂度并不只在“弹层如何展示”,还包括:
这些行为已经超过了给通用弹层新增一种
trigger的范围。相比把这套状态机塞进Popover/Dropdown,独立组件的边界会更清晰,也更利于后续演进。All reactions