尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

Slate v2 Inline 家族迁移第一切片:Mentions 的运行时接缝设计与浏览器验证(plate 项目解析)

Slate v2 Inline 家族迁移第一切片:Mentions 的运行时接缝设计与浏览器验证(plate 项目解析) Slate v2 Inline 家族迁移第一切片Mentions 的运行时接缝设计与浏览器验证plate 项目解析【免费下载链接】plateRich-text editor with AI and shadcn/ui项目地址: https://gitcode.com/GitHub_Trending/pl/plate本文基于 docs/plans/2026-04-06-slate-v2-inline-family-migration-tranche.md 展开。该计划面向 Slate v2 引擎仓库原仓库路径/Users/zbeyens/git/slate-v2记录了 inline 元素家族向 v2 原生运行时迁移的第一个诚实切片——Mentions提及。读完后你将掌握为什么 inline 家族迁移要以 mentions 为起点、v2 运行时唯一允许新增的键盘事件接缝runtime seam如何设计、验收与浏览器验证如何闭环以及当前 plate 仓库中对应实现的落点。Slate v2 的引擎重构有一条明确纪律内核保持无聊keep the core boring运行时接缝显式化应用自有的 inline 行为属于应用代码除非一个运行时接缝被证明是必要的。Mentions 切片就是这条纪律的第一个实战样本它不复活旧版withMentions(withReact(...))的插件覆写架构而是用最小的onKeyDown转发接缝在 v2 原生运行时上完整交付渲染 mention 徽章 query 建议 Enter 插入三个核心行为并为后续 links / paste-html 切片划清了边界。切片背景inline 家族迁移的整体约束在 v2 重构中inline 元素mentions、links 等与 void、markableVoid 一起构成了inline 家族。旧版 Slate 通过withMentions(withReact(...))这类高阶插件覆写链把行为塞进引擎v2 明确拒绝把这种覆写架构拖回内核。本切片Stage 1的交付物被严格限定为一个构建在当前 snapshot/runtime 栈之上的 v2 原生 mentions 表面surface一个支撑该表面所必需的、最小化的运行时接缝覆盖渲染 mention 徽章 / 建议弹出 / Enter 插入的浏览器证明browser proof把本切片归类为首个 inline 家族迁移切片的路由图与文档同步。也就是说这一轮只做 mentions不碰完整的旧版 inline 家族。非目标Non-Goals明确本轮不做什么计划文档用四个 Non-Goals 划出边界防止切片膨胀不尝试复刻旧版withMentions(withReact(...))不为isInline/isVoid/markableVoid引入通用插件覆写接缝不在同一切片内做 link 包裹或 paste-html 迁移不为了让 mentions 显得原生而新增引擎操作op家族。从当前 plate 仓库的实现看这一边界体现在 BaseMentionPlugin.ts 中BaseMentionPlugin通过createTSlatePlugin声明node: { isElement: true, isInline: true, isMarkableVoid: true, isVoid: true }以 v2 原生插件声明的形式表达 inline/void 语义而非旧版withMentions式的行为注入BaseMentionInputPlugin则单独声明isInline isVoid的输入态节点。这正是把节点语义声明化、把行为保留在运行时接缝之外的落地形态。设计规则Engine v2 的三条铁律计划文档将设计规则归纳为三点这也是判断某个能力是否应该进引擎的判据keep the core boring内核只承载通用、可预测的机制不为单个应用特性开洞keep runtime seams explicit如果确实需要在运行时加接缝必须显式命名、显式暴露、显式文档化treat app-owned inline behavior as app code unless a runtime seam is clearly justified应用自有的 inline 行为默认归应用侧除非运行时接缝有清晰的正当性。唯一被论证批准的运行时接缝Editable / EditableBlocks 上的 onKeyDown 转发本切片唯一获批的运行时接缝是Editable/EditableBlocks上的键盘事件转发。理由很直白一个真实的 mentions 表面需要显式的键盘所有权监听触发、方向键选择、Enter 确认而当时的 v2 运行时并未暴露键盘事件入口。没有这个接缝应用就无法诚实地接管键盘只能退回覆写架构。切片落地时该接缝以最小形态合入minimalonKeyDownruntime forwarding onEditable/EditableBlocks只做转发、不做策略具体按键如何响应仍由应用侧组合引擎只保证事件能显式到达应用层。这与后续 links-paste-html 切片 的onPaste转发遵循同一模式——每个 inline 表面各带一个明确、最小、文档化的运行时接缝而不是一个万能的事件覆写钩子。验收标准Acceptance四条可核验的条件一个新的 v2 mentions 示例存在并运行于/examples/mentions该示例证明三项行为初始渲染的 mention 徽章、query触发的建议、Enter 插入示例使用当前 v2 运行时栈而非旧版 Slate 插件覆写本次新增的运行时接缝保持最小化且有文档说明相关文档与路线图明确陈述mentions 是首个 inline 家族迁移切片links / paste-html 有意后置。计划文档记录的落地位原仓库路径为site/examples/ts/mentions.tsxv2 原生 mentions 示例playwright/integration/examples/mentions.test.ts专用浏览器证明跨仓库替换矩阵replacement matrix为旧版与现行 mentions 增加对比行。这些路径指向独立的 slate-v2 引擎仓库不在当前 plate 仓库内当前 plate 仓库中与 mentions 表面直接对应的实现位于 packages/mention 与 packages/combobox。浏览器证明的示例清单在 decoration-roadmap.md 中也有交叉引用mentions 示例与 persistent-annotation-anchors、hovering-toolbar 一起被列为已有 package/browser 证明的表面。验证命令Verification切片如何自证计划文档给出的验证清单yarn workspace slate-react run testslate-react 工作区测试yarn tsc:examples示例的 TypeScript 类型检查针对新 mentions 示例的定向 Playwright 测试yarn test:replacement:compat:local当替换矩阵扩张时运行的兼容性测试对受影响的 slate-v2 / plate-2 文档执行格式检查。这些命令面向原 slate-v2 引擎仓库的脚本约定当前 plate 仓库采用 bun/pnpm 工作区见 package.json 与 pnpm-workspace.yaml运行验证时应以各自仓库的脚本为准。落地结果Outcome合入内容与后续边界切片按mentions 优先完成合入项包括Editable/EditableBlocks上的最小onKeyDown运行时转发v2 原生 mentions 示例原仓库site/examples/ts/mentions.tsx专用浏览器证明原仓库playwright/integration/examples/mentions.test.ts为旧版与现行 mentions 加宽了跨仓库替换矩阵行路线图/文档同步将 mentions 归类为首个 inline 家族迁移切片。替换矩阵的语义可参考 replacement-family-ledger.md 的状态分级Preserved保留、Redefined经更窄的现行接缝重定义、Comparison-only仅对比可见、Intentionally Later有意后置。mentions 属于Redefined一类家族行为保留但通过更窄、更干净的现行接缝承载而不是对旧版行为的逐字节复刻。明确后置的工作项linkspaste-html任何通用插件覆写架构。当前 plate 仓库中的 mentions 实现佐证虽然迁移切片落在独立的 slate-v2 引擎仓库但 plate 仓库的 mentions 插件与之一脉相承可作为理解v2 原生 mentions 表面的活样本1. 节点声明与触发器配置BaseMentionPlugin.tsexport const BaseMentionInputPlugin createSlatePlugin({ key: KEYS.mentionInput, node: { isElement: true, isInline: true, isVoid: true }, }); export const BaseMentionPlugin createTSlatePluginMentionConfig({ key: KEYS.mention, node: { isElement: true, isInline: true, isMarkableVoid: true, isVoid: true, }, options: { trigger: , triggerPreviousCharPattern: /^\s?$/, createComboboxInput: (trigger) ({ children: [{ text: }], trigger, type: KEYS.mentionInput, }), }, plugins: [BaseMentionInputPlugin], })关键参数trigger默认triggerPreviousCharPattern为^\s?$即触发器前一个字符必须为空或空白避免在单词中间误触发createComboboxInput负责把输入态节点mentionInput注入文档该输入态节点同时是 inline 与 void。2. 选中建议后的插入行为getMentionOnSelectItem.tstf.insert.mention({ key: item.key, search, value: item.text }); // 将选区移动到元素之后 editor.tf.move({ unit: offset }); const pathAbove editor.api.block()?.[1]; const isBlockEnd editor.selection pathAbove editor.api.isEnd(editor.selection.anchor, pathAbove); if (isBlockEnd insertSpaceAfterMention) { editor.tf.insertText( ); }这里可以看到与Enter 插入直接相关的运行语义插入 mention 节点 → 光标移到元素之后 → 若位于块末尾且开启insertSpaceAfterMention选项则自动补一个空格。选项类型insertSpaceAfterMention?: boolean定义在 MentionConfig 中。3. 建议列表的触发机制由 packages/combobox 的withTriggerCombobox提供BaseMentionPlugin通过.overrideEditor(withTriggerCombobox as any)接入其行为由 withTriggerCombobox.spec.tsx 覆盖。combobox 相关的触发、选择、键盘导航逻辑正是建议弹出 Enter 确认这套交互在 plate 中的实现载体。4. 序列化/反序列化闭环mentions 的 Markdown 往返由 packages/markdown 承担包括remarkMention插件remarkMention.ts与serializeMention.spec.ts测试保证 v2 原生 mention 节点在导出/导入时语义不丢失。小结一个诚实切片的可复用范式回顾整个计划mentions 切片之所以被称为第一个诚实的 inline 家族迁移切片在于它同时守住了三条底线不改内核没有为 mentions 引入新的操作家族或通用覆写机制只批准了一个有明确正当性的onKeyDown转发接缝不拖旧债旧版withMentions覆写链被明确列入 Non-Goals示例必须跑在当前 v2 运行时栈上边界清晰验收、验证、文档三线闭环且 links / paste-html 被显式标注为后续切片其计划见 slate-v2-links-paste-html-tranche。这套单表面 最小接缝 浏览器证明 路线图同步的迁移范式为 inline 家族后续所有切片links、paste-html、乃至更丰富的 HTML 格式化策略提供了可复制的执行模板。【免费下载链接】plateRich-text editor with AI and shadcn/ui项目地址: https://gitcode.com/GitHub_Trending/pl/plate创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表