鸿蒙 PC Markdown 编辑器搜索选项响应式布局:220 vp 侧栏中的完整中文控件

📅 2026/7/23 15:14:35
鸿蒙 PC Markdown 编辑器搜索选项响应式布局:220 vp 侧栏中的完整中文控件
鸿蒙 PC Markdown 编辑器搜索选项响应式布局220 vp 侧栏中的完整中文控件可调侧栏上线后一个之前被固定宽度掩盖的问题立即出现侧栏缩到 220 vp工作区搜索下方“区分大小写、全词匹配、正则表达式”仍强制放在一行最右侧文字被裁掉。功能状态仍在用户却无法完整确认自己勾选的含义。对于搜索这种可能影响全工作区结果的操作标签不可见不是轻微视觉瑕疵而是会造成错误判断的可用性问题。修复已进入公开仓库 https://gitcode.com/VON-/codex_md_oh实现提交为0d8d38b此前可调侧栏基础提交为358eb3f。本文基于真实 ArkUI 代码和 HarmonyOS MateBook Pro 2in1 模拟器证据说明为什么采用 300 vp 稳定断点、窄宽两行与宽度单行的组合怎样保证当前文档搜索和工作区搜索复用同一状态以及怎样用辅助功能边界而不只是截图验证文字完整。问题由容器能力触发而不是由翻译触发英文标签是Case / Whole / Regex默认 264 vp 侧栏中较容易放下中文标签是“区分大小写 / 全词匹配 / 正则表达式”总宽度明显更长。固定侧栏时期部分窗口和字体环境已经接近边界只是没有稳定复现。用户获得自由调整能力后220 vp 最小值使隐藏假设成为确定 bug。不能把原因归咎于中文“太长”。产品既然支持简体中文和 220 vp 侧栏就必须让两个条件同时成立。缩小字号、截断标签或只在英文允许最小宽度都会降低可读性并制造语言不平等。正确方向是让容器根据可用宽度改变排列。响应式修复还要避免另一端浪费。480 vp 宽侧栏若仍固定两行会占用不必要的纵向空间搜索结果列表可见项减少。因此需要明确断点在窄侧栏完整展示在宽侧栏恢复紧凑。三个选项共享的业务状态WorkspaceShell 用三个布尔状态表示搜索约束searchCaseSensitive、searchWholeWord、searchRegularExpression。当前文档搜索和工作区全文搜索复用这组状态快速打开不使用正文匹配选项。布局不应创建第二组窄版状态。StateprivatesearchCaseSensitive:booleanfalse;StateprivatesearchWholeWord:booleanfalse;StateprivatesearchRegularExpression:booleanfalse;privateupdateSearchCaseSensitive(value:boolean):void{this.searchCaseSensitivevalue;this.searchMatchCount0;if(this.searchPanelModeSearchPanelMode.WORKSPACE){this.invalidateWorkspaceSearchResults();}}更新大小写时当前文档匹配计数归零下一次查找按新条件执行工作区模式还会使已有结果失效因为列表基于旧条件。Whole Word 和 Regex 使用同样的更新语义。响应式分支只选择 Builder 排列回调仍指向同一更新函数。这保证侧栏从 299 拖到 300 vp 时Checkbox 可能重新构建布局但业务值不重置已有状态不会悄悄变成 false。布局是视图不是新的搜索会话。为什么选择 300 vp 断点断点不是设备型号也不是随意的“移动端/桌面端”。它直接基于当前控件宽度、14 vp 左右内容 padding、18 vp Checkbox、4 vp Row 间距和中英文最长标签测得。220 至 299 vp 使用两行300 vp 及以上三项能在当前字体下稳定单行。constSEARCH_OPTIONS_SINGLE_ROW_MIN_WIDTH:number300;使用具名常量让意图明确也方便未来资源文案、字体或显示缩放变化时调整。若把300散落在 Builder 分支和测试里后续会出现阈值不一致。名称描述“搜索选项单行最小宽度”而不是笼统BREAKPOINT_SMALL因为它只服务这一局部布局。断点判断使用sidebarWidth不是整个窗口宽度。窗口可以很宽但用户主动把侧栏调到 220仍应两行窗口变窄导致侧栏隐藏时选项不显示无需布局。以真正的父容器宽度为条件是可组合组件的基本原则。窄侧栏的两行结构小于 300 vp 时外层 Column 固定 52 vp 高度两行各 24 vp中间 4 vp。第一行放“区分大小写”和“全词匹配”用 Blank 分隔到两端第二行只放“正则表达式”。if(this.sidebarWidthSEARCH_OPTIONS_SINGLE_ROW_MIN_WIDTH){Column({space:4}){Row(){this.searchOption(search-case,$r(app.string.match_case),this.searchCaseSensitive,(value:boolean)this.updateSearchCaseSensitive(value))Blank()this.searchOption(search-whole,$r(app.string.match_whole_word),this.searchWholeWord,(value:boolean)this.updateSearchWholeWord(value))}.width(100%).height(24)Row(){this.searchOption(search-regex,$r(app.string.use_regular_expression),this.searchRegularExpression,(value:boolean)this.updateSearchRegularExpression(value))}.width(100%).height(24)}.width(100%).height(52)}为什么不是让 Flex 自动 wrap三个选项重要性和长度已知固定分组能保证中文与英文在临界宽度的顺序稳定不会因文本测量细微变化产生一项/两项随机换行。用户建立的肌肉记忆是前两项在第一行、Regex 在第二行。固定高度避免拖过 300 时父布局反复测量造成内容抖动。断点跨越时高度从 52 变为 24这是明确模式变化同一模式内标签和选中状态都不会改变高度。宽侧栏恢复单行紧凑布局达到 300 vp 后三个选项进入同一 Row中间两个 Blank 分配剩余空间。每项保持自身自然宽度不用固定三等分导致中文标签内部空间不足。Row(){this.searchOption(search-case,$r(app.string.match_case),this.searchCaseSensitive,(value:boolean)this.updateSearchCaseSensitive(value))Blank()this.searchOption(search-whole,$r(app.string.match_whole_word),this.searchWholeWord,(value:boolean)this.updateSearchWholeWord(value))Blank()this.searchOption(search-regex,$r(app.string.use_regular_expression),this.searchRegularExpression,(value:boolean)this.updateSearchRegularExpression(value))}.width(100%).height(24)408 vp 模拟器证据中三项文本纵坐标都为 627-651证明恢复同一行。宽度更大时 Blank 吸收额外空间选项不会被拉成巨大的点击卡片也不会聚成难以区分的一团。一行模式减少 28 vp 垂直占用结果列表能显示更多内容。PC 工具界面重视信息密度但密度必须在文字完整之后断点正是两者的转换条件。每个选项的内部尺寸必须稳定searchOption使用 Row左侧 Checkbox 固定 18 × 18 vp右侧 Text 字号 11 且maxLines(1)。文字本身永不在复选框旁折成两行换行责任完全由外层searchOptions承担。BuilderprivatesearchOption(name:string,label:Resource,selected:boolean,action:(value:boolean)void){Row({space:4}){Checkbox({name:name}).select(selected).width(18).height(18).selectedColor(#087A63).onChange(action)Text(label).fontSize(11).fontColor($r(app.color.workspace_text_normal)).maxLines(1)}}如果允许 Text 自己换行中文“区分大小写”可能在 220 vp 被拆成两行但 Row 高度仍是 24文字会裁切或与下一行重叠。maxLines(1)强制暴露空间不足再由容器分组解决职责更清晰。Checkbox 的name稳定且三项不同方便状态识别和自动化。选中颜色保持工作台绿色强调不改变尺寸。点击标签是否能切换取决于 Row/Checkbox 交互范围当前设备路径主要点击复选框后续可将整项变成统一可点击语义以改善命中。不能用缩小字体解决将 11 vp 缩到 9 vp 可能暂时放下中文但会破坏可读性、显示缩放和无障碍也无法保证未来术语不再变长。动态按宽度缩放字体更差侧栏拖动时文字不断变形三个选项字号可能不同PC 工具表面显得不稳定。省略“正则表达式”为“正则”会降低术语精度英文缩写 Regex 尚可但中文产品词典已选定完整表达。图标替代也不合适大小写、全词、正则没有足够普遍且无歧义的单一符号仍需 tooltip 和无障碍文本。两行布局只增加有限高度却保留完整文案和字号是当前最低复杂度且最稳健的方案。宽侧栏自动回到单行不让常用桌面尺寸长期承担额外高度。不能用水平滚动掩盖选项把选项 Row 改成横向 Scroll 会保留文字但用户需要滚动才能发现最右侧 Regex当前设置状态不再一眼可见。搜索条件属于执行前必须确认的信息不应藏在无滚动条的横向轨道里。水平滚动还会与侧栏整体滚动、触控板手势和拖动分隔线产生交互竞争。三项只有固定少量换一行比引入新的滚动容器更直接。PC 操作面板应优先让关键开关同时可见。同样不应把第三项移到更多菜单。Regex 是专业 Markdown 编辑器高频能力菜单会增加点击路径也让当前是否启用难以持续感知。响应式排列保留了完整功能显性。搜索模式切换与结果失效搜索面板有当前文档、工作区和快速打开三种模式。Current 和 Workspace 使用三个选项Quick Open 按文件名模糊排序不显示或不应用正文匹配语义。模式切换会取消旧任务、清理结果、重置选中索引和匹配计数。privatesetSearchPanelMode(mode:SearchPanelMode):void{if(this.searchPanelMode!mode){this.workspaceSearchRequestSequence1;this.workspaceSearchController.cancel();this.workspaceSearchRunningfalse;this.workspaceSearchResults[];this.workspaceSearchSelectedIndex0;this.searchMatchCount0;}this.searchPanelModemode;}响应式布局不参与取消逻辑。侧栏宽度改变不会把正在进行的工作区 TaskPool 搜索当作新查询也不会重置选项。用户可在搜索后拖宽阅读结果结果列表继续存在只有选项值真正变化时才 invalidation。这一区分避免把视觉断点误当业务断点。否则每次拖过 300 都取消搜索用户会认为侧栏调节导致数据丢失。中英文资源让断点接受双重压力三个标签来自$r(app.string.match_case)、match_whole_word、use_regular_expression。base 分别为Case、Whole、Regexzh_CN 为完整中文。布局组件不判断语言只判断实际容器宽度。当前断点按更长中文设计所以英文在 220 vp 也使用两行虽然理论上可能放下一行。这种一致性避免切换语言时布局模式突然变化也简化测试。若未来希望英文利用更紧凑宽度应使用实际测量而不是语言 if但复杂度是否值得需要产品数据。增加德语等更长语言时300 vp 可能不够。资源扩展必须重新测试最窄和断点边界必要时把断点提高或改为更稳健的测量布局。当前只支持中英文不能把现有值宣传为所有语言通用。真实模拟器截图与边界数据下面截图来自 MateBook Pro 2in1 模拟器侧栏固定到最小 220 vp。前两项位于第一行“正则表达式”位于第二行三个中文标签都完整可读没有与分隔线或编辑器重叠。辅助功能树给出精确边界区分大小写[706,627][811,651]全词匹配[926,627][1010,651]正则表达式[706,680][811,704]。第三项纵坐标明显在第二行且右边界完整位于侧栏内。把侧栏扩大到 408 vp 后三项纵坐标均为 627-651证明布局恢复单行。相比仅凭截图“看起来没截断”边界数据能验证文本节点完整存在且模式按断点切换。可调侧栏和窗口变化的联合测试用户可以用鼠标连续拖动也可以方向键每次调整 16 vp。测试需要检查 299 与 300 的临界点避免因为浮点尺寸或 areaChange 在阈值附近反复切换。当前状态使用 number vp 和 300判断300 精确进入单行。窗口缩小时动态 clamp 可能收紧侧栏小于 900 vp 则侧栏整体隐藏。重新展开后使用当前有效宽度选择布局。Preferences 保存的是钳制后的有限数值重启 220 或 392 都能恢复对应模式。拖动过程中跨过断点会发生一次高度变化下面的结果列表起点随之移动。这是明确的响应式变化不是重载。搜索状态和 Web 编辑器不受影响。后续可评估轻微过渡但操作型工具优先保证即时、稳定避免动画延迟命中。自动化、构建与设备结果最终验证包括 Playwright30/30、Web TypeScript 与离线单 HTML 构建、Debug HAP、ArkTSUnitTestBuild、ohosTest HAP、MateBook Pro 2in1 模拟器 ohosTest7/7、中英文资源键集合一致和git diff --check。最终 Debug HAP 为 1,520,352 字节SHA-256367ab8650479aa1fa8fe73bd1ebadd9a53f46659c850c2e388fc799d5cb88e5bohosTest HAP 为 2,360,824 字节SHA-256b7230037b51044fe16168d2c835fb891e1c70f675941a1046165bc895217592c。两份都是未签名测试产物。Playwright 主要保护 Web 搜索和命令回归ArkTS 构建保护 Builder 类型模拟器边界数据证明原生布局。当前尚未增加专门的 ArkUI 自动测试在 299/300 自动截图这是后续质量增强点本轮已有真实 220 与 408 设备证据。性能、焦点和无障碍布局分支只依赖sidebarWidth拖动每帧会重新评估并在跨过 300 时切换结构。三个小控件的重建成本固定不读取文件、不触发搜索。大工作区 TaskPool 和 CodeMirror 文档不参与这次布局。Checkbox 状态来自外部 State重建不会丢选中。Text 完整进入辅助功能树验证中三个标签都可读。当前应继续增强整行点击和明确的 checked 朗读测试确保不同输入方式一致。焦点位于某个 Checkbox 时跨断点重建可能影响焦点连续性现有设备测试未记录这一极端路径。用户通常在拖动分隔线时焦点位于调整柄但键盘用户可能先勾选再调整后续应把它纳入无障碍回归。文章不把未测焦点保持写成已完成。已知限制与演进300 vp 是当前中英文、当前字体和布局 padding 下的稳定断点不是永恒常量。系统大字体、更多语言或新选项可能要求三行、网格或可折叠高级选项。新增搜索条件时不能继续塞进现有 Row。当前窄模式第二行只有一个选项视觉上左对齐。未来第四项可与 Regex 配对但需要按语义组织不应只追求对称。高级搜索若增加 glob、排除目录等输入更适合独立区域而不是复选框平铺。搜索选项还未持久化切换应用重启会回到 false这是当前产品选择避免用户忘记 Regex 打开导致下次搜索异常。若未来持久化应提供明显状态和恢复默认不应复用侧栏宽度的持久化假设。结论0d8d38b解决的不是一个中文标签裁切而是可调容器中的响应式语义小于 300 vp 用稳定两行保留完整文字达到 300 vp 恢复单行密度三个 Checkbox 始终复用同一搜索状态和更新函数。220 与 408 vp 的真实模拟器边界证明两个模式都按预期工作。对鸿蒙 PC Markdown 编辑器而言自由调整工作空间必须与本地化、焦点、搜索状态和结果列表一起验收。容器能缩放只是第一步内部每个高价值控制项都要在最小尺寸仍可读、可点、可解释这才算真正完成 PC 适配。