Uninote
Uninote
用户根目录
brdr
common
programming
docs
tests
后端试题
问题讨论

功能说明

本文档按使用场景整理 Markdown Editor 当前已经支持的功能。

  • 界面中带说明的控件显示统一样式的 tooltip:
    • 鼠标悬停 300ms 后显示,通过键盘聚焦时立即显示。
    • 提示会自动避开窗口边缘。
    • 快捷键提示按当前平台显示实际修饰键:macOS 显示 Command/Cmd,Windows 和 Linux 显示 Control/Ctrl,不使用跨平台占位写法。
  • 所有按钮文案保持单行显示,不因按钮所在区域变窄而在文字中间换行。
  • 表单中的单行输入和下拉选项默认采用同一行左标签、右控件的紧凑布局。
    • 数字输入保持较窄宽度,文本输入随可用空间伸缩;设置、快捷键、语音与片段配置沿用相同规则。
    • 多行输入保留标签在上方的布局,帮助说明独立显示在字段或分组下方。

1. 菜单索引

  • 从“帮助 → 菜单索引”打开类似文件查找结果的只读标签页,无需先打开笔记库。
  • 命令面板支持搜索“菜单索引”或 help.menuIndex 执行同一操作;默认不绑定快捷键,可在快捷键设置中自行配置。
  • 按当前应用主菜单的顺序列出所有可见菜单及中文功能说明,每级使用两个空格缩进。
    • 当前笔记及仓库批量导出的 PDF、Word 菜单项分别说明导出范围和格式,不使用快捷键设置提示代替功能说明。
  • 包含系统菜单和“打开最近”入口;过滤该入口下的最近打开列表及空列表提示,隐藏项与分隔线也不列出。
  • 禁用菜单保留在索引中并标记“不可用”;勾选项标记当前勾选状态。
  • 再次点击会刷新并复用同一个索引标签页,反映最新菜单及快捷键标签。
  • 快捷键按当前平台合并默认规则与用户配置后输出,包含自定义快捷键、多段组合键及同一命令的多组绑定,并去除重复项。
    • 已被用户删除或在当前平台禁用的绑定不显示,不回退到旧的默认快捷键。
    • 原生菜单独立处理的快捷键按实际菜单绑定显示;macOS 使用 Cmd,Windows/Linux 使用 Ctrl。
  • 索引内容可以选择、复制和使用当前页面查找;不会保存为笔记,也不参与仓库搜索替换。

2. 命令面板

  • 默认命令
  • 使用 Ctrl+Shift+P(macOS 为 Cmd+Shift+P)、F1 或工具栏“命令”按钮打开。
  • 复用 Quick Open 的匹配算法,支持中文原文、无声调全拼、拼音首字母和命令 ID 搜索。
  • 搜索支持空格分隔多个关键词和可选的 > 前缀。
  • 使用上下方向键循环选择,按 Enter 执行;也可以点击命令执行。
  • 点击命令或按 Enter 执行时保存非空查询;最近 50 条去重保存在本机 Local Storage。
  • 历史上一条和下一条默认使用当前平台的 Ctrl 或 Cmd + ↑↓,可在快捷键设置中分别修改。
  • 输入框提示当前历史快捷键绑定,并可返回未提交的输入。
  • 按 Esc 或点击面板外部关闭后,恢复原先 CodeMirror 编辑器或普通 input/textarea 的焦点、光标位置和选区方向。
  • 鼠标点击“命令”按钮也保留原先的输入焦点;中文输入法确认不会执行命令。
  • 执行命令前先恢复原先的焦点和选区,让命令使用原来的输入位置;命令自身仍可按其功能转移焦点。
  • 显示注册命令,包括未分配快捷键的命令和已加载插件命令;不可用命令以较灰的颜色显示,选择时在面板底部提示原因。底部“隐藏不可用命令”复选框默认关闭,勾选后只显示当前上下文可用的命令。
  • 不显示仅适用于系统全局热键或按住 Ctrl 切换标签的命令。
  • 显示当前平台和用户配置的快捷键;当前不可用的命令仍显示已配置的快捷键,便于查看和进入快捷键设置。
  • 命令可用条件独立于快捷键绑定。
  • 每个命令最右侧提供设置图标;点击图标或按 Ctrl+Enter(macOS 为 Cmd+Enter)后打开快捷键设置,并筛选定位到当前命令的全部绑定。
  • 命令面板从 AppData 恢复已记录的命令历史,重启后仍优先显示历史命令;所有历史命令按最近执行顺序排列,忽略工具条中的固定状态。
  • 历史记录与命令历史工具条共享,并同步到已打开的其他窗口。
    • 工具条的固定排列不影响命令面板的历史排序。
    • 隐藏工具条不影响面板恢复历史。
    • 搜索结果仍以匹配程度排序。
  • 命令面板模块在首次打开时加载;执行失败通过应用通知反馈。
  • 执行所选命令时直接检查注册状态和当前上下文,不受搜索结果数量上限影响。

2.1 命令历史工具条

  • 从命令面板执行命令时,按命令 ID 记录历史;再次执行同一命令会将其移到最前,不产生重复记录。菜单、普通快捷键和工具条重执行不增加历史。
  • 历史、固定状态、自定义 emoji 和工具条显隐状态保存在应用 AppData 目录的 command-history-v1.json,并同步到已打开的其他窗口。
  • 固定记录排在左侧,且只在固定区与普通历史之间显示分隔线;普通记录保留最近 50 条。命令卸载或当前不可用时记录仍保留,工具条显示不可用原因。
  • 每个命令自动显示不同的默认 emoji;工具条中的「⋯」按钮可改为单个自定义 emoji,留空保存即可恢复默认图标。
  • 每条历史记录的 PIN 和 emoji 按钮浮在命令按钮下方,仅在鼠标悬停或键盘聚焦该记录时显示;鼠标移向下方按钮时保持显示,不改变主工具条高度。
  • 工具条默认固定在窗口顶部正中,始终显示且不随鼠标移动;可拖动把手调整位置。关闭按钮旁的 PIN 按钮可取消固定。
  • 取消固定后,鼠标移出工具条上下各一个工具条高度后隐藏;停止一秒后在鼠标上方居中出现。悬停工具条时保持可操作,靠近窗口上缘时在鼠标下方显示。
  • 点击关闭按钮后保持隐藏,并在需要手动确认的对话框中提示“主菜单 View → 显示命令历史工具条”的恢复方式。勾选“不再提示”并确认后,本应用以后不再显示这条提示;也可从命令面板执行“显示命令历史工具条”恢复。
  • View 菜单的“显示命令历史工具条”以勾选标记显示当前显隐状态,点击可切换状态;工具条关闭按钮和命令面板恢复操作会同步更新菜单标记。
  • 按 Alt+Shift+H,再按 1–9,执行工具条从左到右对应的前九条记录;固定记录也计入序号。

3. 鼠标微调

  • View 菜单的“片段管理器”下方提供“鼠标左右微调”和“鼠标上下微调”,命令面板也可搜索并执行。
  • 默认全局热键:左右微调 Ctrl+Alt+H,上下微调 Ctrl+Alt+V,在其他应用中也可触发。
    • 可在“设置 → 快捷键 → 热键”修改或删除,受热键总开关控制。
    • 菜单和命令面板命令也可单独配置应用内快捷键。
  • 触发时先读取系统光标;已经是对应方向的双向调整大小形状时保持原位。
  • 默认每步移动 3 像素,并等待 50ms 后检查光标形状;遇到对应形状或该方向配置的额外 handle 即停止搜索。
    • 左右微调先向左搜索,再向右搜索;上下微调先向上搜索,再向下搜索,每侧默认最多 10 步。
    • 第一侧未命中时先回到原位,再搜索另一侧。
    • 命中后停在目标位置;两侧搜索完毕仍未命中或中途出错时,尝试把鼠标恢复到最初位置,恢复失败会报错。
    • 搜索期间重复触发会被忽略,不并行移动鼠标;不模拟按下鼠标按钮。
  • 支持 Windows、macOS 和 Linux X11,识别系统标准调整大小光标。
    • Windows 使用系统光标句柄,macOS 比较系统光标图像,Linux X11 使用标准 Xcursor 名称。
    • 在本应用的前台窗口内,也读取鼠标所指元素的实际 CSS 光标,兼容 Chromium 的 col-resize / row-resize 分隔条光标和页面缩放。
    • 自定义图像或未命名光标可能无法识别;macOS 无法读取全局光标时会报错并停止。
    • macOS 需在“系统设置 → 隐私与安全性 → 辅助功能”授权应用发送鼠标事件。
    • Linux 需要 X11 和 XFixes 2.0 或更新版本;Wayland 暂不支持,触发时提示切换到 X11。
  • 原生接口按需加载;菜单和命令面板执行错误通过应用通知反馈,全局热键执行错误写入应用日志。
  • 每次触发微调时仅输出一次 [mynote:mouse-adjust] 初始位置鼠标形状 日志,包括方向、初始坐标、系统光标名称或描述、原生标识、应用内 CSS 光标及初始位置是否命中。
    • 移动后及回到初始位置后的检查不记录;日志同时输出到控制台和应用统一日志文件。

3.1 第二种方案:按住修饰键锁定

  • 当前先支持 Windows;按住 Ctrl+Alt 时开始监听全局鼠标移动,即使本应用没有焦点也生效。
  • 鼠标命中系统标准左右或上下调整大小光标,或任一方向配置的额外 handle 时,锁定当前位置;本应用的 CSS 分隔条光标也参与识别。
    • 每次按住 Ctrl+Alt 时读取水平、垂直 handle 的配置快照;保存修改后,下次按住即使用新值。
    • 复用第一种方案的分号列表、十六进制规范化及 64 位精确匹配规则。
  • 锁定后即使光标形状改变也保持位置,直到松开 Ctrl 或 Alt;退出应用或发生监听错误也解除锁定。
  • 使用 Koffi 调用 GetAsyncKeyState 检查修饰键,按住期间安装 WH_MOUSE_LL 全局鼠标钩子。
    • 每 10ms 复查按键和光标,处理鼠标事件之后才发生的光标变化,以及没有鼠标移动时的按键释放。
    • 命中时通过 ClipCursor 将鼠标限制在一个像素的位置,解除时恢复原先的活动范围。
    • 单元测试覆盖两轴命中、松键、异步读取、移动、退出及错误清理;Windows 原生冒烟测试验证全局修饰键和锁定/解除,光标命中条件在该后台用例中注入。
    • 第二种方案独立于第一种方案的搜索命令及全局热键开关,不模拟鼠标按键或拖动。

3.2 配置

  • 在“设置 → 鼠标微调”保存以下选项,菜单、命令面板和全局热键共用。
    • 步长(mouseAdjustStepPixels):每一步移动的像素值,默认 3。
    • 每侧搜索步数(mouseAdjustSteps):每个方向最多搜索多少步,默认 10,两侧合计最多 20 个搜索步。
    • 水平额外停止 handle(mouseAdjustHorizontalHandles):用于左右微调,也参与第二种方案的锁定判断。
    • 垂直额外停止 handle(mouseAdjustVerticalHandles):用于上下微调,也参与第二种方案的锁定判断。
  • 默认步长仅用于未配置或无效配置;已保存的自定义步长保持不变。
  • 步长和步数均接受 1–1000 的整数;换侧及结束时恢复原位不计入搜索步数。
  • handle 以分号分隔,留空不添加额外停止条件。
    • 可复制初始形状日志中的 cursorHandle,支持十进制或 0x 十六进制,例如 77;0x58。
    • 保存时将有效值转换为十进制、去重;使用 BigInt 避免 64 位标识精度丢失。
    • 配置的 handle 与原生 cursorHandle 精确匹配,匹配即停止搜索;预定光标及应用内 CSS 判断仍然保留。
    • handle 是平台原生标识,可能随应用或系统重启变化;Linux 对应 XFixes 光标序列标识,应以当前日志为准。
  • 选项保存在本机 workspace-state.json 的 settings 中,不加入云端偏好同步。
    • 保存后下一次触发即生效,不必再次重启;运行中的搜索使用触发时的参数快照。
    • 无效输入阻止保存;从磁盘读取到无效值时,该字段回退默认值。

3.3 实现原理

入口与共享执行逻辑

  • 核心实现位于 src/main/mouse-adjust.ts,由主进程创建一个共享的 createMouseAdjuster 实例。
  • 菜单和命令面板使用 mouse.adjustHorizontal / mouse.adjustVertical 命令。
    • 菜单通过现有应用命令通道交给渲染进程执行。
    • 渲染进程调用 preload 暴露的 adjustMouse(axis),经 mouse:adjust IPC 请求进入主进程。
  • 全局热键使用独立的 mouse.adjustHorizontalGlobal / mouse.adjustVerticalGlobal 命令。
    • 复用现有快捷键配置解析和 Electron globalShortcut 注册机制,直接调用同一个微调实例。
    • 全局热键命令不出现在命令面板中,避免与普通命令重复显示或重复触发。
  • axis 只接受 horizontal 或 vertical;共享的 running 标记防止多个入口同时操作鼠标。
    • 已有搜索运行时直接返回 { busy: true }。
    • 结束或出错时在 finally 中清理资源并释放标记,后续触发可继续执行。
  • 每次触发通过 getSettings 从共享设置存储读取并校验参数,以快照形式用于此次搜索。

系统光标与应用内光标识别

  • 使用已安装的 Koffi 按需调用各平台原生接口,不通过截屏或图像识别模型判断形状。
  • Windows:
    • GetCursorInfo 读取全局光标句柄、可见状态和屏幕坐标。
    • LoadCursorW 加载 IDC_SIZEWE(32644)或 IDC_SIZENS(32645);光标可见且句柄相同即命中。
    • SetCursorPos 执行鼠标移动;常见标准光标句柄同时映射为日志中的形状名称。
  • macOS:
    • 经 Objective-C 接口取得 NSCursor.currentSystemCursor,读取当前光标图像。
    • 使用 CFEqual 比较当前光标与 resizeLeftRightCursor / resizeUpDownCursor 的 TIFF 数据,避免仅按对象身份比较。
    • CGEventGetLocation 读取坐标;创建并发布鼠标移动事件,让悬停应用更新光标。
    • 执行前检查发送事件的权限;创建的 CoreGraphics 事件在使用后释放。
  • Linux X11:
    • 连接 X11 显示服务并检查 XFixes 版本,通过 XFixesGetCursorImage 读取位置和光标名称。
    • 将光标名称与对应方向的标准名称、别名比较,例如 col-resize / sb_h_double_arrow 和 row-resize / sb_v_double_arrow。
    • 使用 XWarpPointer 移动,再用 XFlush 提交;读取的光标数据及时释放,搜索结束关闭连接。
  • 原生预定光标和当前方向额外 handle 均未命中时,createAppCursorMatcher 补充检查本应用当前聚焦且可见的窗口。
    • Windows 屏幕坐标先转换为 DIP,再减去内容区域的位置,并除以页面缩放倍率,得到 DOM 坐标。
    • 使用 document.elementFromPoint 找到悬停元素,再读取 getComputedStyle(element).cursor。
    • 左右方向接受 col-resize、ew-resize、e-resize、w-resize;上下方向接受 row-resize、ns-resize、n-resize、s-resize。
    • 这是针对 Chromium 自带分隔条光标的补充;其他应用仍依赖原生识别,不读取其 DOM。

搜索循环与停止条件

  • 首次读取保存原始位置,并判断该位置是否已命中;已命中则不移动。
  • 未命中时先按负方向搜索,左右对应向左,上下对应向上。
    • 第 step 步的目标坐标为原始坐标加上 direction × step × mouseAdjustStepPixels,另一轴保持原值。
    • 每步移动后等待 50ms,再读取实际位置和形状,为目标应用处理悬停事件留出时间。
  • 负方向完成配置的每侧步数仍未命中时,回到原始位置,等待并再次检查,然后按正方向搜索同样的步数。
    • 两侧目标坐标都以原始位置计算,避免第一轮偏移累计到第二轮。
    • 恢复原位也会检查,若此时命中则直接停止。
  • 任意检查命中返回 { found: true };两侧完成仍未命中返回 { found: false }。
    • 已经尝试移动且未命中目标时,在 finally 中恢复起点,并等待 50ms 让异步鼠标事件生效;命中则保留当前位置,随后释放资源和运行标记。
    • 初始位置已经命中时不移动;搜索中读取失败也会执行原位恢复。
  • 搜索只移动鼠标并寻找可调整的位置,不按下鼠标按钮,也不执行拖动或改变控件尺寸。

初始日志与验证

  • 成功完成初始读取后、决定是否移动前,只记录一次初始位置日志。
    • 字段为 axis、x、y、cursorShape、cursorHandle、cssCursor、matches。
    • cursorShape 是原生名称或描述;无法命名时保留原生标识供排查,CSS 补充结果单独放在 cssCursor。
    • 原生检查或额外 handle 已经命中时不再查询 CSS,因此 cssCursor 可能为空。
    • 移动后继续读取并判断形状,但不输出形状日志;被忽略的重复触发或初始读取失败也不产生初始形状日志。
  • console.log 复用主进程已有的控制台镜像机制,写入应用统一日志。
  • test/mouse-adjust.test.ts 验证搜索顺序、命中后的目标位置保留、未命中及异常后的原位恢复、可配置步长与步数、分轴 handle 匹配、并发保护、入口配置、坐标转换及一次初始日志。
  • test/mouse-adjust-smoke.ts 在 Windows 上验证真实 col-resize / row-resize 悬停光标和停止行为。
    • 可运行 node scripts/run.mts node --test test/mouse-adjust.test.js 和 node scripts/run.mts node scripts/smoke.js --run mouse-adjust test/mouse-adjust-smoke.js。
    • Windows 已通过原生冒烟验证;macOS 和 Linux X11 的原生路径仍需对应平台实机验证。

4. 片段管理器

4.1 入口

  • 从 View 菜单或命令面板打开独立片段窗口。
  • 默认系统级热键为 Ctrl+Alt+N,可在“设置 → 快捷键 → 热键”修改。
  • 从 File 菜单或命令面板执行“将当前项目作为片段管理器的数据源”。
    • 首次以仓库名在应用数据目录的 snippet-projects 下建立 .cfg 集合,递归读取其中的 Markdown 文件。
    • 再次执行时复用该集合。同名文件已存在时追加短哈希以避免覆盖;旧版哈希命名的集合继续复用原文件。
    • 集合以项目名称显示、移到首位并选中,片段窗口打开后保持置顶。

4.2 窗口管理

  • 关闭窗口时隐藏,并让系统焦点回到先前窗口;重新打开后继续使用。
  • 按 Esc 隐藏片段窗口;编辑集合配置时,Esc 只关闭配置对话框。
  • macOS 隐藏片段窗口时直接隐藏,避免异步最小化动画重新显示窗口。
  • “窗口 → 切换窗口”和命令面板中的“切换窗口”只在笔记主窗口之间轮换,不切换到片段窗口。
  • 可从“窗口 → 设为主窗口”或命令面板固定系统级窗口切换命令的目标;未设置时仍以最近聚焦的笔记窗口为目标,固定窗口关闭后恢复此默认算法。
  • macOS 的原生 Window 菜单也不显示片段窗口。
  • 首次加载集合和刷新片段结果时显示加载动画;读取完成或失败后自动隐藏,切换到已缓存集合时直接显示结果。
  • 查询尚未完成时不显示“没有匹配的片段”;仅在查询完成且结果为空时显示。

4.3 集合操作

  • 集合管理:
    • “新建”和“打开”共用的对话框起始路径可在“编辑配置”中填写现有文件夹的绝对路径,设置保存在 snippets.json。
    • 起始路径可留空;留空或配置的目录后来不可用时,不指定对话框起始路径,由系统决定打开位置。
    • 没有打开集合时,“编辑配置”仍可修改全局选项。
    • “打开”可一次选择多个现有 .cfg 文件并加入标签页,不复制配置文件。可切换或关闭集合,并在窗口中编辑配置、刷新结果。
    • 编辑期间配置被外部修改时,保存会提示冲突。
  • 片段窗口中按 F5 刷新当前集合;按 Ctrl+N、Ctrl+O、Ctrl+E 分别新建集合、打开集合、编辑当前配置,macOS 使用 Cmd 代替 Ctrl。

4.4 Tab 管理

  • 每个集合占用与主窗口一致的标签;切换标签时保留各自的查询条件、结果、选中项和滚动位置,刷新只更新当前集合。
  • 拖动集合标签可调整顺序,拖到目标标签左半边或右半边分别插入其前方或后方;拖到标签栏空白处移到末尾。
    • 拖动时显示插入位置;关闭按钮只用于点击,不启动拖动。
    • 排序立即保存在 snippets.json,重启后恢复;当前集合、查询、结果选中项和滚动位置保持不变。
  • 按 Ctrl/Cmd+PageUp、Ctrl/Cmd+PageDown 按 Tab 顺序切换集合。
  • 按 Ctrl/Cmd+Tab(Shift 反向)从最近使用的集合中选择。列表打开时,↑、↓ 继续选择且不会导航搜索历史,松开修饰键切换。
  • 按 Ctrl/Cmd+W 关闭当前集合。
  • 右键集合 Tab 可关闭当前、其他、左侧、右侧或全部集合,也可在文件管理器中显示对应 .cfg 文件。
  • 默认快捷键 Shift+Alt+R 显示当前集合。菜单打开时显示菜单所指集合,按键提示随快捷键设置更新。
  • 已打开集合和当前集合保存在应用数据目录的 snippets.json 中,不随笔记库切换。

4.5 数据源与刷新

  • 监测已加载集合的配置文件和来源文件或文件夹;有变化时标记集合待更新,下次刷新或修改查询条件时先重读集合再查询。
  • .cfg 可用 relay:=其他集合.cfg 引用另一个 Tab 当前查询的全部命中项。
    • 路径可相对当前配置文件或为绝对路径,并可与普通来源混用。
    • 未打开的上游集合会在后台打开,不切换当前 Tab。
    • 按配置顺序合并后,以来源路径和行号去重,再执行当前查询。
    • 上游查询或文件变化后,下游在下次查询或切回 Tab 时更新。
    • 上游配置若仍含 relay:=,该引用显示诊断且不递归。
  • .cfg 每行指定一个文件、目录或文件名通配符;目录及通配符递归读取,相对路径以配置文件所在目录为基准。空行和 # 注释行跳过。
  • .cfg、.cfg.ignore 和片段来源文件先按 BOM 识别 UTF-8、UTF-16 LE/BE;无 BOM 时优先严格按 UTF-8 解码,失败则按 GBK 解码。
  • 每个非空文本行形成一条片段,保留来源路径和原文件行号;首个不以 @@ 开头的内容行在展示及复制时加上 @@ 。

4.6 配置

  • 配置编辑器:
    • 在数据源下方单独显示文件过滤配置。
    • 两个文本框最小显示 6 行,对话框高度随内容自动调整并受窗口高度限制。
    • 文本框支持系统标准的剪切、复制、粘贴、撤销和重做快捷键。
    • 数据源保存到 .cfg,文件过滤配置独立保存到同名 .cfg.ignore;过滤区的注释和空行不会混入数据源。
    • .cfg.ignore 每行可用 ignore:=过滤文件路径 引用一个或多个过滤文件,相对路径以 .cfg 所在目录为基准。
    • 过滤文件沿用 .mynoteignore 的 Gitignore 语义,命中的文件和目录不加载。
    • 将仓库作为数据源时,新建的集合默认引用仓库根目录的 .mynoteignore。
  • 编辑器保存配置时写入 UTF-8。
  • 单个来源文件大小上限默认 2 MiB,片段结果上限默认 20000 条。
    • 两者都可在“编辑配置”中调整,适用于所有集合。
    • 读取错误、超限及不支持的配置行显示在诊断区。
    • 点击任一上限提示可直接打开配置界面并聚焦对应字段,保存后刷新当前集合。

4.7 搜索

  • 按片段文本和来源路径搜索,复用 Quick Open 的子串、跳字模糊、多关键词、无声调拼音全拼与首字母匹配及排序;拼音匹配遵循应用的全局开关。
  • 在片段窗口按 Ctrl+F(macOS 为 Cmd+F)聚焦搜索框。
  • 片段文本和来源路径中的命中字符复用 Quick Open 的高亮规则;拼音全拼、首字母、跳字模糊及 f:、p: 筛选命中也会高亮对应原文。
  • 成功使用片段时保存非空搜索词,最近 50 条去重历史保存在本机 Local Storage。
    • 搜索框用面板历史快捷键回看查询,默认 Ctrl+↑/↓(macOS 为 Cmd+↑/↓),并跟随快捷键设置更新。
  • 搜索框旁的“拼音”按钮可切换全局拼音搜索并立即更新结果;在“设置 → 快捷键”中为“切换拼音搜索”设置的快捷键也可在片段搜索框内使用,改动即时生效。
  • 使用 f: 限定片段文本、p: 限定来源路径。空查询保留来源顺序;显示匹配总数,列表展示前 500 条结果。
    • 空格表示“与”,非引用的 | 表示“或”,无需在竖线两侧加空格。
    • 苹果 红色|香蕉 黄色 表示满足任意一组,组内关键词必须全部满足。
    • p:、f: 是独立于分组的全局条件,多个字段条件必须全部满足,无论写在哪一组。
    • p:资料 苹果|香蕉 f:成熟 表示来源包含“资料”、正文包含“成熟”,并匹配“苹果”或“香蕉”。
    • s: 限定片段正文的开头,全局作用于所有或分组;多个 s: 以及其他字段条件必须全部满足。
      • 红色|黄色 s:苹果 只匹配以“苹果”开头且匹配“红色”或“黄色”的片段。
      • 前缀匹配不区分大小写,不使用拼音或跳字匹配,命中的前缀会高亮。
      • 支持引号中的空格和竖线,例如 s:"a | b";未闭合引号沿用字段规则,空值沿用普通关键词处理。
      • 对加载后的片段正文判断前缀,包含已有的 @@ 标记;例如标题可用 s:@@ 筛选。
    • 字面竖线使用字段引用,例如 f:"a|b" 或 p:"a|b";未闭合的字段引号将剩余输入作为字段内容。
    • 空分组被忽略,苹果|、|苹果、苹果||香蕉 均可搜索;仅有分隔符时返回零条,仅有字段条件时按字段筛选。
    • 同一片段命中多组只显示一次,取最高组分数排序,同分保留来源顺序;高亮全局字段和完整命中组中的字符。
    • 搜索总数、集合接力和导出沿用相同匹配结果;历史查询中的非引用竖线也采用新语义。
    • 本次未增加 e:、括号或否定语法;其他窗口的搜索规则不变。

4.8 片段调用与导出

  • “查询结果另存为”将当前查询命中的全部片段正文按结果顺序保存。
    • 默认文件名为 查询结果.md,也可在系统对话框中指定其他文件名或扩展名。
    • 没有查询结果时不可用。
  • “ctrl for paste”默认勾选,选择保存在本机。勾选时,双击、按 Enter 或按 Alt+数字键打开来源,按住 Ctrl 则粘贴;取消勾选时,普通操作粘贴,按住 Ctrl 则打开来源。
  • 粘贴会把片段写入剪贴板、隐藏片段窗口,并向之前使用的外部应用发送 Ctrl+V(macOS 为 Cmd+V);不会拉起笔记编辑窗口。
    • Windows 会记住片段窗口打开或失焦时的外部窗口,未找到外部窗口时提示先切换到目标应用。
  • Alt+1–Alt+9、Alt+0 分别执行当前结果前十项的双击动作,也受“ctrl for paste”和 Ctrl 修饰键控制;单独输入数字可继续搜索。
  • 跨应用粘贴在 macOS 需要授权系统辅助功能;Linux X11 需要 xdotool,Wayland 需要已运行的 ydotool 服务。系统工具不可用时显示错误并重新打开片段窗口。
  • 行内“插入”按钮执行同样的跨应用粘贴,不要求当前笔记可编辑。
  • “打开来源”将 Markdown 文件在应用内打开并跳转到对应行,其他文件交由系统默认程序打开;包含 HTTP/HTTPS 网址的片段还可选择“打开链接”。

4.9 未迁移功能

  • 当前不支持 filter_path=:、sql_ 配置行、tnd、SQLite 和 .zrtf 内部跳转。

5. 文档与标签管理

5.1 新建、打开与保存

  • 新建 Markdown 文档,并自动填充欢迎内容。
  • 通过文件选择器一次打开一个或多个 Markdown 文件。
  • 再次打开已经位于标签页中的文件时,直接切换到对应标签,不创建重复标签。
  • 保存当前文档。
  • 新建文档首次保存时,可以选择文件名和位置;保存到当前笔记库后会立即加入目录树管理和大纲索引,无需重开笔记库。
  • 使用“另存为”按钮将当前内容保存到新文件。
  • “另存为”也可从 File 菜单执行,默认快捷键为 Ctrl/Cmd+Shift+S。
  • 打开、保存、另存为和图片选择对话框绑定当前窗口显示,不会被主窗口遮挡。

手动导出 PDF 与 Word

  • File 菜单提供“当前笔记导出 PDF…”、“当前笔记导出 Word…”、“批量导出仓库 PDF…”和“批量导出仓库 Word…”。
    • 四个命令均可在快捷键设置中绑定按键,默认不占用快捷键。
    • 仅手动触发,不依赖 .mynote/config,也不跟随保存自动生成。
  • 当前笔记按点击导出时的编辑内容生成文件,包含尚未保存的修改。
    • 未命名笔记也可导出;不会保存源文件、修改标签页内容或清除未保存状态。
    • 在保存文件对话框中选择输出位置,默认使用笔记名称及 .pdf 或 .docx 后缀。
  • 批量导出会重新扫描当前仓库,沿用仓库忽略规则,并固定本次仓库及 Markdown 文件列表。
    • 仅导出磁盘内容,不包含编辑器中尚未保存的修改。
    • 选择输出目录后,在其中创建唯一的 mynote-pdf-… 或 mynote-docx-… 子目录。
    • 每篇生成独立文件,保留仓库子目录结构;同名不同 Markdown 后缀的输出追加编号,避免覆盖。
    • 单篇失败后继续其余文档,完成提示包含成功数、失败数、失败原因及输出位置。
  • 导出期间显示进度,同一窗口不能重复触发文档导出。
    • 取消文件或目录选择不创建导出文件。
    • 文件通过原子写入完成,生成失败不会留下半成品或破坏已有单篇输出。
  • PDF 使用 A4 纵向、白底深色正文及四边 20 mm 页边距,不添加封面或页眉页脚。
    • 长代码自动换行,图片和表格限制在正文宽度内。
    • 中文、链接、代码及已渲染的 Mermaid 图表保留在输出中。
  • Word 输出为可编辑的 .docx,保留标题、段落、列表、表格、引用、代码及链接的基础结构和格式。
    • 空笔记、仅空白内容或渲染后没有正文的笔记会生成包含空段落的 Word 文件;单篇与批量导出均支持。
    • 正文不是整页截图;Mermaid 图表作为 PNG 图片嵌入。
    • 代码按独立可编辑行保留换行、空行及缩进,使用等宽字体;不保留语法高亮配色。
    • Word 的排版不承诺与应用预览逐像素一致,不提供旧版 .doc 格式。
  • 图片嵌入导出文件,不依赖旁边的资源目录。
    • Electron 原生解码器无法读取的 WebP、GIF、BMP 等已识别图片格式由隐藏页面解码为 PNG;PDF 与 Word 导出共用此转换。
    • 已保存笔记的本地图片限制在所在仓库范围内;仓库外单独打开的笔记限制在笔记所在目录内,并检查真实路径以阻止符号链接越界。
    • 未命名笔记的本地图片无法定位,会显示替代文本;网络及 data 图片仍可导出。
    • 网络图片沿用下载超时、10 MB 上限及格式校验;本地图片同样限制为普通文件且不超过 10 MB。
    • 无法读取、解码或转换的图片和图表保留替代文本,并在完成提示中列出警告。
    • 音频保留文字链接,不嵌入播放器。
  • PDF、Word 和现有 HTML/TXT 导出共用串行渲染队列,防止多个窗口同时导出时串页。
  • 开发时更新此功能后需要重启客户端。

保存时导出 HTML 与纯文本

  • 可在笔记库 .mynote/config 的 [export] 分区配置保存时导出:

    [export]
      html_root = .published/html
      txt_root = .published/txt
      css_root = .published/css
      publish_root = https://example.com/notes
      extra_css = /notes/theme.css;https://cdn.example.com/print.css
      extra_js = /notes/interactions.js;https://cdn.example.com/addon.js
    
  • html_root、txt_root 和 css_root 可使用绝对路径;相对路径以笔记库根目录为基准。

  • 文件路径上有嵌套的 .mynote 目录但未配置导出目标时,会继续查找父目录中最近的导出配置;导出目录结构相对于找到配置的目录。

  • extra_css 和 extra_js 可配置多个样式表或脚本链接,以 ; 分隔。

    • 链接按配置原值写入 HTML,不复制对应文件,也不添加 publish_root。
    • 额外样式表排在生成的预览样式之后,额外脚本放在正文末尾;仅导出 HTML 时使用。
  • 导出文件保留笔记库目录结构,并把 Markdown 后缀替换为 .html 或 .txt。

  • HTML 使用与应用预览相同的安全 Markdown、代码高亮和 Mermaid 渲染链路,并生成可独立打开的完整页面。

  • 配置 css_root 后,共享预览样式写入 <css_root>/mynote.css,HTML 改为引用该文件。

    • 每次 Markdown 保存触发导出时都会原子覆盖 mynote.css;只配置 css_root 也会更新 CSS,不需要同时配置 html_root。
    • CSS 由应用内置的基础预览样式和代码高亮样式生成,并在当前应用进程首次导出时读取一次;升级应用或开发时修改内置样式后,需要重启应用并再次保存任意 Markdown 才会导出新样式。
    • 修改 css_root 后,下次保存 Markdown 会写入新位置;旧位置的 mynote.css 不会自动删除。
    • 配置 publish_root 且 css_root 位于 html_root 内时,样式链接包含 CSS 子目录,例如 /client/__css/mynote.css。
    • css_root 位于 html_root 外时,样式链接沿用 ${publish_root}/mynote.css;发布时需把该文件放到对应位置。
    • 未配置 publish_root 时使用从当前 HTML 文件到 CSS 文件的相对链接。
  • HTML 引用的库内本地图片会按笔记库相对路径复制到 html_root。

    • 远程图片和 data: 图片保持原链接。
    • 库外图片不会复制,并会显示导出提示。
    • 不再引用的图片副本不会自动删除,以免影响共享资源。
  • 配置 publish_root 后,库内页面与图片链接会添加该发布前缀,Markdown 页面链接同时改为 .html。

    • 支持 HTTP/HTTPS 地址和以 / 开头的站点路径。
    • 外部链接、邮件、Codex 深链接、data: 和页内锚点保持不变。
    • 未配置时使用从当前 HTML 出发的相对链接。
  • TXT 内容来自渲染正文的 innerText,不是 Markdown 源码。

  • File 菜单中的“批量导出当前仓库”会重新扫描当前笔记库,并按现有忽略规则导出磁盘上的全部 Markdown 文档。

    • 至少需要配置 html_root 或 txt_root;缺少时会显示可复制的完整示例配置和各配置项说明。
    • 批量导出沿用现有目录结构、链接、图片、CSS 和安全渲染规则,不会保存或导出编辑器中尚未落盘的修改。
  • 编辑器保存、批量替换、新建、复制、移动、重命名、同步落盘和版本恢复都会更新导出文件。

    • Markdown 被移动、重命名或删除时,对应 HTML/TXT 会同步迁移或清理。
    • 图片副本保留。
    • Markdown 已成功写盘但导出失败时,源文件仍视为保存成功,并显示导出错误。
  • 每次写入都会重新读取配置,修改 .mynote/config 后不需要重启应用。

5.2 写盘与文件格式

  • 保存使用同目录临时文件和原子替换,写盘失败时不会先截断原文件。
  • 仅打开有效 UTF-8 文件。
  • 保存时保留原文件的 BOM 与 LF/CRLF 风格。

5.3 标签与未保存状态

  • 使用多标签页同时编辑多个文档,并在标签间切换。
  • 在文件树中单击文件会使用斜体的预览标签打开;同一窗口只保留一个预览标签,继续单击其他文件会在原位置替换它。
  • 从文件树单击、双击或按 Enter 切换文件后,键盘焦点留在文件树,便于继续浏览;预览标签与普通标签行为一致。
  • 双击文件、从 Quick Open 确认、使用系统打开文件或重新明确打开预览文件时,会保留为普通标签。
  • 双击预览标签、从右键菜单选择“保留打开”、拖动预览标签或开始编辑时,会把预览标签转为普通标签。
  • 已经打开的普通或固定标签不会因文件树单击或搜索结果单击而降级为预览标签。
  • 标签右键菜单可固定或取消固定标签;直接固定预览标签时会先将其保留为普通标签。
  • 命令面板提供 editor.keepOpen、editor.pin、editor.unpin、批量关闭和强制全部关闭命令。
    • Preview、Pinned 与 Dirty 上下文条件可供快捷键使用。
  • 固定标签显示图钉,集中排列在标签栏最左侧,并在关闭其他、关闭左侧、关闭右侧和全部关闭操作中受到保护。
  • 显式关闭固定标签时,第一次操作会提示保护状态;需在 5 秒提示期内再次按关闭快捷键或点击关闭按钮才会关闭。“强制全部关闭”仍可一次关闭包括固定标签在内的所有标签。
  • 每个标签保留独立的原生编辑页,切换标签时不会重写正文。
  • Markdown 源码使用适配深色背景的高对比语法配色,标题和列表符号、链接文字及链接目标均保持清晰可辨。
  • 标签切换后保留横向与纵向滚动位置。
  • 标签切换后保留光标选区。
  • 标签切换后保留当前应用会话内的撤销与重做记录。
  • 支持拖动标签进行排序;固定与未固定标签各自在所属区域内排序,跨区域拖动不会改变固定状态。
  • 标签排序结果随当前笔记库会话保存。
  • 标签右键菜单支持保留、固定、取消固定,复制已保存文件的绝对路径或笔记库相对路径,查找文件或当前标题引用,以及关闭当前、其他、左侧、右侧、全部未固定标签或强制全部关闭。
  • 按下 Ctrl+Tab 时显示按最近查看顺序排列的标签列表。
  • 最近标签列表打开时,↑、↓ 只切换列表选项,不会滚动编辑器或预览。
  • 松开 Ctrl 后切换到列表中的选中项。
  • 修改后的文档会在标签名称前显示圆点标记。
  • 关闭存在未保存修改的标签时会先进行确认。
  • 最后一个标签可以直接关闭。
  • 无文档时,保存、另存为和图片插入操作不可用。

5.4 会话恢复

  • 每个笔记库独立保存已打开标签、活动标签和未保存内容。
  • 预览与固定状态随笔记库会话保存和恢复。
  • 每个已恢复 Markdown 标签会保存并恢复光标、选区、编辑区/预览区滚动位置及上次聚焦窗格。
  • 切换笔记库时同步切换标签。
  • 关闭窗口前刷新当前笔记库的恢复稿。
  • File → Exit 和命令面板中的 file.exit 共用退出操作。
    • 默认快捷键为 Windows/Linux 的 Ctrl+Q、macOS 的 Command+Q。
    • 等待各窗口完成恢复稿保存,再停止后台服务并写完日志,最后结束应用进程。
    • 多窗口同时返回关闭确认时,退出收尾只执行一次,避免重复进入退出流程后残留进程。
    • 多窗口与标签恢复规则见笔记库。
  • 未打开笔记库时,临时标签不会写入恢复记录。
  • 启动或切换到没有已保存会话的笔记库时保持无文档状态,不自动创建新文档。

5.5 外部文件变更

  • 外部程序修改未在本地编辑的文档时自动重载。
  • 外部程序与本地同时修改文档时显示双版本冲突对比。
  • 外部删除文件时保留编辑器内容并以中划线标记标签,不弹出提示;可继续编辑,保存时直接在原路径重建文件。正文相对最初加载内容未变化时关闭不要求保存,已有修改时仍执行未保存确认。应用内部移入回收站会先停止对应文件监听并关闭对应标签。

6. 笔记库与文件管理

6.1 笔记库

  • 将普通本地文件夹作为笔记库打开,无需导入或转换。
  • 通过系统文件夹对话框选择笔记库。
  • 打开笔记库也可从 File 菜单执行,默认快捷键为 Ctrl/Cmd+K Ctrl/Cmd+O。
  • 通过“文件 → 新建窗口”或 Ctrl+Shift+N(macOS 为 Cmd+Shift+N)打开空白窗口,可在多个窗口中同时打开不同笔记库。
  • Windows 上通过 npm start 启动时,主窗口在首次绘制后显示并激活;若系统仍让启动终端保持前台,会再次请求激活。启动期间用户切换到其他程序后不会抢回焦点。
    • 开发启动 npm start 复用上次成功构建,不自动检查源码是否更新;构建标记或记录的产物缺失时自动完整构建。
    • npm run dev 增量构建并启动 Vite renderer 开发服务;也可先执行 npm run build:dev 再用 npm start 启动静态产物。
    • 增量构建保留四组独立的 TypeScript 缓存,继续执行类型检查;编辑器输入与锁文件未变时复用编辑器 bundle 和许可证。
    • 根 tsconfig.json 引用四组 TypeScript 项目,使 VS Code 打开源码时自动选择对应配置并加载全局类型声明。
      • 若编辑器仍保留旧的类型报错,执行 VS Code 命令“TypeScript: Restart TS Server”重新加载项目配置。
    • 删除、重命名输入文件,或修改编译配置、包清单、锁文件后,增量构建自动回退到完整清理构建,避免残留旧模块。
    • npm run build、测试、基准、同步管理及发布构建仍完整清理重建;构建失败后不能复用不完整产物。
    • 需要完整清理时先正常退出占用 .build 的应用或终端,避免 Windows 目录占用错误;静态产物中的代码修改生效需要重启桌面应用。
    • 耗时诊断和开发构建规则见 TS 迁移启动性能。
    • 主窗口、片段窗口、Quick Cmd Form 和发布渲染页统一使用 ESM;运行时通过显式导入共享工具、类型和窗口状态,初始化按原有顺序执行。
    • Vite 开发模式支持 CSS 热更新、无状态 ESM 函数模块 HMR 和 runtime ESM 业务函数体热替换。
      • 安全热替换保留编辑器实例、未保存内容、选区、滚动位置和撤销历史,不重复注册事件监听器。
      • runtime 导入、函数签名、初始化、变量声明、状态类、无状态工具的回调工厂或导出结构变化时,先保存恢复稿和窗口快照,再刷新并恢复打开的标签、未保存内容和选区。
      • 刷新会重建编辑器,不能保留撤销历史;打开的对话框关闭后才执行待处理的刷新。保存失败或快照超出存储配额时取消刷新并保留当前编辑器。
      • 开发页面仍使用 file://,继续加载本地媒体;开发服务只监听 127.0.0.1,保留沙箱、上下文隔离及主帧校验。
      • 编辑器适配器源码也由 Vite 加载,状态类修改时安全刷新;主进程、preload、开发工具配置及依赖修改后,需要退出开发应用并重新运行 npm run dev。
      • 具体范围和独立测试命令见 Vite renderer 开发。
  • 所有平台均可按 Ctrl+Shift+Alt+S 在当前已打开的应用窗口间循环切换。
  • 新打开窗口、切换到已有窗口或从“最近笔记库”切换笔记库后,如果当前标签是编辑器且编辑区可见,会自动聚焦当前编辑器;应用内对话框打开时不会抢走对话框焦点。
  • 每个窗口独立保有当前笔记库、目录索引和标签恢复上下文;最近笔记库、偏好和同步账号仍在应用内共享。
  • 窗口标题显示当前笔记库名称,方便在系统任务切换器中区分多个窗口。
  • 自动恢复上次使用的笔记库。
  • 退出时保存各窗口仍打开的仓库;下次启动并行重建窗口,并从各仓库恢复稿还原标签。恢复时以稳定的最近仓库记录校验路径,不会因其他窗口先完成而中断;手动新建的空窗口不会自动打开最近仓库。
  • 各笔记库分别保存打开标签和活动标签;切换笔记库时恢复该库的标签,没有打开笔记库时不持久化标签。
  • 最近笔记库不限制条目数;侧边栏选择器、原生“文件 → 打开最近”菜单和快捷选择面板共享同一列表,并随打开、重命名和移除操作即时更新。
  • 所有平台统一使用 Ctrl+R 打开类似 Quick Open 的最近笔记库面板。
    • 可按仓库名称或完整路径模糊筛选,并使用方向键、Enter 或鼠标切换。
    • macOS 的 Cmd+R 仍用于重新加载。
  • “打开最近的笔记库”也注册为 workspace.openRecent 命令,可从命令面板执行。
  • 所选目录被移动或删除后,清除失效选择及其最近文件和收藏状态,并从最近列表移除。
  • 根目录失效时也会清除当前内存索引;其他扫描错误仍按原错误报告,不会误删最近记录。

6.2 目录树与侧边栏

  • 侧边栏目录树展示文件夹和受支持的 Markdown 文件。
  • 支持 .md、.markdown、.mdown 和 .mkd;.mynote、符号链接和名称以 .app 结尾的 macOS 应用包不会进入目录树或递归扫描。
  • 工具栏使用“编辑 / 并排 / 预览”三段式控件选择唯一的文档视图,避免同时隐藏编辑区和预览区。
    • 连续切换视图后重新显示编辑区时,会保留 caret 和选区并恢复文本焦点,可立即继续输入。
    • 每个文档页面独立记住编辑、并排或预览模式,切换页面互不影响;视图模式随笔记库会话保存在本机,重启后随页面恢复。
    • 搜索页和差异模式的临时布局不会覆盖文档页面保存的视图模式。
    • 侧栏与大纲仍使用独立开关。所有选择按笔记库保存在本机。
  • 侧栏中的“仓库”“最近”“收藏”和“文件”分区可分别折叠或展开,选择会按笔记库保存在本机;各分区标题使用统一的加大字号。
  • 拖动侧栏与编辑区、编辑区与预览区之间的分隔条调整大小;侧栏宽度和编辑/预览比例按笔记库自动保存在本机,重启后恢复。
  • 分隔条支持 Tab 聚焦后用方向键调整,Shift 加方向键加大步长;窄窗口上下排列时可调整编辑与预览高度比例。
  • 目录树使用背景色标示当前选中项;未由当前标签关联时,选中项和滚动位置按笔记库恢复。
  • 文件树标题栏的设置菜单提供“关联当前页面”和“显示空文件夹”两个选项;两个选项均按笔记库保存在本机。
  • 切换笔记库后,旧笔记库的文件树设置保存响应不会修改新笔记库的界面。
  • “关联当前页面”默认开启;原全局设置字段不迁移,新版本直接使用各笔记库自己的默认值或已保存值。
  • 开启时,切换标签页会展开对应文件的父目录并高亮节点;节点不在可视区域时,文件树会滚动到该节点;目录展开状态按笔记库恢复。
  • 文件树存在多选时,关联当前页面暂不替换整组选区;恢复单选后继续按上述规则定位当前文件。
  • 关闭时,切换标签页不改变文件树的选择、展开状态和滚动位置;重新开启后立即定位当前页面。
  • 未保存页面、搜索页及笔记库外的文件没有对应节点,关联开启时会清除树中的高亮。
  • 目录树支持鼠标右键菜单及 Shift+F10 键盘菜单。
  • 上下文菜单支持方向键、Home/End、Enter/Space 和 Esc 操作。
  • 目录树使用单一 Tab 停靠点。
  • 目录树支持方向键、Home/End、Enter 和空格键导航、展开与打开条目;后台刷新、过滤变化或目录重绘后按路径恢复原焦点,避免方向键意外变成滚动文件树。

文件树刷新机制

重新扫描与界面重绘
  • 左侧文件树使用最近一次扫描得到的工作区快照,不持续监听整个笔记库目录,也没有独立的定时目录刷新。
    • 重新扫描会读取磁盘目录、受支持的 Markdown 文件、文件大小、文件修改时间及同步冲突标记,再更新文件树。
    • 扫描仍遵守下文的路径边界、文件数量上限和 .mynoteignore 准入规则。
    • 扫描后仍应用当前文件筛选和“显示空文件夹”设置,因此磁盘上存在的文件不一定显示。
  • 界面重绘只重新展示已有快照,不重新枚举磁盘目录。
    • 展开或折叠、修改文件筛选、切换“显示空文件夹”、关联当前标签及选择变化可能改变树的显示,但不能据此判断已读取外部目录变化。
    • 重绘时按路径恢复树内键盘焦点;同一笔记库刷新时沿用展开状态和仍有效的选择,移除已不存在或被筛选隐藏的选区条目。
会重新扫描的入口
  • 打开、切换或启动时恢复笔记库。
  • 点击文件树标题栏“刷新笔记库”,或执行同名命令。
    • 默认快捷键为 Windows/Linux 的 Ctrl+K R、macOS 的 Cmd+K R,也可在快捷键设置中修改。
    • 手动刷新先保存会话恢复信息,再扫描磁盘;它不会把未保存正文写入笔记文件,也不会强制重新加载所有已打开文档。
    • 按钮显示加载状态,完成后短暂显示成功或失败反馈;扫描失败会提示原因。
  • 在应用内新建文件或文件夹、重命名、移动、复制、粘贴、移入回收站,以及撤销或重做这些操作后,使用返回的新快照更新树。
  • 在当前窗口保存设置且改变 Markdown 文件扫描上限后。
  • 手动同步正常完成后;同步抛出错误时也会尝试刷新,以展示可能已经写入的冲突文件。
    • 同步因冲突或未保存文件等原因直接暂缓时,不能依赖该手动同步入口刷新树。
  • 自动同步取得非空结果后,主进程为打开该笔记库的各窗口重新扫描并发送快照。
    • 此刷新不要求实际拉取到新文件;返回“暂缓”结果时也会发送快照。
    • 未登录等情况未取得结果,或同步过程抛出错误时,不会通过该回调刷新树。
    • 因此自动同步可能顺带显示此前的本地外部目录变化;它不是文件树独立的定时刷新机制。
  • 恢复文件历史版本、部分仓库恢复或冲突处理流程,以及打包界面的“刷新笔记库”等入口,也会扫描并更新主窗口文件树。
  • 每次应用文件筛选、筛选预设或文件树差异比较前都会重新扫描,刷新候选文件和时间信息;因此外部新建的文件会参与本次筛选。
不会直接重新扫描的情况
  • 在资源管理器、终端或其他编辑器中新增、删除、移动、重命名文件或文件夹,以及修改 .mynoteignore,不会单独触发整棵文件树刷新。
  • 普通“保存”和“另存为”更新文档状态及相关大纲索引,不直接重新扫描左侧文件树。
    • 未命名文档首次保存到笔记库后,文件可能要等下一次扫描才出现在树中。
  • 外部文件监听针对已登记监听的具体文档路径,不是整个笔记库的递归监听。
    • 监听父目录事件时按文件名过滤,并等待约 120 毫秒合并事件;应用自身保存会按内容签名抑制对应通知。
    • 外部修改主要更新已打开文档、冲突提示和相关大纲索引;外部删除会保留编辑器内容并标记标签缺失,不直接从树快照中移除节点。
    • 同目录中其他未监听文件的变化通常被忽略;监听错误也不会自动回退为整库扫描。
  • 切回应用窗口、切换标签或刷新编辑器 Git HEAD 差异,不会重新扫描目录树。
  • 同一笔记库在多个窗口打开时,一个窗口的普通文件操作不会统一广播新的树快照;其他窗口需自行刷新或等到后续自动同步快照。
外部变化后的使用方式
  • “有时自动刷新,有时不刷新”通常取决于外部变化之后是否又发生了上述扫描入口;单纯的界面重绘或文档监听不足以发现目录变化。
  • 需要立即确认外部文件或目录变化时,执行“刷新笔记库”;若仍不可见,检查扩展名、准入规则、当前筛选和空文件夹显示设置。

路径映射与扫描边界

  • 可在笔记库 .mynote/config 中按 Git config 风格配置 [mirror] 下的 host:

    [mirror]
      host = https://react.dev/learn
    
  • HTTP/HTTPS 链接位于该前缀内,且映射的 Markdown 文件存在时,编辑区和预览区默认打开本地文件。

    • 按住 Shift 点击始终打开原链接。
    • 未配置、配置无效、链接越界或文件不存在时仍按外链处理。
  • 例如 https://react.dev/learn/creating-a-react-app 映射到仓库根目录的 creating-a-react-app.md。

  • 单个笔记库默认最多扫描 10000 个 Markdown 文件和 20000 个目录项;可在设置中调整文件上限,保存后当前窗口自动刷新,目录项上限保持为文件上限的两倍,超限时明确报错。

  • 所有工作区 IPC 都校验真实路径,拒绝 .. 越界和通过符号链接访问库外文件。

.mynoteignore 准入规则

  • 根目录可创建 UTF-8 编码的 .mynoteignore,按 .gitignore 语义支持:
    • 空行、# 注释、! 反选、*、? 和 **。
    • 以 / 锚定根目录,以及以 / 结尾的目录规则。
Gitignore 基本规则
  • 空行用于分隔规则,以 # 开头的行是注释;需要匹配字面量 # 或 ! 时在前面加反斜杠。
  • 同一个规则文件内按从上到下的顺序匹配,后出现的匹配规则覆盖先前结果。
  • !pattern 反选先前排除的路径,但不能单独反选已被排除目录内的文件:
    • test/ 排除整个目录后,!test/1.md 不会生效。
    • 若要只保留该文件,可写成 test/* 和 !test/1.md,让父目录本身保持可遍历。
  • 不含 / 的模式可匹配任意层级中的名称;开头的 / 把模式锚定到规则文件的根目录;结尾的 / 只匹配目录。
  • * 匹配除 / 外的任意内容,? 匹配除 / 外的单个字符,[abc] 和 [a-z] 匹配字符集合或范围,** 可跨越目录层级。
  • 行尾空格默认忽略;需要保留字面量空格时使用反斜杠转义。
  • 完整语法和更多示例见 Git 官方 gitignore 文档。
# 构建产物与临时文件
build/
*.tmp
/private.md
!important.tmp
  • 规则只限制尚未加入管理的新路径:
    • 已进入目录树或同步基线的文件继续显示、搜索和同步。
    • 命中规则的新文件保持隐藏且不加入同步。
    • 保存和文件变更通知触发的大纲更新也遵守准入规则;删除并退出管理后,同名文件重新创建不会绕过过滤。
    • 准入结果保存在 .mynote/managed-paths.json,重启后仍有效。
  • .mynoteignore 最大 256 KB,必须是普通文件,不显示在只展示 Markdown 的目录树中。
    • 它参与托管同步,也不能被自身规则排除。
    • .app 应用包和 .mynote 是不可反选的内置排除项。
  • 多设备并发修改规则时,远端版本生效;本地并发版本保存在 .mynote/sync-conflicts/mynoteignore-<设备>-r<revision>.txt,不会生效或再次同步。
  • .mynoteignore 同步要求所有设备使用支持“只限制新路径”的客户端,并重启已升级的同步服务;旧客户端可能停止跟踪命中规则的已有文件。
Ignore 逻辑使用范围与一致性
  • 仓库级 .mynoteignore 用于以下流程:
    • 工作区扫描:决定文件树、全文搜索和大纲索引可见的 Markdown 文件。
    • 工作区递归操作:重命名、移动、复制、删除和批量导出枚举 Markdown 文件时跳过未准入路径。
    • 托管同步:本地变更预览、冲突检查、上传与删除推断使用同一份准入结果。
    • .mynoteignore 自身仍作为同步文件处理;远端应用规则文件后,下一次本地扫描使用新规则。
  • 片段集合的 .cfg.ignore 只保存 ignore:=过滤文件路径 引用:
    • 每个被引用的过滤文件都复用仓库级规则解析与路径判断。
    • 规则以各过滤文件所在目录为根;一个来源路径命中任意过滤文件就不加载。
    • 片段过滤不读取仓库的已管理路径记录,因此规则始终直接作用于片段来源。
  • 文件树和打包界面的“排除规则”使用同一个 Gitignore 匹配库,但只匹配已经进入工作区树的 Markdown 文件:
    • 它与文件名、相对目录、扩展名和修改时间条件共同决定当前显示或打包范围。
    • 它不参与仓库准入、文件操作或同步,也不读写 .mynoteignore。
  • 算法统一情况:
    • 规则语法统一。三处都使用项目固定版本的 ignore 库,遵循 Gitignore 的规则顺序、通配符、注释、转义和反选语义。
    • 仓库扫描、工作区递归操作、同步和片段集合共用 MyNoteIgnorePolicy;它统一规范化路径分隔符,并集中处理 .mynoteignore、.mynote 和 .app 的固定规则。
    • 最终策略不完全相同,这是使用场景的必要差异:仓库规则只阻止新路径准入,已管理路径继续可见和同步;片段规则没有“已管理”例外;界面排除规则只是已有文件树上的临时筛选。
    • 目录遍历也按内容范围分别实现:工作区只收集支持的 Markdown,托管同步收集协议支持的 Markdown、图片和 .mynoteignore,片段集合读取配置指定的普通文件。工作区与同步扫描另行跳过符号链接,这不属于 Gitignore 匹配算法。

6.3 文件操作

新建与文件树工具

  • 支持新建文件和文件夹。
  • 在当前文件夹新建文件时,没有受支持的 Markdown 扩展名就自动补充 .md;已有 .md、.markdown、.mdown 或 .mkd 时保持不变。
  • 文件树标题栏集中提供新建文件、新建文件夹、刷新、全部展开、全部折叠和文件树设置图标按钮。
  • 文件树标题栏从“刷新笔记库”开始的刷新、全部展开、全部折叠、修改时间过滤和文件树设置操作均可从命令面板执行;
    • 这些入口共用 workspace.* 命令,仅在已打开笔记库且没有模态窗口时生效。
    • 默认快捷键依次为 Ctrl/Cmd+K R、Ctrl/Cmd+K E、Ctrl/Cmd+K C、Ctrl/Cmd+K T 和 Ctrl/Cmd+K ,。
      • 也可在快捷键设置中修改。
    • 5 个按钮的 tooltip 显示当前平台实际生效的快捷键,并随用户配置即时更新。
  • 文件树设置菜单可切换是否显示不包含 Markdown 文件的空文件夹,并按笔记库记住该选项。
  • 修改时间、文件名、目录、扩展名或排除规则等过滤启用时仍遵循“显示空文件夹”设置;关闭该设置时只保留匹配文件及其父目录。
  • 隐藏空文件夹时会递归隐藏仅包含空目录的父目录;该选项默认显示空文件夹。

文件筛选与打包

打包文件
  • 文件树时间过滤按钮旁提供“打包文件”按钮,首次沿用文件树筛选,随后恢复独立的上次选择,并显示已选、匹配和总文件数。
    • 打包入口由文件树控件模块 src/renderer/runtime/tree-controls.mts 注册,首次打开时按需加载打包界面。
    • 首次打开默认全部勾选;同一笔记库重新打开时保留上次勾选。
    • 切换文件夹复选框会递归切换自身及所有子孙节点,混合选择显示半选状态。
    • 树上方的操作行依次显示“应用筛选”“清除筛选”“全选”“取消全选”“全部折叠”“全部展开”和“刷新”。
    • 刷新按钮旁的“统计文件大小”默认勾选,展示文件的磁盘字节大小及文件夹内当前筛选范围的文件大小总和;取消勾选隐藏大小。
      • 复选框后显示当前已勾选文件的总大小;取消勾选时一并隐藏。
      • 操作行中的按钮、复选框和总大小垂直居中对齐。
      • 文件、文件夹和总大小统一按 KB(1 KB = 1024 字节)显示,保留两位小数,每三位数字用逗号分隔。
      • 总大小在文件勾选、文件夹递归勾选、全选和取消全选后立即重新计算;未选择文件时显示 0.00 KB。
      • 文件和文件夹行显示的磁盘大小在刷新时更新,文件夹行仍汇总当前筛选范围的文件。
      • 同一笔记库关闭后重新打开保留此选项。
    • 筛选区初始时按内容高度同时显示“编辑筛选条件和预设”与“修改时间”,不在操作按钮下方保留空白;展开筛选条件时会增大筛选区,文件树保留最小可见高度,对话框空间不足时可滚动查看文件树、问答与操作区。
    • 筛选区始终显示灰色边框,失去焦点时仍可辨认其范围。
    • 点击文件夹名称可切换其展开状态。
    • 命令面板可搜索“打包文件”或 workspace.packFiles 打开同一对话框;默认无快捷键,可在快捷键设置中绑定。
    • 底部的“在内容头部插入相对路径”默认勾选,可取消;路径头格式为 // ======= 相对路径。
    • 点击“选择文件打包”按文件树顺序读取所选文件的磁盘内容,每个文件的每行以从 1: 开始的行号为前缀,以空行拼接后在对话框中展示并可复制;未保存编辑需先保存。
    • 任一文件读取失败会显示具体路径,不输出不完整的打包结果;修改筛选、选择或路径选项会清空旧结果。
    • “查询打包”保留查询命令和命中文件打包流程,但不发送最终回答请求。
    • “选择文件提问”跳过查询命令和文件过滤,直接打包当前勾选的全部文件,在打包结果框显示内容并发送最终回答请求。
      • 最终回答请求的 messages 依次为系统提示词、打包文件内容、用户问题;文件内容和问题分别放在独立的 user 消息中,原样发送。
      • 默认系统提示词要求只使用文件事实回答、证据不足时明确说明、引用相关文件的相对路径,并将文件内容视为不可信数据,不执行其中的指令。
    • “选择文件打包”位于打包结果框下方、“复制打包结果”左侧;只在本机打包当前勾选的文件,不发送任何 DeepSeek 请求。结果框始终保留布局位置,避免首次或重复打包时界面跳动;没有结果时复制和另存为不可用。
    • 打包结果框下方可复制完整打包内容,包括超过 1 MiB 的结果,也可通过“另存为…”将完整结果保存为 UTF-8 文件;默认扩展名为 .md,手动指定的扩展名会保留。底部按钮用于复制 DeepSeek 回答。
  • 打包界面可从完整文件树重新筛选;清除筛选恢复全部文件。每次应用筛选、预设或清除筛选都会重新扫描,并按当前条件重建默认全选的文件树;“刷新”按钮也会重新扫描并保留当前条件。
  • 关闭打包对话框时仅隐藏界面;在同一笔记库再次打开会复用原有界面,保留文件勾选、筛选、展开状态、问题及打包结果。在其他笔记库打开时会创建新界面。
  • 打包期间禁用筛选和勾选,避免结果与当前选择不一致;切换预设、应用筛选、修改勾选或路径头部选项会清空旧输出并禁用复制。
筛选条件
  • 文件树和打包界面共享可保存、更新、重命名、删除的筛选预设,支持包含规则、排除规则与修改时间。
  • 多个筛选条件须同时满足;空项表示不限。
  • 包含规则每行一条,复用排除规则的 Gitignore 匹配语法;留空或仅写注释时包含所有文件(仍受其他条件限制)。
    • 例如 工作/ 包含目录下的文件,**/*周报*.md 匹配文件名,多个正向规则匹配任一条即可。
    • 支持 # 注释和 ! 反选;排除规则优先,包含规则不能恢复被排除的文件。
    • 排除规则同样每行一条;不能在已排除的父目录下单独反选文件。
    • 不迁移旧版文件名、目录和扩展名条件;扩展名可改用 *.md 等包含规则。
  • 包含规则和排除规则输入框至少显示 120px 高度,内容较多时仍可手动拉高。
  • 筛选仅控制显示和打包范围,不修改 .mynoteignore、文件或同步规则。文件树显示匹配数量,重置后显示全部文件并恢复默认差异选项。
文件筛选预设与打包
  • 预设包括不可修改的“全部文件”“最近七天”和每个笔记库最多 100 个用户预设。选择预设立即应用;填写名称后可另存、更新、重命名或删除,成功与失败均以不改变布局的 toast 反馈。
  • 预设保存筛选条件与时间规则,不保存独立的编辑器差异选项;相对时间在应用或恢复时重新计算,指定日期保持不变。
  • 用户预设、文件树当前条件及时间范围、打包界面上次使用的条件及时间范围,按笔记库分别保存在应用用户数据目录的 repository-ui-state-v1.json;重启后各自恢复。
  • “文件筛选与差异”和“打包文件”使用同一套过滤器,以打包界面为模板,共用预设编辑、修改时间字段、校验、日历入口和布局代码。
    • 界面入口分别为 file-filter-diff.mts 中的 createFileFilterDiff 和按需加载的 file-pack.mts。
    • 公共组件集中在 file-filter-ui.mts,包括预设编辑、时间范围字段、筛选区域模板和输入交互。
    • 公共业务集中在 file-filter.mts,包括筛选匹配、时间解析、预设身份判定及预设操作校验和列表变换;界面通过回调完成保存和应用。
    • 两处共享预设列表,但分别保存当前选择。
    • 预设下拉框与预设操作栏在筛选区域滚动时保持可见。
    • “编辑筛选条件和预设”与“修改时间”默认折叠,展开后使用相同的平面缩进布局。
    • 单行字段的标签与输入控件同排显示;包含和排除规则使用整行多行输入,预设名称位于条件编辑首行。
    • 预设操作栏统一显示“另存为预设”“更新”“重命名”“删除”;“应用筛选”“清除筛选”位于各自的外部操作行。
    • 两处统一通过同一入口解析时间条件;切换到自定义时间或指定日期时,自动聚焦对应输入框。
    • 清除筛选共用完整草稿重置逻辑:清空包含、排除和时间输入,恢复“全部文件”预设,并清除自定义校验;随后重新扫描笔记库并应用不限条件。
    • 文件树专有的差异选项和“比较整个文件树”操作继续保留;文件树清除筛选成功后仍恢复默认差异选项。
    • 重新打开缓存的打包窗口时刷新共享预设列表,使文件树中新建、重命名或删除的预设立即反映到下拉框;保留当前筛选、打包输出和提问草稿。
  • 内置预设不能更新、重命名或删除,尝试操作时会提示先另存为用户预设;用户预设操作按钮提供提示,校验或保存失败时显示原因。
修改时间过滤
  • 文件树标题栏提供修改时间过滤:默认展示全部文件,可选择最近一天、七天、一个月、两个月、三个月、半年,也可输入自定义时间表达式。
    • 纯数值仍以天为单位(如 0.5 表示半天);
    • “一个月”实际按 30 天计算,半年按 180 天计算,不是日历月。
    • 固定时间间隔支持可组合的 ms、s、m、h、d、w 单位(如 1d 12h,其中 m 表示分钟);
      • 也支持 ISO 8601 周/日/时间间隔(如 PT1H30M)。
    • 2025-3-1 12:0 形式的时间点按当前系统时区转换为时间戳。
    • 也可通过日期输入与独立的“日历”按钮指定起始日期,并可一键重置。
    • 日期选择器导致窗口暂时失焦时,过滤面板仍保持打开,以便结果写回输入框。
    • 文件修改时间统一取 mynote 仓库最近历史时间与磁盘 mtime 中较早的一个,不依赖 Git;
    • 文件首次加入时会在新增历史中记录当时的磁盘 mtime,只有新增历史时使用该记录,旧历史没有该字段时兼容回退到新增版本时间,尚无历史时使用当前磁盘 mtime。
    • 应用启用时间条件的筛选或预设时会先重新扫描笔记库,刷新候选文件及其时间,再应用筛选。
    • 文件过滤和文件差异的选择均按笔记库保存,切换笔记库或重启后恢复。
    • 旧版数值天数配置继续兼容;重置文件时间后恢复全部文件及默认的 Git HEAD 差异选项。
    • 退出差异模式恢复普通布局时会重新生成当前文档的大纲,避免保留进入差异模式前的文档大纲。

文件差异

当前文件差异
  • 时间过滤面板的“文件差异”默认选择排在首位的 Git HEAD;
    • 还可关闭差异、“同上”使用文件过滤时间,或通过“其他”独立选择时间预设、自定义时间表达式和日历日期。
    • 选择框旁的“切换”按钮会按下拉框顺序循环选择并立即应用,workspace.cycleFileDifferenceMode 命令也可从命令面板触发并在快捷键设置中绑定;
    • 从面板外执行时不会打开面板,而是直接切换、保存并刷新编辑器差异视图。
    • 状态栏常驻显示当前生效选项,并为“同上”和“其他”显示完整时间,如“当前差异模式:同上-自定义时间-3天”和“当前差异模式:其他-自定义时间-3天”。
    • 文件时间为“不限时间”时会跳过无法产生基线的“同上”。
    • 切换离开“其他”后仍会按笔记库保留最近使用的预设、自定义表达式或日期,再次切回时自动恢复。
    • 选择 Git HEAD 时,当前文件与笔记库所在 Git 仓库的 HEAD 对应版本比较;
    • 仓库可位于笔记库的上级目录,并兼容 Git 2.23 等不支持 rev-parse --path-format 的旧版本。
    • 应用可见期间自动跟踪 commit、分支切换和 reset 等 HEAD 变化;窗口重新获得焦点时也会立即检查。
    • 未初始化 Git 或 HEAD 尚无提交时会提示版本不可用;HEAD 未跟踪的新增文件使用空基线,当前内容全部标为新增。
    • 独立差异时间与修改时间、整个文件树比较基线共用时间字段生成函数;保留各自的字段标签、控件 ID 和时间选项。
    • 展开独立差异时间字段时,面板会重新定位在窗口可见范围内,并在窗口高度不足时提供内部滚动。
    • 启用后,编辑器以淡绿色标出当前内容相对所选基线新增或修改的行,并随未保存编辑即时更新;
    • 删除行因当前编辑器没有对应行而不着色;两种基线复用同步中心的逐行差异计算。
    • 时间基线使用目标时间或更早的最近 mynote 历史版本,不依赖 Git,且截止时间早于首个历史版本时以空内容为基线,将当前正文整篇视为新增。
    • 相邻差异行合并为一处。
      • 从 Go 菜单或按 Alt+N / Alt+P 可跳过当前整处差异,定位到下一处 / 上一处的首行。
      • 到达首尾后不循环折返。两个命令的绑定可在快捷键设置中修改。
    • 两个导航命令分别为 editor.nextDifference 和 editor.previousDifference。
    • 只有一处差异时,两个快捷键仍能重新选中并滚动到该处;按住 Ctrl(macOS 为 Command)双击差异行会返回编辑页并将对应行定位到顶部,纯删除行定位到当前正文中紧邻的行。
    • 同一路径删除后重新创建时,历史查询优先使用当前有效文件身份;若有多个有效身份,选 revision 最新者。只有不存在有效身份时才回退到最新删除墓碑。
    • macOS 的 Go 菜单仅展示这些快捷键,由应用快捷键系统处理 Option 组合,避免原生菜单截获按键;
    • 即使系统将 Option+N/P 报告为重音组合输入,快捷键仍会执行并抑制后续字符提交。
文件树差异
  • 面板底部的“比较整个文件树”沿用当前“文件差异”基线,并像“应用”一样立即应用及按笔记库保存面板中的文件时间与文件差异选择;
    • 选择 Git HEAD 时,先固定当前 HEAD 提交,再将当前未过滤 Markdown 文件树中的每个文件与该提交中的版本比较。
    • 选择“同上”或独立差异时间时,读取对应截止时间或更早的最近 mynote 历史版本。
    • “文件差异”关闭时继续使用当前文件时间条件;
    • “同上”或关闭差异且文件时间为“不限时间”时,比较按钮保持禁用,避免用不存在的截止时间启动比较。
    • 结果在占满应用窗口宽度和高度的独立对话框中按文件相对路径列出实际正文变化,文件列表弹性占据顶部控件与底部按钮之间的剩余高度并独立滚动,默认全部展开;
    • 每个标题栏可直接跳转并打开对应文件,顶部可全部折叠或全部展开,也可切换精简差异和自动换行。
    • 对话框提供 Git HEAD 和时间范围选项、表达式、日期及日历控件,修改后可直接重新比较。
    • View 菜单的“文件树差异”、view.fileTreeDifference 命令或 Ctrl/Cmd+Alt+D 可直接打开该对话框;
    • 关闭或跳转只隐藏对话框,同一笔记库再次打开时会保留上次的比较基线、摘要、差异内容和展开状态,跳转按钮会恢复为可再次使用的状态。
    • 比较会统一基线正文与磁盘正文的换行符,并沿用逐行差异对文件末尾换行的处理,避免把正文相同的 CRLF 文件或仅末尾换行表示不同的文件误报为变化。
    • Git HEAD 未跟踪的新增文件使用空基线并显示为整篇新增;没有可靠同步历史身份的文件会跳过并显示数量。
    • Git blob 与磁盘文件使用同一 UTF-8 解码规则去除 BOM,并统一 CRLF、CR 和 LF。
      • 文件筛选与逐行渲染还会再次规范化,避免正文相同的 Windows 文件被误报为整篇变化。
    • 每个文件的展开或折叠图标使用独立的左侧槽位,与文件名保持间距。
  • 获取差异时,主进程终端与渲染器开发者工具会输出带 [mynote:file-diff:*] 前缀的结构化详细日志。
    • 日志包括目标时间、历史版本、基线来源、缓存命中、差异行/块数量和耗时,不输出笔记正文。

文件整理与导航

  • 支持重命名、移动和复制文件或文件夹;文件树条目可拖到目标文件夹,或拖到文件并以其父文件夹作为目标,默认移动,拖拽时按 Ctrl(macOS 为 Cmd)则复制。
  • 文件树支持文件与文件夹混选:普通点击保持打开文件或展开文件夹的行为;Ctrl(macOS 为 Cmd)点击增减选区,Shift 点击按当前可见节点顺序选择范围。右键已选项保留整组选区,右键未选项改为单选;拖动已选项操作整组,拖动未选项只操作该项。
  • 文件树右键菜单提供“比较文件”,仅在恰好选中两个文件且没有正在执行的文件树操作时可用;选中文件夹、单个文件或更多条目时禁用。
    • 命令面板也提供“比较文件”(workspace.compareFiles),沿用相同的选区与可用性规则;无默认快捷键,可在快捷键设置中自定义。
    • 使用 VS Code 的 --diff 打开磁盘上的两个文件,按文件树顺序排列左右两侧;未保存的编辑内容不参与比较。
    • macOS 通过系统应用启动服务查找 VS Code;Windows 查找标准安装目录和 PATH 中的安装位置;Linux 需要 code 命令位于 PATH。
    • 未安装 VS Code、路径失效或启动失败时,使用应用内提示框显示错误。
  • 筛选隐藏或刷新后已不存在的条目从选区移除;折叠目录中的已选子项保留。多选仅在当前笔记库会话中有效,切换笔记库或重启应用后恢复现有的单选路径。
  • 文件树聚焦时支持 VS Code 风格的操作快捷键:Windows/Linux 按 F2 重命名、Delete 移入回收站,macOS 按 Enter 重命名、Cmd+Backspace 移入回收站(也支持 Delete);Ctrl/Cmd+X 剪切,Ctrl/Cmd+C 复制,Ctrl/Cmd+V 粘贴。
  • 文件树聚焦时,Ctrl/Cmd+Z 和 Ctrl/Cmd+Shift+Z 分别撤销、重做新建、重命名、移动、复制、粘贴和移入系统回收站;多选操作作为一步处理。多选删除及其撤销、重做并发处理各项目的系统回收站操作,统一更新工作区状态并刷新文件树。编辑器聚焦时仍撤销、重做正文修改。文件树历史只在当前窗口和当前笔记库会话内保留。
  • 点击文件树空白处会将焦点移入文件树。重命名、新建文件夹、移动、复制、粘贴及撤销、重做完成后,焦点留在文件树;原节点消失时聚焦操作结果或其他可见节点,空树则聚焦文件树容器。新建文件继续聚焦新文档以便输入正文。
  • 删除及撤销新建、复制时仍使用系统回收站,不另存文件副本;恢复会沿用删除时记录的系统回收站类型。回收站项目已被 Explorer 恢复或移走时,对应历史记录失效并从文件树撤销历史中移除,提示中列出失效项目的相对路径;项目仍在回收站但原路径被占用,或相关文档有未保存修改时,历史操作会停止并提示原因,保留可重试的记录。
  • 文件树撤销或重做某项失败时,弹窗显示失败项目的相对路径和原因,并提供取消、重试、跳过。默认聚焦取消;取消保留当前进度,重试只重试该项,跳过只移除该项的历史记录并继续同组的其余项目。
  • Windows 通过系统 Shell 回收站接口定位和恢复项目,不依赖 PowerShell;回收站记录中的中文路径经 URI 编码传递,并将原目录规范化后匹配。定位时还核对删除前后的卷与文件 ID,避免将其他进程删除的同名项目记入撤销历史;无法确认身份时不创建撤销记录。中文名称和短路径目录中的项目也可获得撤销所需的回收站记录。
  • 删除、撤销和重做会输出 [mynote:tree:renderer] 与 [mynote:tree:main] 诊断日志,记录操作路径、各阶段耗时 stageMs 和累计耗时 elapsedMs。主进程日志细分系统回收站、工作区扫描、大纲索引和快照;Windows 还细分删除后的回收站查询、系统删除与恢复。可分别在开发者工具控制台和启动应用的终端查看。
  • 复制不会立即改变文件树;剪切条目以半透明显示,粘贴完成后恢复。可在任意文件或文件夹节点粘贴:文件以其父文件夹为目标,文件夹以自身为目标。
  • 混选时剪切、复制、粘贴、拖动和回收站操作处理整组选项;同时选中父文件夹与子项时只操作父文件夹。粘贴目标由当前焦点项决定。重命名、收藏等单项操作仅在选中一项时可用。
  • 选中文件夹表示操作整个磁盘目录,包括界面筛选隐藏的文件、隐藏文件和非 Markdown 文件;复制目录仍沿用跳过符号链接的规则。批量操作逐项执行,失败后停止并报告完成数量,已完成结果保留;剪切粘贴失败时可重试尚未移动的项目。
  • 条目也可拖到文件树根部;拖拽目标用不同强调色显示移动或复制,并在鼠标释放时以窗口级主修饰键状态决定操作。
  • 新建和重命名使用应用内输入对话框,避免依赖 Electron 不可靠的浏览器提示框。
  • 目标同名、移动到自身内部、符号链接操作或路径越界时拒绝操作。移动和重命名会保留已打开标签中的未保存修改,并同步迁移标签标题、路径、正文基线和文件监听,不触发外部删除恢复提示。
  • 移动或复制文档时,调整常见 Markdown 图片相对路径。
  • 文件树右键菜单支持从当前选中文件循环遍历上一个或下一个文件,默认快捷键为 Alt+PageUp / Alt+PageDown;
    • 遍历顺序与文件树一致,首尾折返,修改时间过滤隐藏的文件不参与,并在启用预览编辑器时通过预览方式打开目标文件。
    • Windows 会阻止关闭 NumLock 后的小键盘 PageUp/PageDown 被系统同时解释为 Alt 数字码,连续遍历不会向编辑器插入字符。
  • 文件树条目和已保存文档的 Tab 上下文菜单支持“在文件管理器中显示”;默认快捷键为 Shift+Alt+R,也可从命令面板执行。

路径与引用

  • 文件树右键菜单支持复制文件或文件夹的系统绝对路径与笔记库相对路径,并显示当前生效的可配置快捷键。
  • 默认按 Shift+Alt+C 复制路径;按 Ctrl+K Ctrl+Shift+C(macOS 为 Cmd+K Cmd+Shift+C)复制相对路径。
  • 已保存的仓库内 Markdown 标签及文件树 Markdown 文件支持“复制引用”和“复制引用(大纲)”;后者默认按 Ctrl+Alt+C(macOS 为 Cmd+Alt+C)触发。
  • “复制引用”始终生成指向文件顶部的 Markdown 链接。
  • “复制引用(大纲)”对已打开文件使用其保留的 caret,并在片段中保留中文等非 ASCII 字母与数字,以便直接阅读。
    • 文件未打开、caret 位于首个标题之前或没有标题时,退化为文件引用。
  • 文件引用格式为 [文件名](/仓库路径.md),大纲引用格式为 [大纲标题](/仓库路径.md#标题锚点);两者使用仓库根相对地址,可粘贴到仓库任意目录。库外文件的标签页只提供绝对路径。

删除与未保存保护

  • 支持将文件或文件夹移入系统回收站。
  • 批量移入回收站先统一确认一次;确认后检查所选目录,只有发现文件树未显示的文件(含非 Markdown 文件等)时才二次确认。取消任一确认都不会删除项目。
  • 文件树获得焦点时,按 Delete 可将所选文件或文件夹移入系统回收站;取消确认后即使文件树期间发生重绘也会恢复原条目焦点,确认删除后焦点仍留在文件树,并同时关闭对应的已打开标签。
  • 有未保存文档时,仍阻止删除对应文件和父文件夹;移动和重命名会保留未保存正文并更新标签路径。
  • npm run test:smoke:tree-multiselect 验证混选、整组操作、隐藏内容与符号链接范围,以及批量失败后的剩余项目。

6.4 查找、最近文件与收藏

全文搜索与替换

  • 支持按文件名和正文搜索。
  • 正文搜索结果显示命中片段。
  • 使用 Ctrl+Shift+F(macOS 为 Cmd+Shift+F)显示侧边栏并聚焦全文查找。
  • 使用 Ctrl+Shift+R(macOS 为 Cmd+Shift+R)展开全文替换并聚焦替换输入框。
  • 使用 Ctrl+H(macOS 为 Cmd+Option+F)在编辑区展开当前文件替换;可替换当前匹配或一次替换全部匹配,并沿用大小写和全字匹配选项。
  • 当前文件替换展开时,Tab 从查找内容依次进入替换内容、查找选项和替换操作;Shift+Tab 按相反顺序移动。
  • 焦点位于替换内容输入框时,按 Enter 替换当前匹配并保持输入焦点,可连续按 Enter 逐个替换。
  • 焦点位于替换内容输入框时,Windows/Linux 按 Ctrl+Alt+Enter、macOS 按 Cmd+Enter 可替换当前文件中的全部匹配。
  • 全文替换与查找共享大小写和全字匹配选项,仅修改 Markdown 正文,不更改文件名。
  • 全部替换前显示影响文件数和替换数并要求确认;命中文件存在未保存修改时会阻止写盘。
  • 全部替换使用原子写盘,保留 UTF-8 BOM 和 LF/CRLF 换行格式,并同步刷新已打开文件、搜索标签页和大纲索引。
  • 单击侧栏搜索结果时使用预览标签打开,后续结果会复用同一个预览位置。
  • 侧栏搜索结果可通过搜索框旁的“在编辑器中打开”按钮生成只读搜索标签页。
  • 全库搜索内容、大小写和全字选项按笔记库保存;切换笔记库时清除旧结果并恢复目标笔记库的搜索状态。
  • 搜索标签页按文件列出全部匹配行,默认显示每个匹配前后各一行上下文,并可随时隐藏或恢复上下文行。
  • 搜索标签页高亮所有源码匹配位置,包括同一行的多次命中;查询或上下文状态改变后更新高亮,滚动时保持对齐,且不妨碍文本选择和页内查找。
  • 搜索标签页顶部可直接修改查询,输入停止 200 毫秒后动态刷新当前标签页的结果和标题,并保留上下文显示状态。
  • 搜索标签页支持编辑区内查找;双击文件标题、匹配行或上下文行可打开源文件并定位。
  • “聚焦下一个搜索结果”命令(search.action.focusNextSearchResult)默认绑定 F4,可在快捷键设置中自定义。
    • “聚焦上一个搜索结果”(search.action.focusPreviousSearchResult)默认绑定 Shift+F4,同样支持自定义快捷键,并沿用相同来源与位置指示。
    • 最近一次侧栏结果单击或搜索结果页双击决定导航来源;跳转源文件后继续沿用该来源。
    • 两种来源都按每一处正文匹配遍历,同一文件的多行匹配和同一行的多次匹配均逐项访问。
      • 侧栏仅路径匹配的文件算一条;结果页跳过文件标题和上下文行。
    • F4 从记录的位置前进,末尾循环到首条;Shift+F4 后退,首条循环到末条;打开源文件预览,两种来源都会定位并选中命中内容。
    • 侧栏突出当前文件并显示结果序号、总数及源文件行列;结果页工具栏显示相同位置信息,并突出当前匹配。
      • 指示保留在原来源中,返回结果页时可查看当前项;刷新后清除失效位置。
    • 首次使用优先取当前结果页,否则取侧栏结果;没有可用侧栏结果时可使用其他打开的搜索结果页。
    • 刷新后按文件路径、行号和列号重新定位;原位置消失或首次使用时,前进从首条开始,后退从末条开始。
    • 来源关闭或无结果时依次退回当前结果页、侧栏和其他打开的结果页;全部为空时不执行。
    • 保留现有单击、双击行为;双击标题或上下文后的下一步仍只遍历正文匹配。
  • 搜索标签页是当前会话内的静态快照,不会作为 Markdown 文件保存,也不会在重启后恢复。

搜索边界与结果页

  • 全文搜索匹配仓库相对路径和 Markdown 正文,不区分大小写;超过 2 MB 的文件仍可打开,但跳过正文搜索。每次最多返回 100 项,文件内容按修改时间和大小缓存。
  • 搜索结果区域在零条或单条结果时仍保持可用高度;长路径和片段省略显示,不产生横向滚动。搜索框在窄侧栏中收缩到可用宽度。
  • “在编辑器中打开”每次创建独立的只读搜索快照。
    • .code-search 文本显示查询、结果和文件统计、文件分组及源码行号。
    • 匹配行用 :、上下文行用 -;相邻命中的重叠上下文只显示一次。
  • 从全文搜索打开结果页时继承大小写和全字匹配选项;结果页可独立调整。全文搜索的选项同时作用于路径与正文,结果页改动查询时会同步更新源码跳转映射。
  • 搜索结果页最多覆盖 100 个文件和 10,000 个匹配行;达到限制时显示截断提示。仅路径匹配或正文因体积跳过的文件仍可列出并打开。
  • 结果页双击匹配行时,会在源码中选择仍位于记录位置的首个匹配。
  • CodeMirror 报告页通过外部正文替换更新查询,匹配范围使用 decorations。
    • 键盘、粘贴、图片插入和替换命令不能修改报告正文。
    • 迁移记录见 CodeMirror 迁移。
  • 搜索栏、搜索结果页、编辑区和预览区的当前文件查找栏均提供 Aa(区分大小写)与 Ab(全字匹配)开关。
  • 编辑区页内查找条件变化后,当前匹配已完整显示在视图中时保留滚动位置;匹配在视图外时滚动定位。
    • 也可按 Alt+C、Alt+W 切换,只更新当前栏的选项和结果。
    • 全字匹配要求查询前后不紧邻 Unicode 字母、组合标记、数字或下划线。
      • 例如 cat 不匹配 scatter、cat2 或 cat_。
  • 聚焦全文搜索输入框时按 Alt+Enter 可在编辑器打开结果;查询为空或正在打开结果时不会重复执行。通过快捷键重新聚焦页内或全文查找时,不超过 200 字符的单行选区会带入查询框。
  • 页内和全文查找各自保存最近 50 条去重历史;输入停止 300 毫秒后记录,↑ 和 ↓ 可回看。
    • 历史位于 Electron userData/Local Storage。
    • 键名分别为 mynote.page-find-history.v1 和 mynote.workspace-search-history.v1。
  • npm run test:smoke:workspace-search 覆盖真实渲染器中的全文查找与替换、结果页、写盘、打开文件刷新和恢复原文。
    • 同时覆盖 F4 与 Shift+F4 的两种来源、连续前进、后退与循环、结果刷新、来源关闭与空结果回退,以及自定义快捷键。
    • 验证两种来源的当前位置指示,以及同一文件多行和同一行多次匹配的逐项遍历。

最近文件与收藏

  • 支持最近文件、文件收藏和大纲收藏;大纲面板中每个标题右侧的星标及大纲右键菜单可收藏或取消收藏该标题。
  • 每个笔记库最多保存 20 个最近文件和 100 个文件或大纲收藏,收藏记录包含类型、路径、定位信息及毫秒时间戳。
  • outline.toggleFavorite 命令可从命令面板执行,默认按 Alt+F 切换光标或大纲焦点所属标题的收藏状态;光标位于首个标题之前时不执行收藏。
  • 收藏记录类型、所属文件、大纲身份、收藏时的位置和收藏时间。
    • 打开收藏时,先按最新正文中的标题、层级和同名序号动态计算大纲行号。
    • 精确身份失效时,直接跳转到收藏时记录的源码行,不会猜测附近标题。
    • 收藏目标会覆盖标签页原有阅读位置;预览渲染完成后不会跳回旧位置。
    • 默认按文件组织;同一文件的大纲收藏按文档顺序缩进展示在文件下。
  • 每次打开收藏区“整理”都会先把所有精确匹配大纲的最新行号自动写回收藏,再列出无法精确匹配的失效收藏;
    • 已打开文档使用包含未保存修改的最新正文,其他文档读取磁盘内容。
    • 大纲使用与编辑器章节高亮相同的归属规则:记录行不是标题时取其前方最后一个、也就是当前最深层的所属标题;
    • 记录行位于首个标题之前或文件无法读取时只能取消收藏。
    • 可逐项或勾选、全选后批量更新,更新会写入重新计算的 title、层级和同名序号并保留原收藏时间;
    • 更新到已有收藏身份时自动移除失效的重复项。
  • 整理列表支持双击详情跳转,跳转前关闭面板且不让焦点恢复覆盖目标位置;outline.organizeFavorites 命令仅在当前笔记库有大纲收藏且没有模态窗口时可用,可自定义快捷键。
  • 收藏区“时间”按钮按“时间降序 → 时间升序 → 按文件组织”循环切换,首次点击优先显示最新收藏;时间方向和文件组织状态统一写入仓库 UI 数据并按笔记库恢复。
  • 按时间展示收藏时,首行显示文件名或大纲标题,第二行统一显示仓库相对路径和收藏时间;大纲收藏前显示不受样式表字符集影响的箭头标记。

文件快速打开

  • Ctrl/Command+P 打开文件快速打开面板;普通查询按文件名或相对路径模糊、多词匹配,空查询优先显示最近文件。标题查询与限定语法见大纲快速打开。
  • 输入中未闭合的限定值引号按当前内容即时匹配;文件名、标题和路径中的匹配字符以亮蓝色粗体标出,全拼和拼音首字母命中时高亮对应汉字。
  • 面板支持方向键、Enter 和 Escape;确认打开时保存非空查询,最近 50 条去重历史保存在本机 Local Storage。历史快捷键可配置,普通 ↑↓ 仍选择结果。
  • 关闭 Quick Open 会恢复原 CodeMirror 或输入框的焦点、光标、选区方向和编辑器滚动位置。
    • 确认结果时,先恢复输入位置,再由目标打开或跳转设置新位置。
    • 输入法组合期间,Enter 与方向键仍交由输入法处理。
  • 使用方向键切换结果不会带动编辑器或预览滚动。
  • 工作区状态保存在 Electron userData/workspace-state.json,使用原子写入;笔记正文和附件仍在用户选择的普通文件夹中。
  • 顶层 localSettings 保存仅本机使用的配置,其中所有值均不参与账号偏好同步。
    • 热键总开关使用 localSettings.hotkeysEnabled,默认启用。
    • 不读取或迁移旧位置的开关值。
    • 设置层统一负责本地配置的加载、保存及窗口间广播;快捷键文件模块只读取开关并应用热键注册。
    • 初始化、对话框修改和其他窗口的本地设置广播,均通过 applySettings 更新 runtime store。
    • 热键对话框与 Quick Cmd Form 的 h 命令直接调用 WorkspaceStateStore.updateLocalSettings,复用现有设置队列及 save();保存失败时保留开关及热键注册状态。
    • IPC 只订阅已提交的本地设置变更并广播,不维护额外保存函数或队列。

6.5 失效链接检查

  • 侧边栏“检查链接”可批量扫描当前仓库中已保存的全部 Markdown 文件;同一功能也作为 workspace.checkBrokenLinks 命令显示在命令面板和快捷键设置中。
  • 检查普通 Markdown 链接、图片、引用式链接以及原始 HTML 的 href / src,并忽略代码围栏和行内代码中的示例文本。
  • 检查相对路径、仓库根相对路径、URI 编码路径、Markdown 标题锚点和原始 HTML 的 id / name 锚点。
  • 报告区分目标不存在、目标无法读取、标题不存在、路径越界和符号链接逃逸,并高亮失效目标;双击文件标题或问题行可打开源文件并定位到对应行。
  • 报告使用只读临时标签页,同一窗口内再次检查会刷新原报告,不创建重复标签;报告不会进入会话恢复记录。
  • 检查以磁盘中已保存的正文为准;存在未保存编辑时,应先保存再运行以获得最新结果。
  • HTTP、HTTPS、邮件和其他带协议的链接不会发起网络请求,统一计入报告中的“已跳过外部链接”。
  • 单次最多显示 10,000 个失效链接;达到上限时报告会明确标记结果已截断。

引用查找

  • 标签、文件树 Markdown 项和命令面板提供“查找文件引用”“查找当前标题引用”。
    • Shift+F12 查找光标所属标题;光标位于首个标题之前、没有标题或文件未打开时回退为文件查找。
    • 未保存新文档、库外文件、文件夹和搜索报告不提供此命令。
  • 扫描当前仓库文件清单中的 Markdown;文件查找包含指向任意标题的链接,标题查找只统计解析到该标题的链接,包括同文件锚点、中文与编码地址、重复标题的唯一锚点。
  • 支持 Markdown 行内链接、引用式链接和 HTML href;不统计图片、外部 URL 或代码中的链接。已打开文件使用未保存正文,其余文件读取磁盘,不强制保存。
  • 复用独立只读的“引用查找”标签,按文件展示引用次数、行号和源码片段,同一行的多个引用分别计数。单击不跳转,双击跳到来源行并支持前进、后退;“刷新引用”重新读取内容,结果不会随输入自动更新。
  • 最多返回 10,000 处引用并在超限时提示截断;单文件读取失败后继续扫描并标明结果不完整。关闭报告、切换仓库或开始新查询后,旧请求不会覆盖当前报告。
  • 引用查找结果页支持 F4 下一处、Shift+F4 上一处,首尾循环;文件标题不参与遍历,同一行的多个引用逐项访问。
    • 双击引用行后继续从该引用遍历;跳到源文件后保留引用页作为导航来源,已有未保存内容保持不变。
    • 工具栏显示当前序号、总数和来源位置,并高亮当前引用;刷新、关闭或空结果沿用搜索结果页的定位与回退规则。
    • 引用跳转保持定位到来源行,不选择链接文本。
  • npm run test:smoke:references 验证引用查找及失效链接报告流程,并覆盖引用结果的双向遍历、循环、重复引用及刷新。

6.6 仓库详情

  • View 菜单的“用 VS Code 打开当前仓库”会新建 VS Code 窗口打开当前仓库根目录,不沿用现有窗口;切换仓库后使用新的仓库路径。
  • “用 VS Code 打开当前仓库”作为 workspace.openInVSCode 命令显示在命令面板和快捷键设置中。
    • 默认快捷键为 Alt+Shift+V,可修改或添加多个自定义快捷键。
  • 此功能需要安装 VS Code 并注册 vscode:// 协议,无需配置 code 命令的 PATH;未打开仓库或系统报告启动失败时显示错误提示。
  • 侧边栏“刷新”旁提供“仓库详情”入口。
  • “仓库详情”后提供当前仓库的同步快捷按钮;同步期间按钮显示加载状态并禁止重复操作,完成后通过非阻塞通知反馈结果。
  • “切换仓库后仍自动同步”和“安全的自动同步”两个独立仓库级开关位于侧边栏仓库操作区,无需打开同步中心即可配置。
  • 仓库详情显示以下信息:
    • 当前仓库的本地名称与路径;
    • 同步身份与账号;
    • 本地和远端 Markdown 数量;
    • revision 与 cursor;
    • 同步状态和时间。
  • 可为本地仓库设置独立的显示名称;侧边栏、最近仓库和仓库详情统一使用该名称,磁盘上的根目录文件夹名与路径保持不变。
  • 修改仓库名称时保留以下数据:
    • .mynote 元数据;
    • 最近文件;
    • 收藏;
    • 后台同步设置;
    • 已打开标签。
  • 可在应用内二次确认后,将当前仓库从最近仓库列表中移除。
  • 移除仓库时删除根目录下的 .mynote 元数据文件夹,但不删除 Markdown 等笔记文件。
  • 若元数据删除失败,仓库保留在列表中以便重试。
  • 大纲索引保存在 .mynote/outline-index-v1.json,记录文件修改时间、大小、标题层级和源码行号。
  • 启动或切换仓库后在后台按修改时间增量校验大纲索引;侧栏“重建索引”可强制重新解析全部受管理 Markdown。
  • 普通刷新也会按文件修改时间和大小增量校验索引;后台变化会原位刷新已打开的全库大纲查询并尽量保留选中项。损坏或未知版本的索引会保留诊断副本后重建;该缓存可删除、可重建,不参与同步。
  • 本地目录不存在时通过非阻塞通知明确提示。
  • 本地目录不存在时移除对应的最近仓库记录。
  • 不继续读取失效仓库的同步状态。
  • 失效仓库处理不会影响 Windows 仓库下拉框继续操作。
  • 仓库 ID 不属于当前账号与服务地址时明确提示,不继续读取失效身份的同步状态。

6.7 仓库切换与同步缓存

  • 成功克隆仓库后,同步中心自动关闭。
  • 克隆完成后,以非阻塞通知显示克隆位置。
  • 克隆完成后,将焦点移到仓库下拉框,避免 Windows 原生对话框阻止仓库选择器展开。
  • 同步客户端缓存按路径、账号或服务、设备和仓库 ID 隔离。
  • 仓库身份变更后,不会把旧仓库的 cursor 或状态显示到新身份上。
  • 读取仓库详情期间身份发生变更时,明确报告错误。

6.8 基础设置

  • 设置编辑器字号。
  • 字号范围为 12–24 px;笔记库 Markdown 文件上限也可在设置中调整。
  • 设置单击文件时是否启用预览标签;关闭后文件树与搜索结果单击均直接打开普通标签。
  • 搜索标签页的临时面板布局不会覆盖按笔记库保存的侧栏、大纲和按文档页面保存的视图选择。
  • 可设置外部冲突工具的可执行文件绝对路径和参数模板;模板支持 %local、%remote、%base、%merged,替换后作为独立参数直接启动,不经过 shell。
  • macOS 上的 Beyond Compare 应使用 /Applications/Beyond Compare.app/Contents/MacOS/bcomp。
    • 已有配置指向同目录 BCompare 时会自动改用 bcomp。
  • 普通设置跨窗口共享并在保存后立即应用;取消或按 Escape 丢弃未保存的表单修改。设置窗口保持打开时,后台刷新或其他窗口保存不会覆盖当前表单。

7. Markdown 编辑与预览

7.1 编辑与渲染

选区与编辑命令

  • 在可编辑 Markdown 文档中选中文字后,编辑区选区旁显示悬浮格式工具条;取消选区、切换标签、隐藏编辑区或进入只读状态时关闭。
    • 工具条优先显示在文字上方;靠近编辑区顶部、上方空间不足时显示在文字下方,避免遮挡标签栏。
    • 编辑器聚焦且有文字选区时,按 Esc 取消选择,光标保留在选区的活动端,编辑器保持聚焦;只读文档也支持。
  • 工具条提供正文及 1–6 级标题、引用、列表、粗体、斜体、删除线、链接、行内代码和代码块。标题只处理单行;引用和列表处理选中的完整逻辑行;行内格式再次点击可移除标记。
  • 链接通过应用内对话框填写链接文本和地址,打开时默认聚焦并选中链接文本。
    • 普通选区自动回填文本;选中 URL 时也回填地址。
    • 选中完整 Markdown 行内链接、其文字或地址时,自动回填原有文本与地址并替换原链接。
    • 选区附带的空白和换行留在链接之外。
    • 格式修改参与文档撤销、未保存状态和实时预览更新。
  • 选区格式操作也可从命令面板执行,并在快捷键设置中自行绑定。
    • 列表和代码块沿用已有命令,其余操作提供独立命令。
    • “插入链接”在可编辑 Markdown 文档中始终显示;无选区时可手动输入文本和地址并在光标处插入。
    • 其他新增格式命令需有选区;已有的列表命令仍可处理光标所在行。
  • “修改错别字”命令 editor.proofreadSelection 可从 Edit 菜单或命令面板执行。
    • 命令将当前选中文本发送给 DeepSeek,修改错别字并补充必要的标点符号。
    • 返回结果有变化时,应用逐行和行内差异高亮的确认弹窗;用户确认后才替换原选区。
    • 返回结果没有变化时只显示通知,不打开弹窗。
    • DeepSeek 响应前原文已发生变化时不会覆盖新内容。
  • “切换列表”命令 editor.selectionToList 有选区时处理选中的完整逻辑行,无选区时处理光标当前行。
    • 目标行全部带 - 时统一移除,否则为未带标记的行补上 - 。
    • 默认快捷键为 Alt+Shift+L,Edit 菜单同步展示,可在快捷键设置中修改。
  • “插入 fenced code”命令 editor.wrapFencedCode 可从 Edit 菜单或命令面板执行,默认无快捷键。
    • 只包裹选中文字,必要时补齐围栏前后的换行;内容含反引号时自动使用更长的围栏。
    • 无选区时在光标处插入空代码块,并将光标置于围栏内。
    • 操作后保留原文选区,支持一次撤销;只读文档不可执行。
  • “整体提升大纲级别”和“整体降低大纲级别”命令可从 Edit 菜单或命令面板执行:
    • 命令 ID 分别为 editor.promoteHeadingLevels、editor.demoteHeadingLevels。
    • 两者处理选区触及的完整逻辑行,将其中每个 Markdown 标题整体升降一级。
    • 选区内存在一级标题时不执行整体提升,存在六级标题时不执行整体降低,避免部分修改标题层级关系。

路径代码片段

  • Quick Cmd Form 的 Code Snippet Paste 可将来源选区直接采集为此格式,随后使用同一组检查、整理和比较命令。
  • 从 Edit 菜单、命令面板执行以下命令;默认无快捷键,可在快捷键设置中绑定。
    • editor.checkCodeSnippets:检查代码片段。
    • editor.collateCodeSnippets:整理代码片段。
    • editor.compareCodeSnippets:比较代码片段。
  • Edit 菜单“比较代码片段”下方提供“插入代码片段注释标示”,命令面板使用同名命令 editor.insertCodeSnippetComment。
    • 默认快捷键为 Alt+I,可在快捷键设置中修改。
    • 在当前光标位置依次插入 //.,,、一个空格和一个换行符,光标移到换行之后;有选区时在选区的光标端插入,保留选中文字。
    • 仅在可编辑的 Markdown 笔记且没有打开对话框时可执行;一次撤销可恢复插入前的内容。
  • 使用反引号围栏,路径紧接在开始围栏后,正文从下一行开始。
    • 示例:开始行为 ```C:\Users\Administrator\AppData\Local\Temp\file-sizes.txt,结束行为 ```。
    • 路径可以包含空格、中文;支持绝对路径,以及 ./、../ 或含目录分隔符的相对路径。
    • 相对路径以当前笔记目录为基准,未保存笔记需要先保存才能使用相对路径。
    • 无目录的相对文件名请写成 ./file.txt,避免与普通代码块语言标签混淆。
    • 仅处理顶层路径代码块;列表、引用中的围栏和普通语言代码块不参与操作。
    • 不识别旧的 <--cs_begin/--cs_end> 外层格式,不自动转换旧笔记。
  • 内部标记沿用 FindHelper 的规则。
    • 单独一行 <===cs_sep===> 分隔同一文件的多个片段。
    • 包含 //.,, 的整行不参与源码匹配或比较,整理时保留并随所属片段移动。
    • 其他行仍按源码处理,注释标记不会让后续整段内容变成注释。
  • 检查和整理在有选区时只处理完整位于选区内的代码块;无选区时处理全文。
    • 源文件按 UTF-8 读取,匹配前统一换行并去除各片段首尾空白。
    • 每段必须在源文件中完整出现;失败时选中并滚动到对应片段,显示原因。
    • 文件缺失、读取失败、路径代码块未闭合或没有可处理代码块时显示提示。
  • 整理先完成全部检查,再按解析后的路径合并同文件片段。
    • Windows 路径分组不区分大小写;其他平台按大小写区分。
    • 按源码首次匹配位置稳定排序,使用内部分隔符连接;同组沿用首个代码块的路径写法。
    • 整理结果放在第一个被处理代码块的位置,其他笔记文字保持原样。
    • 正文含反引号时自动加长围栏,避免截断代码。
    • 一次撤销可恢复整个整理操作;只读文档不可整理。
    • 等待期间切换文档、变更路径或正文后,放弃过期结果并提示重试。
  • 比较处理光标所在的路径代码块,不要求片段与源文件一致。
    • 排除内部标记后将片段正文写入保留源文件扩展名的 UTF-8 临时文件,复用 VS Code 文件比较能力。
    • 不修改源文件;VS Code 不可用时显示错误。
    • 临时文件保存在应用用户数据目录的 code-snippet-diffs 子目录,下次应用启动时清理。
  • 预览标题显示完整文件路径,保留代码显示和复制按钮;预览本身不会读取源文件。

编辑器右键菜单

  • 正文编辑器支持鼠标右键菜单,也可在编辑器聚焦时按 ContextMenu 或 Shift+F10 打开。
    • 鼠标打开时菜单显示在点击位置附近。
    • 键盘打开时菜单显示在当前光标附近。
    • 菜单位置自动限制在窗口可视范围内。
  • 标准编辑操作包括撤销、重做、剪切、复制、粘贴、粘贴为纯文本和全选。
    • 撤销与重做使用当前标签独立的 CodeMirror 历史。
    • 有选区时,剪切和复制处理选中文字。
    • 无选区时,剪切和复制沿用快捷键行为,处理光标所在的完整逻辑行。
    • 空文档禁用剪切、复制和全选;没有对应历史时禁用撤销或重做。
    • “粘贴为纯文本”只读取剪贴板文本,在菜单打开时的选区插入,不转换 HTML,也不下载图片。
  • Markdown 操作包括粗体、斜体、删除线、链接、行内代码、引用、列表和代码块。
    • 粗体、斜体、删除线、行内代码和引用需要选区。
    • 链接、列表和代码块可在没有选区时使用;链接打开应用内链接对话框,列表处理当前行,代码块在光标处插入空围栏。
    • 操作复用选区工具栏的转换规则,并保留菜单打开时的选区;正文在执行前发生变化时不会套用过期操作。
  • “下载外部图片”处理选区内的 HTTP/HTTPS Markdown 图片;没有选区时处理当前文档的全部外部图片。
    • 重复地址只下载一次,成功的图片保存到文档同级 assets/ 并替换对应地址;失败的地址保持原样。
    • 进度显示已处理、总数、成功和失败数量。“终止”会停止当前请求及后续下载,保留已完成的结果。
    • 结束时提示成功、失败和未处理数量。任务期间文档变化时,不覆盖新正文。
  • 编辑器右键菜单提供“清理资源”,仅对已保存到当前笔记库的可编辑 Markdown 笔记可用。
    • 有正文选区时,只清理引用语法完整位于选区内的资源;无选区时,清理当前文档引用的全部资源,不扫描未引用附件。
    • 使用当前编辑器内容,包含尚未保存的修改;引用式链接可使用选区外的全文定义。
    • 支持图片、音频、视频、普通附件链接和 HTML 媒体引用;代码中的伪引用不会作为资源处理。
    • 仅处理笔记库内现存的非 Markdown 附件文件,跳过网络地址、库外路径、目录、保留目录和符号链接附件。
    • 同一资源的重复引用只处理一次;清理前通过应用确认弹窗列出数量和相对路径,取消不会删除资源。
    • 资源移入系统回收站,正文引用保持不变;共享资源也会删除,其他笔记中的引用将失效,确认弹窗会说明这一点。
    • 确认期间正文、文档路径或笔记库变化时取消操作,需重新执行;没有可清理资源时显示提示。
    • 一次清理作为一组文件树撤销/重做历史,编辑器撤销仍仅处理正文修改。无法定位系统回收站记录的资源不能通过文件树撤销恢复。
    • 部分失败时列出完成数量、失败路径和原因,成功项仍可撤销。
  • 只读编辑器仍可打开菜单,并保留复制和全选。
    • 撤销、重做、剪切、粘贴、粘贴为纯文本及全部 Markdown 操作均禁用。
  • 菜单中的粘贴调用 Electron 原生编辑命令,并继续进入现有编辑器粘贴事件链。
    • 剪贴板含 HTML 时,按标题、段落、强调、链接、列表、引用、代码块、表格和图片等规则转换为 Markdown;纯文本中的 HTML 标签保持原样。
    • 每次粘贴检查“不转换 HTML 的剪贴板类型”列表,匹配任一类型且有非空纯文本时,优先粘贴原始纯文本,保留代码缩进、换行及 Markdown 语法,不转换高亮 HTML 或导入图片。
      • 所有用户默认包含 vscode-editor-data,未配置此列表的现有用户也使用该默认值。
      • 设置页支持每行填写一个类型,可添加、删除或清空列表;清空后取消过滤。
      • 来源标记存在但没有非空纯文本时,仍沿用 HTML 与图片粘贴流程。
      • 无法识别来源的 IDE 可使用右键菜单中的“粘贴为纯文本”。
    • HTML 同时含正文和图片数据时优先保留完整正文;没有有效 HTML 时沿用单图粘贴。应用内跨目录 Markdown 图片路径调整保持原有行为。
    • HTML 中的 HTTP/HTTPS 图片与 data:image 图片会尝试保存到当前文档同级的 assets/,重复地址只保存一次;相对地址保持原值。
    • 每次粘贴最多导入 20 张图片,单张图片上限为 10 MB,网络请求 15 秒超时。
    • 图片下载失败时仍粘贴正文,保留失败图片的原地址并提示数量。未保存文档取消选择保存位置时,也会粘贴正文并保留图片原地址。
    • 默认在每次 HTML 粘贴转换时显示 Toast:“检测到 HTML 格式内容,正在尝试转换为 Markdown。”
      • 每次粘贴都检查当前用户配置;普通文本、IDE 原文及应用内 Markdown 粘贴不显示此提示。
      • 点击 Toast 或其下方的“查看更多”按钮,打开自定义确认对话框,选择“不再提示”“继续提示”或“转到设置”。
      • “禁用转换”关闭 HTML 自动转换,从下次粘贴起优先保留纯文本,不再显示转换提示。
      • 设置页提供默认启用的“启用 HTML 转 Markdown”,可重新开启自动转换;该开关与提示开关独立。
        • 取消勾选时,下方的转换提示开关和类型过滤列表立即禁用并变灰;重新勾选后恢复可编辑。
        • 禁用不会清空提示偏好或类型列表,取消设置修改后恢复已保存的状态。
      • 禁用转换后不导入 HTML 内嵌图片;纯图片剪贴板仍沿用图片插入流程。
      • “转到设置”打开设置页并聚焦“粘贴 HTML 时显示转换提示”,该选项默认启用,可重新开启或关闭。
      • 提示偏好保存在本机应用配置中,跨窗口生效,重启后保留;不影响 HTML 自动转换与图片处理。
      • 对话框为当前剪贴板中除 text/plain、text/html 外的每个附加类型分别显示“该类型不转换”按钮;浏览器的 Files 条目指示器不作为类型选项。
      • 点击类型按钮将其追加到过滤配置中,不关闭转换提示;从下次粘贴起生效,多个窗口同时追加也保留各自的选择。
      • 图片下载失败仍显示独立的失败提示,并保留原地址。
    • HTML 粘贴作为一次编辑,可用标准撤销与重做快捷键恢复。
    • 实现调用链与边界见 HTML 粘贴与图片本地化实现。
  • 菜单打开后自动聚焦第一个可用操作。
    • ↑、↓ 在可用操作间循环移动。
    • Home、End 分别移动到第一个和最后一个可用操作。
    • Enter 或空格执行当前操作。
    • Escape 或 Tab 关闭菜单并恢复编辑器焦点和选区。
  • 点击菜单外部、滚动编辑器、切换标签、调整窗口大小或窗口失焦时关闭菜单。

Markdown 渲染

  • 在编辑区输入 Markdown 时实时刷新预览。
  • 支持 GitHub Flavored Markdown。
  • 源码中的换行会显示为预览换行。
  • 支持标题、列表、引用、代码块、表格、链接和图片等常用 Markdown 内容。
  • 带语言标识的预览代码块使用 Highlight.js 完整内置语言及别名目录进行语法高亮;未标识语言时自动识别,无法识别或显式语言未知时安全显示为纯文本。
    • 路径代码块优先用文件扩展名匹配语言及别名,例如围栏后的 E:\uninote\mynote-client\src\main\quick-cmd-form.ts 识别为 ts,正文只有 ... 时也适用。
    • 预览顶部同时显示识别出的类型和完整路径;无法匹配扩展名时保留正文自动识别及路径显示。
  • 预览中的 fenced code block 顶部展示语言类型,并提供复制纯代码文本的按钮;按钮会就地反馈复制成功或失败。
    • 仅主窗口预览页 fenced code 正文使用字体序列 Menlo, Monaco, Consolas, "Courier New", monospace;代码块工具栏、行内代码、缩进代码块、HTML 发布及文档导出沿用原有字体。
    • 英文、空格使用等宽字体;中文和框线字符的宽度取决于系统实际字体及回退字体,图示需按该字体的字符宽度排版。
  • 单个预览代码块超过 102,400 个 UTF-16 单元时跳过语法分析并保留代码展示,避免实时预览被超大代码块阻塞。
  • 支持 Mermaid 流程图等图表。
  • 使用 ```mermaid 围栏书写图表定义,预览区会实时渲染。
  • 流程图节点使用原生 SVG 文字,并按完整行宽度排版。
  • 窄预览区中的流程图支持横向滚动。
  • 长中文与无空格文件路径不会被截断或缩小。
  • Mermaid 语法错误会在图表位置显示提示。
  • Mermaid 会自动恢复由 display:none 隐藏路由节点引发的连线定位错误,并保持这些节点不可见。
  • 预览面板隐藏时会延后 Mermaid 的几何布局,重新显示后再渲染,避免应用重启恢复隐藏布局时出现连线定位错误。
  • 已完成的标签页预览会保留其 DOM;切换回未修改的标签时直接恢复原预览,避免 Mermaid 重绘造成闪烁和晃动。

7.2 链接

  • 编辑器源码中的链接支持使用 Ctrl+单击(macOS 为 Command+单击)激活。
  • 预览中的链接支持普通单击激活。
  • 跨文档标题链接在目标预览已缓存时仍会定位到对应标题。
  • 当前文档标题链接会跳到对应标题。
  • 相对 Markdown 链接会打开库内或当前文档旁的目标文件,并支持继续定位标题。
  • 源码链接会将目标行稳定定位到编辑区顶部,且不会被目标标签尚未完成的旧视图恢复覆盖。
  • Markdown 文件及标题链接跳转会加入编辑器导航历史。
    • Alt+Left 返回来源位置,Alt+Right 前进到最终文件与标题,不产生文件顶部的中间历史位置。
    • Windows 上完成上述导航后松开 Alt,焦点仍留在编辑区域,不会转移到原生菜单。
    • 历史位置通过正文行及相邻行锚点动态解析,目标前方发生编辑后仍能恢复正确位置。
  • HTTP、HTTPS、邮件和 Codex 链接在系统外部目标中打开,并使用安全的链接关系属性;其他协议不会执行。

Codex 深层链接

  • 编辑区和预览区都可激活 Markdown 链接或裸露的 codex:// 地址。
  • 链接经校验后交由系统协议处理器打开 Codex;在 Windows 上等同于在“运行”中输入并执行该地址。
  • 选中 codex:// 地址插入链接时,对话框会自动回填链接地址。

7.3 编辑器显示

  • 正文编辑器使用 CodeMirror 6,提供 Markdown 源码语法高亮、虚拟化渲染和每个标签独立的编辑历史。
    • 正文编辑器、行号、查找高亮层、链接定位层和差异视图沿用 "Cascadia Code", Consolas, monospace 字体序列。
    • 1–6 级标题使用分别配色且加粗的可区分标题样式,同时保持源码行高一致。
    • 带语言标识的围栏代码块按对应语言高亮。
      • 支持 JavaScript、TypeScript、Python、Java、C/C++、Go、Rust、HTML、CSS、JSON、SQL、Shell 等常用语言及其别名。
      • 路径围栏也可按文件名识别语言,例如 E:\uninote\mynote-client\src\main\quick-cmd-form.ts 使用 TypeScript 高亮,并按需加载语言模块。
  • 大文件正文超过 524,288 个 UTF-16 单元时暂停源码语法配色,缩小后恢复;正文与预览仍可使用。
  • 正文仍为普通 Markdown;预览仍走既有 Markdown 渲染链路。
  • 编辑命令通过 transaction 提交,外部整体重载清空历史,保存和切换标签保留历史。
  • 编辑区查找、报告命中、标题区间和差异行使用编辑器装饰层。
  • 编辑区左侧显示源码行号。
  • 输入、切换文档和纵向滚动时实时同步行号。
  • 长行保持为单行并可横向滚动,确保行号与源码行准确对齐。
  • 编辑区正文使用文本插入光标,横向和纵向滚动条及其交角使用常规箭头光标。
  • 使用清晰的蓝色背景和左侧强调线高亮光标当前行,行号区域同步高亮;当前行位于所属章节底色内时仍优先显示,并在移动光标、滚动和切换文档时保持准确定位。

7.4 页面内查找

  • 编辑区和预览区均支持类似 VS Code 的页面内查找。
  • Ctrl/Command+F 在最近使用的内容区打开浮动查找栏。
  • 聚焦查找框时保留当前阅读位置。
  • 每次重新聚焦编辑区查找框,都会按编辑器当前 caret 重新计算当前匹配序号,不移动 caret 或滚动位置。
  • 编辑区查找框文本变化时,也会按当前 caret 重新计算匹配序号。
  • F3 / Shift+F3 每次从最新 caret 或选区重新计算目标匹配。
  • 查找栏显示当前匹配序号和总匹配数,并支持循环定位;编辑区切换到已完整显示在当前视图中的上一个或下一个匹配时保持滚动位置不变。
  • 预览查找框保持打开且存在结果时,继续编辑会刷新结果高亮,同时保留编辑区和预览区的当前滚动位置。
  • 编辑区与预览区均以深色文字高亮全部搜索结果,并以独立颜色突出当前匹配;焦点离开查找框后继续保留高亮。
  • 编辑器使用醒目标记持续显示当前结果,并准确跟随中英文混排内容。
  • 导航结果或缩放页面时,自动横向和纵向滚动以露出完整命中词。
  • 使用 Enter、Shift+Enter 或 F3 前后导航。
  • 使用 Alt+C 切换是否区分大小写。
  • 使用 Escape 关闭查找栏。

7.5 编辑与预览面板

编辑与预览布局

  • 通过工具栏的“编辑”和“预览”按钮分别显示或隐藏编辑区与预览区。
  • 文档视图可按 Ctrl/Cmd+Shift+V 在编辑、并排和预览之间循环切换。
  • 仅显示编辑区或预览区时,可见界面自动占满两者的可用空间;窄窗口上下排列时同样填满可用高度。
  • 恢复同时显示编辑区和预览区时,沿用此前保存的分栏比例。
  • 使用 View 菜单、命令面板的“聚焦编辑器”或 Shift+Alt+E 聚焦当前编辑区。
    • 编辑区隐藏时自动显示,并保留已显示的预览和大纲、原光标及选区。
    • 快捷键可在设置中修改;应用内对话框打开时不会抢走焦点。

差异模式

  • 工具栏和 View 菜单提供“切换差异模式”,默认快捷键为 Alt+Shift+D。
    • 差异模式只作用于当前 Markdown 标签。进入后临时关闭预览与大纲,让编辑区占满文档区域并禁止编辑。
    • 切换到其他标签时沿用各标签自己的模式;后台设置或工作区状态刷新不会重新打开预览。
    • 退出后恢复该笔记库原有的面板显隐设置。
  • 当前标签的差异模式随恢复会话持久化。
    • 默认比较当前正文与最近保存正文;文件树已启用历史时间差异时,改用该历史版本作为旧版本。
    • 修改行按“旧行、新行”紧邻显示;纯删除行仅显示旧行,纯新增行仅显示新行。
    • 在差异模式内使用 Alt+N / Alt+P 会以当前滚动视图为起点,直接滚动到下一处 / 上一处可见变化并标出当前变化;手动滚动后不会沿用之前记住的差异索引。
    • 退出模式后,编辑光标保留在该变化对应的正文位置。

7.6 大纲面板

大纲显示与过滤

  • 通过“预览”旁的“大纲”按钮显示标题大纲。
  • 当前文件名显示为大纲根节点;即使文档没有 Markdown 标题,根节点仍可见。根节点不作为标题参与复制或收藏。
  • 大纲顶部使用与文件树一致的图标按钮执行全部折叠、全部展开和复制。
    • 逐个标题的展开箭头与标题按层级一起缩进,也可用左右方向键切换;上下方向键只经过可见标题。
    • 双击根节点或标题文字可切换该节点的折叠状态,同时将焦点留在大纲。
    • 右键根节点或标题可递归折叠、展开该节点及其子标题;根节点递归折叠时只显示文件名。
    • 手动折叠状态在本次应用会话内随编辑和标签切换保留。
  • 折叠或展开节点后,不会为了追踪编辑器当前标题而自动滚动大纲。
  • 大纲过滤支持标题原文、全拼和拼音首字母,默认只显示命中标题。
    • “仅命中”图标按钮高亮时仅显示命中标题;取消高亮后显示命中标题及其祖先节点,提示为“显示完整匹配路径”。
    • 父标题命中不会自动显示未命中的子标题。手动折叠优先于过滤。
    • 过滤历史独立保存在本机,最多 50 条去重记录,可用上下方向键回看。
  • 焦点位于大纲面板时,Ctrl/Cmd+F 聚焦并选中大纲过滤框中的查询;在编辑器或预览区仍打开页内查找。
  • 大纲顶部可将当前可见标题复制为 Markdown 标题或按原始级别缩进的纯文本。全部折叠、全部展开、聚焦过滤框、切换过滤模式和两种复制操作也可从命令面板执行。
  • 命令面板提供 outline.collapseBranch 和 outline.expandBranch,分别递归折叠、展开当前大纲节点。
    • 大纲节点获得焦点时操作该节点;从编辑器执行时优先操作大纲中当前高亮的标题,没有可见的高亮标题时操作文件名根节点。

大纲尺寸与导航

  • 拖动大纲左侧分隔条调整宽度并按笔记库自动保存,重启后恢复;窄窗口上下排列时拖动上方分隔条调整高度,宽度与高度分别记录。
  • 大纲分隔条支持 Tab 聚焦后用方向键调整,Shift 加方向键加大步长;隐藏大纲或切换到搜索标签页时同步隐藏分隔条。
  • 激活大纲节点时,将对应源码定位到编辑区顶部。
  • 大纲高亮跟随当前聚焦的内容窗格:编辑器聚焦时跟随光标行,预览聚焦时跟随预览滚动位置;高亮节点超出大纲视图时自动滚入可视范围。
  • 编辑区隐藏时,激活大纲节点会直接定位可见的预览内容,并将焦点留在大纲。
  • 双击大纲节点切换折叠状态时,焦点仍留在大纲。
  • 使用 View 菜单的“聚焦大纲”或 Shift+Alt+O 直接打开并聚焦面板;Ctrl/Command+Shift+O 用于切换大纲显隐。

大纲收藏

  • 最近文件与收藏
  • 大纲标题右侧星标、右键菜单和命令面板中的“切换当前大纲收藏”共享同一操作;默认快捷键为 Alt+F。
  • 切换大纲收藏只原位更新星标,不重建大纲列表,保留大纲栏的滚动位置、焦点和当前高亮。

大纲快速打开

  • Ctrl/Command+P 的 Quick Open 中,@ 搜索全库持久大纲,@! 仅搜索已收藏的大纲,@@ 搜索当前编辑内容的大纲;
    • 选中文件或大纲结果后,按 Ctrl+Enter(macOS 为 Cmd+Enter)可在当前可编辑的笔记库 Markdown 文档中替换选区并插入对应引用,不切换文件;普通 Enter 仍打开结果。
    • @! 会按已打开标签的最新正文动态计算收藏大纲行号。
    • 结果按标题级别缩进,一级标题不缩进,之后每增加一级添加两个空格;
    • 结果可直接打开文件并跳转到标题。
    • 索引更新状态显示在底部固定提示栏,不会挤压或推动结果列表;
    • 后台索引刷新时保留当前选择项。
  • 文件、标题和路径搜索支持中文原文、无声调全拼、拼音首字母以及空格分隔的混合关键词。
  • 可通过“视图 → 拼音搜索”或命令面板中的“切换拼音搜索”全局启用或禁用拼音匹配,默认启用;状态栏显示当前状态。该设置适用于快速打开、命令面板、快捷键设置和大纲过滤,并在重启后保留。
  • 上述四处搜索框旁的“拼音”按钮也可切换同一设置;切换后当前搜索结果立即更新。
  • File、Edit、View、Go 等原生菜单中对应应用命令的快捷键跟随快捷键配置更新或移除。Windows 和 Linux 的单段快捷键显示在菜单右侧;双段快捷键及 macOS 上的快捷键显示在菜单名称后。搜索框按钮也显示当前拼音搜索快捷键,聚焦搜索框时可直接切换并更新结果。
  • 文件及 @、@!、@@ 大纲 Quick Open 均支持限定搜索:
    • p: 按笔记库相对路径,f: 按所属文件名。
    • 限定值为不区分大小写的连续子串;含空格时可用双引号包裹,例如 @p:"abc efg" f:plan 发布。
    • 限定项可重复,与普通关键词共同组成“与”关系;只有限定项时最近文件优先。
  • 全拼仅支持精确、前缀和连续子串匹配,不再按分散在多个音节中的字母进行跳字匹配,避免短关键词误命中无关结果。
  • 中文原文和拼音首字母仍支持按字符顺序跳字的模糊匹配;纯英文名称也保留这一行为。
  • 上述中文、拼音和模糊匹配规则同时适用于普通文件快速打开、@ 全库大纲和 @@ 当前文件大纲。

大纲导航设置

  • 设置中可控制单击或按 Enter/Space 激活大纲节点后,是否把键盘焦点转移到编辑器。
  • 关闭焦点转移后仍定位源码,但焦点留在大纲中。
  • “导航大纲时即时跳转”默认开启。
  • 即时跳转开启时,使用方向键或 Home/End 移动大纲焦点会同步定位源码。
  • 即时跳转关闭时,需要按 Enter/Space 才跳转。
  • 大纲跳转按照未自动换行的源码行精确定位。
  • 标题前的长行不会产生额外的纵向偏移。

7.7 滚动同步与源码高亮

  • 编辑区和预览区拥有独立滚动条。
  • 程序定位、预览重建和导航恢复产生的延迟滚动事件不会覆盖另一窗格的显式位置。
    • 导航恢复期间忽略编辑器测量布局产生的中间位置;恢复完成后继续双向同步。
    • 并排编辑时,每次预览重建后重新对齐编辑器的当前阅读位置,避免连续输入使编辑器发生滚动漂移。
    • Mermaid 异步重绘产生的中间滚动不会反向移动编辑器。
  • 两个区域按照 Markdown 源码块锚点双向同步,避免标题、列表、图片及换行造成长文档定位偏差。
  • 预览区从隐藏状态首次打开时,会立即对齐编辑区的当前阅读位置,无需再次滚动或编辑。
  • 移动编辑器光标时,预览区以浅蓝背景高亮对应的源码内容。
  • 列表中的每个列表项独立匹配源码范围,只高亮光标所在的列表项。

7.8 设置窗口

  • 设置可从原生菜单打开,默认快捷键为 Ctrl/Cmd+Shift+,。
  • 普通设置在所有应用窗口间共享;任一窗口保存后,其他窗口立即应用最新设置,并在下次打开设置窗口时显示最新值。
  • 设置窗口中的未保存修改会在点击“取消”或按 Escape 关闭时丢弃;窗口保持打开期间,后台同步刷新或其他窗口保存设置都不会覆盖这些修改。
  • 编辑快捷键时,按键录制/手动输入模式同时作用于通用键位和全部平台覆盖;录制内容写入当前聚焦的键位输入框。
  • 通用快捷键可留空,只设置特定平台;至少需要一个有效键位。
  • 输入模式按钮旁提供平台转换:Windows 将 Control 转为 Command 填入 macOS,macOS 将 Command 转为 Control 填入 Windows;优先读取当前平台覆盖,留空时读取通用键位,保存后生效。

7.9 剪贴板收集器

操作入口与共享状态

  • 从主菜单 View → 剪贴板收集器,或命令面板中的“剪贴板收集器”打开控制面板。
  • 面板采用单行紧凑布局,目标显示笔记文件名;悬停可查看完整路径。
    • 状态和错误在同一行显示,过长文本省略;悬停可查看完整内容。
    • 极窄窗口仅在面板内部横向滚动,不让整个窗口横向溢出。
  • 每个主窗口可以显示自己的面板。
    • 全应用只有一个收集器和一个固定目标笔记。
    • 任一窗口的目标、状态和成功收集数量都会同步到其他窗口。
    • 后打开的窗口读取当前共享状态。
  • 停止时可以选择当前窗口笔记库内已有的 Markdown 文件。
    • “使用当前笔记”选取当前已保存的笔记,不能使用搜索页或未保存的新建笔记。
    • 收集或暂停期间,“使用当前笔记”仍可点击。
      • 切换到不同笔记时,先停止收集,再设置新目标,并提示点击“开启”开始新一轮收集。
      • 当前笔记已经是目标时,显示提示并保留原来的状态和数量。
      • 当前笔记尚未保存为文件或是搜索页时,显示错误,不停止现有收集。
    • 通过“选择笔记”打开文件选择器前,仍需先停止收集。
  • 点击“开启”开始新一轮收集,成功数量清零。
  • 因编辑或错误暂停后,处理问题并点击“恢复”;恢复保留本轮成功数量。
  • 关闭面板不停止收集。
  • 切换笔记、切换笔记库、失去焦点或最小化不会改变目标或停止收集。
  • 关闭选择目标的窗口后,只要还有主窗口,收集继续。
  • 关闭最后一个主窗口或退出应用会停止收集。
    • 状态和目标仅保留在本次应用运行期间。
    • 重启后默认关闭,需重新选择目标并开启。

内容与追加格式

  • 开启和恢复时,以当前剪贴板内容为基准,只收集之后的新内容。
  • 退出应用时停止收集,并等待正在执行的写入结束,再完成日志落盘和退出。
  • 暂停或停止期间不缓存内容,也不在恢复时补收。
  • 收集纯文本和图片,不转换网页 HTML。
    • 文本保留原始缩进和换行,沿用笔记的换行编码设置保存。
    • 同一快照同时有图片和文本时,优先保存图片,避免收集附带的地址或文件名。
    • 图片保存为目标笔记同目录 assets/ 下的 PNG,并追加相对路径 Markdown 图片引用。
  • 面板提供“分隔符”和“日期时间”两个独立开关,默认都开启。
    • 各窗口共享配置;运行或暂停时也可以修改,对之后采集的条目生效,不改写已有内容。
    • 停止、恢复或更换目标不会重置配置;应用重启后恢复默认开启。
  • 每条内容按“分隔线、当地时间、正文”的顺序追加到笔记末尾,各部分之间留空行。
    • 关闭对应开关时省略分隔线或日期时间;两个都关闭时只追加正文,条目之间仍留空行。
    • 时间格式为 YYYY-MM-DD HH:mm:ss,使用电脑当地时间。
  • 忽略空内容和连续重复内容。
    • A → A 只收集一次。
    • A → B → A 保留三条。
  • 成功数量只在笔记写入成功后增加。
  • 主进程使用唯一的 500 毫秒轮询,并串行追加。
    • 两次轮询之间出现后又消失的剪贴板内容无法保证捕获。
    • 第一版不提供剪贴板历史、来源应用识别、全局快捷键或重启后自动收集。

编辑保护与错误处理

  • 开启、恢复和每次追加前检查所有主窗口中的目标笔记。
    • 任一窗口有未保存编辑、缺失文件状态或正在输入法组字时,暂停收集。
    • 提示先保存,再手动恢复;不会自动保存或覆盖用户编辑。
    • 窗口未响应时也暂停,避免仅根据延迟的恢复会话判断是否可以写入。
  • 确认目标干净后,写入期间短暂锁定目标编辑页;文件更新广播后解除锁定。
  • 收集追加与普通笔记保存共用按路径串行的写入队列。
  • 每次追加重新读取磁盘内容,并检查写入前的版本变化。
    • 无法安全追加时暂停,并显示原因。
    • 文件删除、移动、不可写,或图片/笔记保存失败时暂停。
    • 不自动重建丢失的目标文件;需要先停止并重新选择目标。
  • 成功写入沿用原子保存及发布流程,并通知所有打开目标笔记的窗口刷新标签和预览。

8. 图片管理

8.1 插入图片

  • 通过工具栏或快捷键选择并插入本地图片。
  • 通过工具栏读取剪贴板图片。
  • 在编辑器中直接粘贴复制的图片。
  • 插入图片前,如果当前文档尚未保存,会先提示选择文档保存位置。

8.2 图片存储与路径

  • 图片复制到 Markdown 文件同级的 assets/ 目录。
  • 图片使用避免重名的文件名。
  • 文档中插入相对于 Markdown 文件的图片路径,便于连同 assets/ 目录一起迁移。
  • 预览区按照当前 Markdown 文件的位置解析相对图片路径。

8.3 跨目录粘贴

  • 在应用内跨目录复制或剪切含图片的 Markdown 文本时,粘贴会自动换算图片相对路径。

    ![说明](../assets/image.png)
    
  • 可通过标准撤销与重做快捷键恢复这次粘贴。

  • 移动或重命名单个 Markdown 文件时,图片引用仍指向原附件;整体移动或复制文件夹时,文件夹内部的附件引用跟随新位置。

  • HTTP、HTTPS、仓库根路径和锚点引用保持不变;无法无损识别的复杂或未转义地址不作猜测性修改。

  • 同目录粘贴和外部剪贴板文本保持原样;该能力仅处理 Markdown 图片语法,不改写普通链接或 HTML 标签路径。

  • 自定义剪切写入 CodeMirror 所属页面的撤销历史,可用 Ctrl/Command+Z 撤销并重做。

8.4 支持格式

  • 支持插入 PNG、JPEG、GIF、WebP 和 BMP 格式的本地图片。
  • 剪贴板图片保存为 PNG。

8.5 复制图片

  • 编辑器没有文字选区且光标位于 Markdown 图片语法内部时,右键菜单显示“复制图片”。
  • 此时使用 Windows/Linux 的 Ctrl+C 或 macOS 的 Cmd+C 也会复制图片本身。
  • 在预览区的图片上右键,也可以通过“复制图片”复制所点击的图片,不依赖编辑器光标位置。
    • 支持 Markdown 与 HTML 渲染的图片,沿用预览中已经解析的图片地址。
    • 点击菜单外部、按 Esc、滚动预览、切换文档或重新渲染预览时关闭菜单。
  • 支持行内和引用式 Markdown 图片,本地相对路径按当前文档位置解析。
    • 相对路径图片需要文档已有保存位置。
    • HTTP/HTTPS 和 data:image 图片沿用图片导入的格式检查、10 MB 上限与网络请求 15 秒超时。
  • 复制写入系统剪贴板的图片数据,可粘贴到其他支持图片的应用;不会修改文档、光标或选区。
  • 有文字选区时继续复制 Markdown 文本;光标不在图片内部时继续复制当前整行。剪切行为保持不变。
  • 图片不存在、下载失败或无法解码时显示通知,并保留原剪贴板内容。

8.6 录音与豆包语音转文字

录音、暂停与文件命名

  • “插入图片”左侧的麦克风按钮、工具栏“操作 → 录音”和命令面板“录音插入附件”(editor.recordVoice)共用应用内录音窗口。
    • 不绑定默认快捷键;可在快捷键设置中自定义。旧 voice.record 命令保留已有绑定。
    • 仅可编辑的 Markdown 页面允许启动;预览、差异、搜索页面及打开其他对话框时不可用。
    • 录音期间锁定目标笔记与选区,禁止编辑、关闭和切换;全应用只允许同时处理一个录音任务。
    • 未保存的笔记先选择保存位置;取消保存不会启动录音。
    • 仅授权应用自身窗口的音频请求;拒绝远端页面、子框架和摄像头请求。macOS 打包包含麦克风用途说明。
    • 请求麦克风权限后使用原生 MediaRecorder 录制 AAC-LC/M4A,单声道、目标 64 kbps,支持“暂停”和“继续录音”。
    • 暂停会暂停编码写入并禁用麦克风音轨,计时不包含暂停时长。
    • “完成并插入”先校验录音可播放、非空且不超过上限,再保存到当前文档同级的 assets/,插入普通 Markdown 链接,例如 [录音 00:12](assets/voice-20260909-170901.m4a)。
    • 替换开始录音时的选区,光标移至引用末尾,笔记保持未保存;插入支持一次撤销,撤销不删除附件。
    • 文件名使用录音开始时的本机日期与时分秒,例如 voice-20260909-170901.m4a。恢复和重试沿用已选择的路径。
    • 同名文件存在时依次追加 -2、-3,使用排他创建避免覆盖已有文件。
    • 已有录音不改名,单个附件不能超过 20 MiB。
    • 不设固定时长上限;分段数据或码率估算达到 19 MiB 时自动完成,为封装保留空间。暂停时间不计入大小估算。
    • 仅前台录音;切到后台、锁屏、设备中断时停止并保留内容,恢复后选择插入或放弃。权限请求造成的临时失焦不触发中断。
    • 取消录音会释放麦克风并丢弃本次录音;保存失败时可以播放录音并重试保存。
  • 录音分段写入本机 userData/voice-recordings/,临时文件不进入同步目录。
    • 恢复记录包含目标笔记、原始正文、选区、开始时间和固定附件路径。
    • 保存或正文插入失败后可重试;重启并打开原笔记时提示恢复,点击录音入口选择插入或放弃。
    • 已导入附件与已插入的恢复稿不会重复创建或插入。异常退出留下的文件必须通过可播放校验。
    • 独立打开的笔记没有仓库会话恢复稿,录音恢复记录会保留到插入后的正文落盘,再清理临时文件。
    • 正常取消清理临时数据;已导入的附件保留,与图片附件的撤销规则一致。
  • Markdown 预览中的 M4A 链接下方显示完整语音条和“转文字”按钮。
  • 当前平台必须支持 M4A/AAC 编码;不支持时显示应用内错误,不自动切换音频格式。

完整语音条与全局倍速

  • 语音条包含播放/暂停、倍速选择、当前时间、总时长和可拖动进度;编辑区打开本地 M4A 链接显示同样的应用内播放器。
    • 拖动期间显示目标时间,松手后定位;播放时继续播放,暂停时保持暂停。
    • 未加载录音可按链接中的时长定位,加载后按实际时长校正;旧链接没有时长时加载媒体时长。
    • 倍速支持 0.5、0.6、0.7、0.8、0.9、1、1.25、1.5、2 倍,默认 1 倍。
  • 倍速使用本机应用级设置 voicePlaybackRate,所有录音、笔记、仓库与窗口共享,重启恢复;不参与账号设置云同步。
    • 保存失败显示提示并保留原倍速;无效设置恢复为 1 倍。
  • 全应用同一时间只播放一段录音。开始录音、切换笔记/仓库/模式、进入后台或关闭播放面板时停止播放。
    • 预览重绘和缓存切换会清理旧播放器和媒体 URL,隐藏节点不会继续播放。
    • 本地附件通过授权 IPC 读取,拒绝越界、私有目录和符号链接;缺失或损坏附件显示错误。远端链接仍按原规则处理。
  • 录音相对引用在笔记移动、目录复制和内部 Markdown 粘贴时采用与图片相同的路径调整规则。
  • M4A 附件沿用现有云同步、忽略规则、二进制哈希、配额及历史恢复,不新增协议字段。

本机配置与单段转写

  • 在“操作 → 语音识别设置”填写 AppID 与 Access Token,可修改或清除配置。
    • 使用豆包录音文件识别模型 2.0 标准版,资源为 volc.seedasr.auc。
    • 该接口不使用 Secret Key。官方鉴权说明。
    • 凭据通过 Electron safeStorage 加密保存到本机 userData/voice-transcription/,不写入笔记、同步数据或日志。
    • 系统安全存储不可用时拒绝保存凭据。
  • 点击预览录音旁的“转文字”,或将光标放在录音链接上后执行“操作 → 语音转文字”。
    • 文档只有一个录音链接时可以直接执行。
    • 上传本地 M4A,提交异步任务后每 5 秒查询结果;上传超时为 90 秒,查询超时为 30 秒。
    • 结果允许编辑,点击“插入文字”写入录音链接所在行的下方,保留录音附件并支持撤销。
    • 单段录音链接出现多次时保留结果供复制,不自动选择插入位置;可使用批量转换统一插入各个位置。
    • 关闭或终止窗口后停止查询,已提交任务仍由服务端继续处理。
    • 本机按附件真实路径、内容摘要和 AppID 保留请求编号与结果,重新打开后继续查询或显示已有结果。
    • 提交前先保存任务编号,网络失败后“重试查询”沿用该编号,避免自动重复上传;“重新识别”明确提交新任务。
    • 只允许读取已授权笔记所在笔记库内的 M4A;单独打开的库外笔记使用其所在目录作为附件范围。

当前文件批量转写

  • “操作 → 批量语音转文字”按文档顺序处理当前文件的全部 M4A 链接。
    • 排除代码围栏、缩进代码、行内代码、图片与远程链接。
    • 重复链接只调用一次服务,结果插入各个对应链接所在行的下方。
    • 再次批量转换时,跳过链接下方已经存在的相同转写结果,避免重复插入。
      • 单段转换插入的相同结果也会跳过;新增的链接位置和此前失败的结果仍可插入。
      • 判断依据是当前正文,重新打开笔记后仍然有效;撤销或删除结果后可以再次批量插入。
      • 手动修改过的文字与本次转写结果不相同时,仍会插入本次结果;单段手动插入保持原有行为。
    • 转换期间显示进度窗口并锁定编辑区,禁止修改正文。
    • 单段失败后继续处理其他录音,结束时显示成功与失败数量及错误详情。
    • 完成后统一插入成功识别的非空文字;关闭进度窗口后恢复编辑,可以一次撤销本次插入。
    • 终止操作停止后续查询与转换,不插入尚未统一插入的结果;已完成结果保留在本机任务记录中。
    • 笔记在转换过程中被外部更新或切换时,不覆盖变化后的正文,保留结果供手动复制。
  • 录音、单段转写、批量转写和设置也可以从编辑菜单、命令面板或自定义快捷键执行。

9. 界面与状态显示

9.1 布局

  • 原生 File、Edit、View 菜单与工具栏操作复用可配置命令;各功能的行为和默认快捷键在对应章节说明。
  • 侧栏可从 View 菜单切换,默认快捷键为 Ctrl/Cmd+B。
  • 界面中的完整本地日期时间统一显示为 YYYY-MM-DD HH:mm:ss,日期与时间字段均补零并使用 24 小时制。
    • 仅日期和仅时间场景分别使用 YYYY-MM-DD 与 HH:mm:ss。
  • 默认使用左右分栏布局,同时显示编辑区和预览区。
  • 窗口宽度较小时自动切换为上下分栏布局。
  • 编辑区、预览区和大纲直接展示内容,不占用空间显示重复的面板标题条。
  • 工具栏仍可独立切换编辑区、预览区和大纲的显隐。
  • 工具栏、标签栏和状态栏固定在窗口内,不随文档内容滚动。

9.2 标签与滚动

  • 标签名称过长或标签数量较多时,支持省略显示和横向滚动。
  • 标签支持标准键盘焦点以及左右方向键切换。
  • 编辑区自动换行可从 View 菜单、命令面板或按 Alt+Z 切换,默认快捷键与 VS Code 一致。该共享选项会同步到所有窗口以及已打开和后续创建的编辑页。
  • 编辑区和预览区均保留可见的滚动条。

9.3 状态栏

  • 状态栏显示当前文件名或完整路径。
  • 状态栏显示当前文件的磁盘修改时间,并在保存或检测到外部修改后即时更新。
  • 状态栏显示文档字符数和行数。
  • 状态栏显示光标所在的行与列;存在选区时同时显示选择的字符长度,反向选择按活动端定位光标。
  • 状态栏显示 UTF-8 BOM 和 LF/CRLF 信息。

10. 同步协议

10.1 加载与身份模型

  • 打开笔记库后可从工具栏按需启动同步。
  • 普通启动和编辑路径不会加载同步实现。
  • 使用稳定的笔记库、设备和文件 ID。
  • 使用服务端单调 revision 和拉取 cursor。
  • 同一安装重新登录同一账号与服务时复用原设备 ID。
  • 重新登录时轮换登录令牌。
  • 执行“远程退出当前设备”后,凭正确密码重新登录会重新激活该设备。
  • 重新激活设备时保留仓库同步基线,不会从 cursor 0 重新遍历远端。
  • 仅当远端已不存在该设备身份时才重新登记。

10.2 队列、重试与幂等

  • 本地变更先写入持久化队列。
  • 网络失败后显示错误并可安全重试。
  • 本地扫描发现未跟踪路径时,先读取远端最终状态。
  • 远端已有同路径同内容文件时,直接采用其 fileId 和 revision。
  • 采用远端文件身份时,不上传正文,也不创建新 revision 或冲突副本。
  • 上传前后发生竞态时,同内容路径冲突按相同规则收敛。
  • 重复操作使用客户端操作 ID 保证幂等。
  • 提交后断网不会生成重复版本。

10.3 收藏同步

  • 每个打开的仓库都会安全读取或创建 .mynote/library.json;收藏按其中的稳定仓库 ID 保存,不依赖本机绝对路径。
  • 文件收藏和大纲收藏保存在应用数据目录的 repository-favorites-v1.json,渲染端仍只接收原有收藏字段。
  • 旧版 workspace-state.json 中按路径保存的收藏不迁移;升级后使用新的仓库 ID 收藏集合。
  • 尚未创建远端仓库时,收藏仍可在本机使用并保留待同步状态;首次文件同步创建远端仓库后自动上传。
  • 多设备按收藏身份、修改时间和变更 ID 逐项合并;取消收藏保留墓碑,避免旧设备重新带回已删除项目。
  • 文件移动、删除、回收站恢复、大纲整理和 100 项上限都会生成对应收藏变更。
  • 同步中心独立显示收藏云同步状态、待上传数量和最近成功时间。
  • 旧服务端没有收藏接口时自动降级为仅本地收藏,不影响文件和用户设置同步;升级服务端后自动恢复。
  • 收藏不进入 Markdown 文件 revision、仓库历史恢复或原始文件导出。

10.4 Markdown 合并与冲突处理

  • 同路径 Markdown 双设备编辑使用共同祖先执行保守三方合并。
  • 非重叠修改自动合并并清理临时版本。
  • 重叠修改在原文件旁保留 .base、.local 和 .remote 文件。
  • 文件树显示未解决冲突警告。
  • 打开的冲突文件会在标签栏显示警告标记,左上角仓库名也会在任一文件存在冲突时显示警告标记。
  • 存在任何未解决的文件冲突时,手动与后台自动同步都会停止;点击同步操作会提示先处理冲突。
  • 设置中可配置外部合并程序及 %local、%remote、%base 和 %merged 参数。
  • 可通过右键菜单直接启动外部合并程序。
  • 冲突处理后可标记完成。
  • 图片、删除、路径与重命名意图冲突使用普通冲突副本或同步回收目录。

10.5 删除与恢复

  • 删除以墓碑同步。
  • 远端删除的本地文件进入 .mynote/sync-trash/,以便恢复。

10.6 同步窗口与诊断日志

  • 同步窗口分别显示待推送/待拉取数量;任一数量非零时高亮,并同时显示当前状态、远端游标和上次成功时间。
  • 同步中心以“待同步(推送)内容”显示本地文件列表,区分新增、修改、重命名和删除。
  • 展开待同步文件可查看相对上次同步内容的逐行 diff;待同步预览只扫描本地文件,不上传、下载或改写持久化同步队列。
  • 已因失败保留在持久化队列中的内容按队列快照展示,并与本地扫描预览明确区分。
  • 诊断日志按时间正序排列,最新记录位于底部。
  • 笔记库同步日志位于 <笔记库>/.mynote/sync-hosted-v1/<namespaceKey>/logs/YYYY/MM/DD.log。
  • 用户设置同步日志位于 Electron userData/preference-sync-logs-<namespace>/YYYY/MM/DD.log;Windows 默认 userData 为 %APPDATA%/mynote-client。
  • 上述落盘日志每行为一条 JSON 记录,同步中心最多读取并展示最近 200 条。
  • 收藏同步供同步中心读取的日志仅保存在当前应用进程内,最多 200 条;退出应用后清空,不建立独立的收藏日志文件。新产生的记录同时写入下述统一日志文件。
  • 诊断日志初始定位到最新记录。
  • 用户停留在底部时,持续跟随新增记录。
  • 用户向上查看旧记录后,保留当前位置。
  • 点击远端仓库、登录设备、待同步(推送)内容、最近版本或诊断日志模块的标题时,对应模块滚动到窗口顶部;点击模块内部内容不会触发滚动。
  • 关闭同步中心后再次打开时,恢复上次浏览的窗口滚动位置;异步刷新账号和仓库内容后仍保持该位置。
  • 诊断日志始终展开显示。

6.6.1 客户端统一每日日志

  • 客户端额外将日志汇总到 Electron userData/logs/YYYY/MM/DD.log。
    • Windows 默认目录为 %APPDATA%/mynote-client/logs/。
    • 按本机日期每天一个文件,所有窗口和笔记库共用;重启后继续追加。
    • 历史同步日志不迁移;原有同步日志文件和同步中心读取规则不变。
  • 覆盖主进程和主窗口、片段窗口、隐藏导出页面的控制台日志,以及笔记库、用户设置、收藏同步诊断和客户端错误摘要。
    • 保留现有控制台输出的内容、参数和级别,仅额外记录文件副本。
    • 独立部署的服务端、构建脚本和测试运行器输出不纳入客户端统一日志。
    • 未登录、离线或远端上报失败时,客户端错误摘要仍记录到本地;原有远端上报规则不变。
  • 文件使用 UTF-8、LF,每行一条 JSON,包含 at、level、category、source、message 和 args。
    • at 使用 ISO 时间;日期目录使用本机日期。
    • 已有分类前缀原样保留;无前缀的文件副本补充主进程、渲染器或对应同步类别,控制台文本不添加前缀。
    • 来源包括主进程 PID;渲染器还记录 webContentsId 和页面 URL。
    • 参数在产生时快照,保留嵌套详情和错误堆栈;循环引用、BigInt 和不可读取属性使用明确标记。
  • 保留现有日志内容,包括 DeepSeek 请求正文、打包内容和回答;此功能不增加脱敏、自动清理、大小轮转或日志查看界面。
  • 主进程串行追加;正常退出会等待队列写完,强制结束进程或系统崩溃可能丢失尚未写出的记录。
    • src/main/app-log.ts 负责按日期写入、控制台与诊断镜像,以及等待写入队列清空;文件头和各函数头部注释说明对应职责。
  • 文件写入失败不阻断控制台、业务操作或远端上报;失败期间在原控制台提示一次,后续记录继续尝试写入,失败记录不自动补写。
  • 需要重启客户端后启用新增的统一日志机制。

10.7 运行时边界

  • 产品同步入口只连接托管服务。
  • 协议测试使用 test/helpers/memory-sync-remote.ts 中的内存远端替身。
  • 内存远端替身不进入应用运行时或安装包。

11. 托管同步 Beta

11.1 服务与账号

  • 可配置 HTTPS 托管服务地址。
  • 支持注册或登录邮箱账号。
  • 点击“注册 Beta 账号”进入邮箱验证码注册表单,点击“返回登录”切回密码登录。
    • 输入邮箱后点击“发送验证码”,填写邮件中的 6 位数字验证码,再点击“验证并注册”。
    • 验证码发送不要求先填写密码;提交注册时仍要求密码为 10–200 个字符。
    • 验证成功后创建账号并自动登录,登录已有账号不需要验证码。
    • 验证码有效期为发送成功后 10 分钟,至少等待 60 秒才能重发。
    • 每个验证码最多允许 5 次错误尝试,重发会使旧验证码失效。
    • 每个邮箱每小时最多请求发送 5 次,每个来源 IP 每 10 分钟最多请求发送 10 次。
    • 发送失败的请求也计入限额,并保留 60 秒重发间隔。
    • 发送期间不能重复发送或提交注册;服务端返回重试时间后,发送按钮显示倒计时。
    • 修改邮箱或服务地址、返回登录、成功注册或关闭同步中心时清空验证码。
    • 服务端未配置 SMTP 时暂不开放注册,已有账号仍可登录和同步。
    • 所有新注册都必须提供有效验证码,旧客户端不能继续直接注册。
  • 密码不会保存在客户端。
  • 登录或注册失败时保留当前密码输入,方便修正账号信息后重试。
  • 登录、注册成功或关闭窗口后清空密码。
  • 已保存登录凭据但服务地址暂时不可达时,同步中心保留并重新显示服务地址与登录表单。
  • 服务地址不可达时,允许修改地址后重新登录。
  • 瞬时网络故障不会自动删除本机安全凭据。
  • 同步中心直接显示托管服务地址和登录表单,不提供本地原型模式选择。
  • 登录后,账号区域显示完整用户 ID。
  • 提供一键复制用户 ID 到系统剪贴板的按钮。

11.2 登录凭据与设备会话

  • 登录令牌使用系统安全凭据能力加密。
  • 系统加密不可用时,不会退回明文保存。
  • 支持让其他设备远程退出。
  • 支持撤销当前设备会话并清除本机凭据。

11.3 自动同步

用户设置云同步

  • 登录后,以下账号级设置自动跨设备同步:
    • 编辑器字号;
    • 编辑器自动换行;
    • 单击文件时使用预览标签;
    • 拼音搜索;
    • 输入法状态显示;
    • 激活大纲后聚焦编辑器;
    • 导航大纲时即时跳转;
    • 笔记库 Markdown 文件上限;
    • 快捷键 JSON;
    • 热键 JSON;
    • 系统级热键启用状态。
  • 本机路径、外部冲突工具命令及参数、窗口布局、仓库级界面状态、自动同步配置和登录凭据不同步。
  • 服务端启动时清理旧版本写入云端的 hotkeysEnabled 字段;热键总开关仅由各设备本机设置决定。
  • 设置保存后立即尝试上传,并每 60 秒独立检查其他设备的修改;关闭笔记库自动同步不会关闭用户设置云同步。
  • 从其他设备拉取设置并保存后,立即更新已打开窗口的设置和拼音搜索菜单状态。
  • 用户通过侧栏“同步”、同步中心“立即同步”或 sync.run 命令手动同步当前仓库时,会同时同步上述账号级设置。
  • 首次登录以云端已有值为准;覆盖前将本机可同步设置备份到应用数据目录的 preference-backups。
  • 不同字段分别同步,同一字段以服务端最后成功提交的版本为准;快捷键 JSON 和热键 JSON 分别作为独立字段处理。
  • 离线修改在连接恢复后重试;同步中心显示用户设置同步状态、上次成功时间、待重试数量和不含配置值的诊断日志。

笔记库自动同步

  • 登录后可启用按秒计时的全局自动同步。
  • 默认同步间隔为 60 秒。
  • 开关或同步间隔修改后自动保存,无需额外点击保存按钮。
  • 关闭自动同步时持久化保留当前间隔,重新打开应用或再次开启后可继续使用该值。
  • 关闭全局自动同步后禁用全部后台调度。
  • 开启全局自动同步后,当前仓库始终进入定时任务,不受仓库级开关影响。
  • “切换仓库后仍自动同步”默认关闭。
  • “切换仓库后仍自动同步”不依赖全局开关,可在全局自动同步关闭时预先选择;全局关闭期间不执行调度。
  • “安全的自动同步”是独立的仓库级选项,不依赖“切换仓库后仍自动同步”或全局开关,可单独预先选择。
  • 当前仓库和切换后继续参与的后台仓库都遵循各自的安全模式设置:
    • 未选择时执行原有完整同步。
    • 选择后,仅本地待推送或远端待拉取其中一侧有变化时才同步。
    • 双向变化或同步请求间发生竞态时,保留队列与工作文件并跳过,不生成冲突副本。
    • 当前仓库因此跳过自动同步时,侧栏仓库标题显示警告,tooltip 标明具体阻止原因,直至后续同步成功或关闭安全自动同步。
  • 多个目标按顺序同步,一个仓库失败不会阻断其余仓库。
  • 手动“立即同步”不受仓库级开关影响。
  • “立即同步当前仓库”作为 sync.run 命令显示在命令面板和快捷键设置中;默认快捷键为 Alt+A Alt+S,仅在已打开仓库且没有模态窗口时可执行。

11.4 远端仓库与克隆

  • 无需先打开本地仓库即可进入同步中心。
  • 登录后列出当前账号的全部远端仓库。
  • 远端仓库列表显示 revision、当前未删除 Markdown 文件数和创建时间。
  • 图片附件不计入 Markdown 文件数。
  • 未命名仓库显示完整 ID。
  • 手动命名后,仓库显示为 名称(完整 ID)。
  • 可选择远端仓库克隆到本地,并直接切换为当前工作区。
  • 选择空文件夹时直接克隆。
  • 选择非空文件夹时,在其中新建以仓库名称或完整 ID 命名的安全子文件夹。
  • 新设备选择空文件夹后,自动接入账号中唯一已有数据的远端笔记库,无需手工复制隐藏元数据。
  • 同一台机器可保留同一远端库的多个本地目录副本。
  • 每个本地目录副本维护独立同步游标。

11.5 配额、设备与版本历史

  • 显示账号配额、登录设备、最近版本和当前同步状态。
  • 首次成功同步会分页下载全部版本元数据和版本正文,并按账号、设备和仓库隔离保存在本地 .mynote 同步目录中。
    • 后续同步以本轮已应用的远端游标为上限,只下载并写入本地连续缓存之后的新增 revision。
    • 已完整覆盖该游标时不发起历史请求。
    • 每个成功分页都会形成可恢复检查点;缓存缺页或损坏时才重新构建完整历史。
  • 同步进度将实际文件拉取显示为“下载远端变更”,将离线历史缓存显示为独立的“同步版本历史”阶段。
  • 同步中心版本列表、单文件版本历史、展开差异和编辑器按时间比较只读取本地历史缓存,不发起服务器请求;本地存在尚未同步的修改或持久化待推送队列时同样如此。
  • 打开或刷新同步中心时,“最近版本”会立即读取并渲染本地历史,不等待配额、远端仓库和设备等网络数据加载完成;服务器关闭或暂时不可达时仍显示本地缓存,并同时保留连接失败提示。
  • 最近版本标明新增、修改、重命名、删除或恢复动作。
  • 最近版本显示修改时间和设备名。
  • 同步中心“最近版本”中未删除的版本也提供“另存”,可将本地缓存的该版本原始内容保存到用户选择的文件;断网或未登录时仍可使用已缓存的版本。
  • 文件树或已保存标签的右键菜单可查看指定文件的远端版本历史;命令面板同时提供 sync.showFileHistory“查看文件历史”命令,并按标签、文件树选中项、当前文档的顺序确定目标。
  • 指定文件历史与同步中心“最近版本”共用可展开条目、版本元数据、差异渲染和恢复流程。
    • 文件历史中未删除的版本可通过“恢复”旁的“另存”按钮,将本地缓存的该版本原始内容保存到用户选择的文件;网络断开或未登录时仍可使用已缓存的版本。
    • 取消另存不写入文件;没有缓存正文的版本不能另存。
    • 两处版本详情均可在“与上一版本比较”和“与当前版本比较”之间切换。
    • 当前文件按稳定文件 ID 跟随重命名后的路径;已删除时按空内容展示删除差异。
    • 仓库级“整体恢复”仍仅在同步中心提供。
  • 同步中心“最近版本”中仍存在于当前本地笔记库的文件可直接“定位到文件树”;操作会关闭同步中心、显示并展开文件树、选中对应文件,但不会打开文件或切换当前标签。
  • revision 高于当前本地同步游标的最近版本以“待同步到本地”高亮,拉取完成并刷新列表后自动取消高亮。
  • 最近版本列表上方常驻说明蓝色高亮条目代表待拉取(同步到本地)的版本。
  • 展开版本后可查看以下信息:
    • 设备、文件和操作标识;
    • 哈希;
    • 原路径;
    • 恢复来源;
    • 逐行正文 diff。
  • 大型 Markdown 的版本 diff 会按中间未变化行持续对齐,不会因超过内存保护阈值而把首尾变化之间的内容误显示为整段删除和整段新增。
  • 同步中心、文件历史、待同步正文 diff、文件树比较和编辑器差异模式都按内容相似度做保序行对齐:
    • 每个旧行后紧跟对应新行;保留原句但大幅扩写的行仍可配对。
    • 匹配的旧行与新行分别用高亮红色块和高亮绿色块标出行内删除、增加片段。
    • 中间插入不会造成后续修改错配;无法配对的删除行和新增行分别单独显示。
  • 正文 diff 使用 13px 等宽字体,行高为字号的 1.5 倍。
  • 差异框随内容展开,不再单独限制为最高 300px。
  • “精简差异”默认启用,只显示每处变化及其前后 3 行。
  • 取消“精简差异”后显示完整 diff。
  • “自动换行”默认关闭。
  • 自动换行关闭时,长行使用横向滚动。
  • 自动换行启用后,长行在差异框内换行。
  • 切换差异显示选项时,不重复请求服务端。
  • 展开版本的标题与恢复按钮在详情滚动期间吸附在列表顶部。
  • 二进制附件显示修改前后的大小。
  • 未删除的历史正文可恢复为新版本。
  • 每条最近版本都提供“整体恢复”,可将本地同步文件和已打开的编辑内容强制还原为该全局 revision 的仓库快照,并丢弃原有本地待推送队列。
  • 整体恢复在全局自动同步关闭时只产生本地待推送变更,不修改远端;全局自动同步开启时会在恢复后立即遵循该仓库的普通或安全自动同步策略。

11.6 本地同步状态

  • 同步基线、待上传队列、cursor 和诊断日志保存在仓库 .mynote 内。
  • 状态文件名不依赖仓库绝对路径。

11.7 图片与录音附件

  • 同步 PNG、JPEG、GIF、WebP 和 BMP 图片附件,以及 M4A 录音附件。
  • 跨设备保留原始二进制字节。
  • 单文件上限为 20 MB。

11.8 服务端能力与诊断

  • 服务端使用关系元数据、加密对象存储、版本历史、墓碑和审计事件。
  • 同步失败、渲染进程异常和未处理错误可发送有界诊断摘要。
  • 诊断摘要不包含登录令牌。
  • 可将服务端当前完整 Markdown 与图片库导出为普通目录。
  • 导出目录保留 .mynote/library.json。

11.9 Beta 限制

  • 托管同步当前标记为 Beta。
  • 尚未提供图片与 M4A 录音之外的通用附件。
  • 尚未提供密码重置。
  • 尚未提供团队共享。
  • 尚未提供端到端加密。

12. 快捷键

12.1 热键与快捷键独立配置

  • 配置中心的「快捷键 / 热键」选择同时决定列表、编辑、添加、删除、恢复默认和 JSON 操作的配置类型。
  • 快捷键用户覆盖存入应用数据目录的 User/keybindings.json。
  • 系统级热键用户覆盖独立存入 User/hotkeybindings.json。
  • 「编辑 JSON」仅编辑当前类型的用户文件;「定位文件」打开对应文件位置,「默认 JSON」仅显示当前类型的默认绑定,标题和说明文案同步显示“快捷键”或“热键”。
  • 两个文件均使用现有 JSON 数组格式,支持平台覆盖和默认绑定移除;不按命令分类拒绝整个文件,也不自动将规则移动到另一个文件。
  • 两类文件分别监听外部更新,保存后立即生效;文件损坏时保留该类型当前有效绑定,JSON 修复只更新当前文件。
  • 热键注册仅读取热键文件;修改快捷键不会重新注册全局热键。
  • 未被当前执行端使用的命令或移除规则不会阻止其他有效配置加载;JSON 格式、键位和 When 仍需通过校验。
  • 热键总开关仅保存在本机 workspace-state.json 的 localSettings.hotkeysEnabled,不参与云同步,缺省启用,禁用时保留 Quick Cmd Form 启动热键的现有例外规则。
  • 账号同步仅使用 keybindings 和 hotkeybindings 字段同步绑定规则,localSettings 中的所有值均不参与同步,不兼容旧位置或旧云端开关字段;热键字段缺失时默认空用户覆盖。
  • 不兼容旧混合配置,不读取其中的热键、不自动迁移或删除本地旧文件,也不迁移云端旧值。
  • 本次更新需配套更新并重启桌面客户端与同步服务。

12.2 快捷键参考

快捷键设置:MVP

  • 快捷键注册与响应技术流程:命令与绑定注册、平台覆盖、When 求值、Chord 状态机、输入法保护、菜单与命令面板入口、配置持久化及全局热键注册。

  • Windows 上使用 Alt+左/右 或 Ctrl+Alt 加非修饰键后,先松开 Alt 不会将焦点转移到原生菜单。单独按 Alt 仍可使用原生菜单。

快捷键 功能
Ctrl+N 新建文档
Ctrl+O 打开文件
Ctrl+P 快速打开文件;输入 @ 搜索全库大纲,输入 @! 搜索收藏大纲,输入 @@ 搜索当前文件大纲
Ctrl+Alt+N 系统级热键:显示或隐藏片段管理器;可在快捷键设置中修改
Ctrl+H 替换当前文件(macOS 为 Cmd+Option+F)
Ctrl+G(Windows、macOS) 输入行号并跳转到当前文档的对应行
Ctrl+R 打开最近的笔记库;macOS 同样使用 Ctrl 而不是 Command
Ctrl+Shift+Alt+S 在当前已打开的应用窗口间循环切换;Windows 与 macOS 相同
Ctrl+F 在当前编辑区或预览区内搜索
Ctrl+Shift+F 在文件中查找
Ctrl+Shift+R 在文件中替换
Ctrl+= / Ctrl+Shift+=(Ctrl++) 放大整个应用页面
Ctrl+- 缩小整个应用页面
Ctrl+0 重置页面缩放为 100%
Enter / Shift+Enter 查找栏打开时跳到下一个/上一个匹配
F3 / Shift+F3 从编辑器最新 caret/选区位置跳到下一个/上一个匹配;查找栏关闭时会先在当前编辑区或预览区重新打开
Alt+C 查找栏打开时切换区分大小写
Alt+S 打开同步中心
Alt+Shift+D 切换当前文件的差异模式
Ctrl+Alt+D 打开文件树差异;macOS 使用 Cmd+Option+D
Windows/Linux:Ctrl+Shift+V 在编辑、并排和预览三种文档视图间循环切换
macOS:Cmd+Shift+V 在编辑、并排和预览三种文档视图间循环切换
Alt+A Alt+S 立即同步当前仓库
Escape 关闭当前查找栏
Ctrl+S 保存当前文档
Alt+Shift+S 系统级热键:主窗口已显示且激活时,macOS 像 Cmd+H 一样隐藏应用的所有窗口、Windows/Linux 最小化主窗口;已显示但未激活时置于前台并激活;隐藏或最小化时恢复显示并激活
Ctrl+W 关闭当前标签
Ctrl+Q 退出应用;macOS 使用 Command+Q
Ctrl+Tab 打开最近使用标签列表并向前选择,松开 Ctrl 后切换
Ctrl+Shift+Tab 打开最近使用标签列表并向后选择,松开 Ctrl 后切换
Alt+1–Alt+9 按 1-based 顺序切换到第 1–9 个标签;对应位置没有标签时不执行操作;Windows 下使用小键盘时会阻止 Alt 数字码的延迟字符写入编辑器
macOS:Command+Shift+[ 循环切换到上一个标签
macOS:Command+Shift+] 循环切换到下一个标签
Windows/Linux:Ctrl+PageUp 循环切换到上一个标签
Windows/Linux:Ctrl+PageDown 循环切换到下一个标签
Ctrl+Shift+I 插入本地图片

除表中明确标为所有平台统一使用 Ctrl 的快捷键外,macOS 可以使用 Command 代替 Ctrl。显示或隐藏主窗口的快捷键是系统级热键,在应用位于后台时同样生效。

  • 启动时优先按已保存的热键配置注册全局热键,不会先尝试注册已被替换或删除的默认热键。

    • 主窗口显示/隐藏热键统一通过可配置热键控制器注册,不再保留独立的固定键位注册入口;默认仍为 Alt+Shift+S。
    • 配置无法读取或格式无效时才回退默认配置;热键总开关关闭时不注册任何全局热键。
  • 全局热键逐个注册;任意热键被系统占用或注册异常都不会阻止其他热键继续注册。

  • 热键列表页的删除、恢复默认与启用开关,以及修改页和 JSON 编辑器的保存,不会因热键注册失败而失败。

    • 配置仍会保存,注册成功的热键立即生效,注册失败的热键暂不生效;失败原因写入应用日志。
    • 读取或重新加载配置会重试失败热键;配置格式错误和文件写入失败仍会正常报错,写入失败时撤销本次新注册。
  • 缩放快捷键在编辑器聚焦时同样生效,可在设置 → 快捷键中修改,也可通过命令面板执行。

  • 同时支持 Ctrl+小键盘 + 放大和 Ctrl+小键盘 - 缩小(macOS 使用 Command),不需要按 Shift。

  • 小键盘加减键可独立录制和修改;快捷键 JSON 中分别写为 numadd 和 numsub,例如 ctrl+numadd。

  • View 菜单保留缩放操作;键盘缩放由应用快捷键系统统一处理,避免原生菜单抢占用户配置的按键。

13. 工作区性能与验证

13.1 性能基准

运行 npm run benchmark:workspace 会创建 1000 个小型 Markdown 文件,测量目录扫描、首次正文搜索和缓存搜索。

2026-08-14 开发环境的多次运行参考范围:

  • 扫描约 130–180 ms。
  • 首次搜索约 470–1200 ms。
  • 缓存搜索约 160–420 ms。

结果用于比较相对回退,不作为所有设备的硬性 SLA。真实笔记库规模或延迟超过当前方案能力时,再评估 SQLite FTS。

13.2 自动化覆盖

  • npm run test:smoke:voice 使用 Electron 自带的模拟麦克风验证 M4A 编码、暂停与恢复、计时、保存重试、批量锁定、终止竞态、外部更新保护和撤销。
  • node scripts/run.mts node --test test/voice.test.js test/voice-recordings.test.js 验证录音命名与重名、分段落盘、重启恢复、独占任务、授权边界、倍速持久化、引用调整、凭据存储和豆包异步任务恢复;语音服务请求使用模拟响应。
  • npm run test:smoke:voice-player 验证完整语音条、实际 M4A 播放、拖动、全局倍速、播放互斥、失败提示与缓存清理。
  • npm run test:smoke:voice-app 验证应用按钮位置、命令面板触发、模式禁用、录音锁定、附件插入、倍速保存、编辑区播放器与撤销重做。
  • 录音 UI 修改及 macOS 麦克风用途说明需要重新构建并重启桌面应用;Windows 原生编码使用模拟音源验证,系统锁屏/真实设备拔出及 macOS 真机需手工验证。
  • 工作区扫描、文件读取、新建文件和文件夹,以及搜索、最近记录、收藏和设置持久化。
  • 仓库被外部删除后的失效选择清理、文件重命名、移动、复制与系统回收站调用。
  • 文件操作和跨文档剪贴板中的图片相对路径重写;路径穿越、符号链接逃逸、名称冲突和递归移动拒绝。
  • 打开文档迁移后的状态更新;目录树选中态、文件夹展开、右键与 Shift+F10 菜单、键盘导航和路径复制。
  • 编辑器右键菜单的鼠标与键盘入口、格式操作、撤销与重做、粘贴、全选、只读禁用状态及焦点恢复。
  • Electron 冒烟测试中的工作区恢复、目录树、搜索、打开文件、新建文件和文件夹,以及手动刷新反馈。
  • 拖放时按下或释放 Ctrl(macOS 为 Cmd)即时切换复制与移动提示,即使鼠标不再移动;最终执行移动。
  • 同步冲突的 Markdown.base、Markdown.local、Markdown.remote 临时版本在原文件旁显示警告。
    • 临时版本本身不作为工作区 Markdown 节点或同步文件显示。
  • 仓库存在未解决冲突时阻止手动与后台同步;右键菜单可清理临时版本,配置工具后可启动外部三方合并。工具路径逐项替换参数,不通过 shell 展开文件名。
  • 文档大纲的层级提取、代码块排除、实时更新、文件名根节点、面板切换、顶部定位、即时跳转、双击折叠、递归折叠与展开、折叠时的滚动位置、命令面板、View 菜单快捷键和键盘导航。

13.3 冒烟测试诊断输出

  • 主冒烟入口和粘贴撤销入口注册真实收集器 IPC,避免启动读取出现 collector:read 未注册错误。
  • 主冒烟入口的收集器与文件、同步处理器共享应用状态,清理测试目录前停止收集器。
  • 错误弹窗场景仅在 app-alert 专项和 full 综合流程中执行;其他专项不再重复触发预期读取失败。
  • 用例通过时,故意读取不存在笔记和移动到同名目标产生的 IPC 拒绝按消息合并,显示次数并省略重复调用栈。
  • 其他错误保留完整诊断;用例失败、崩溃或超时时也保留这些拒绝的完整诊断,便于排查。
  • Smoke suite failed 和非零退出码仍表示真实失败,不能当作预期拒绝忽略。
  • 后续单独集中提取 test/electron-smoke.ts 和 test/paste-undo-smoke.ts 的启动与清理模块;本次不拆分测试流程。

13.4 人工平台验证

发布前仍需在 Windows/macOS 测试制品上检查:

  1. 系统文件夹对话框与最近笔记库切换。
  2. 中文、空格、长路径和只读目录。
  3. 回收站中的恢复操作。
  4. 文件夹跨层级移动及含附件目录的复制。
  5. 外部程序修改目录结构后手动刷新。
  6. 1000–10000 文件笔记库的滚动和搜索体验。

14. 管理后台 API 初始化

  • 独立管理前端复用托管同步服务的 SQLite 和对象存储。
  • /admin/v1 提供管理员登录、会话恢复、退出、概览、分页账号列表和分页笔记库列表。
  • 管理员凭据与用户同步账号、metrics 管理令牌独立。
  • 管理会话通过 HttpOnly Cookie 保存,普通用户 token 无法访问管理接口。
  • 初版只读;完整配置和接口约定见 管理后台 API。

15. Quick Cmd Form

  • 通过“视图 → Quick Cmd Form”或命令面板 quickCmdForm.open 打开。
  • 默认全局热键为 Ctrl+Alt+S,命令 ID 为 quickCmdForm.toggleWindow。
    • 可在快捷键设置中修改或移除。
    • 在外部应用中先选中内容,再按热键打开,输入短命令后立即执行。
    • Windows 下窗口置顶显示但不激活,来源窗口保留焦点和选区。
    • 窗口显示期间使用 Windows 低级键盘钩子(WH_KEYBOARD_LL)读取字母、数字、退格及控制键,在输入法处理前接收并拦截,短命令不会输入到来源应用。
      • 关闭、执行命令、窗口销毁或应用退出时解除钩子;执行失败重新显示时恢复钩子。
      • 模拟复制按键不被钩子拦截。macOS/Linux 保留聚焦窗口后的 DOM 输入及快捷键监听。
      • Windows 钩子和 DOM 按键入口共用 Escape、Tab/F1、F2、F3 的处理;DOM 中 Tab/F1 仅在命令输入框内切换目标,其他控件保留正常焦点导航。
    • 从主窗口打开时复制该窗口保留的选区。
  • 短命令仅在 Quick Cmd Form 窗口内输入执行;命令面板保留打开窗口的 quickCmdForm.open,快捷键设置保留 quickCmdForm.toggleWindow。
    • 不再注册每个短命令对应的命令面板命令,也不提供主窗口直接执行短命令的 API。
    • 已有短命令自定义快捷键或命令历史不再提供直接执行入口,请先打开窗口再输入短命令。
    • 界面、代码标识符及命令 ID 统一使用 Quick Cmd Form 命名。
    • 打开窗口和全局热键的自定义配置使用上述两个命令 ID,不兼容旧命令 ID。
    • 相关源码及测试文件统一使用 quick-cmd-form 文件名前缀;冒烟验证入口为 npm run test:smoke:quick-cmd-form。
  • Esc 关闭窗口,Tab/F1 在命令输入框切换当前笔记和临时笔记,F3 执行 z。
  • 粘贴目标使用按钮显示当前值,鼠标每点击一次切换到下一个目标,无需激活窗口或展开下拉框;目标旁标注 F1,代码片段选项旁标注 F2。
  • 右上角最小化、最大化/还原和关闭按钮保持可用;关闭只隐藏 Quick Cmd Form,不退出应用。
    • Windows 使用不激活窗口的原生样式保留来源窗口焦点,同时保留正常标题栏操作。
    • 最小化时暂停命令按键监听;还原后继续监听,也可用 Quick Cmd Form 快捷键重新显示。
  • 命令开始执行时保持 Quick Cmd Form 可见,任务成功完成后再自动隐藏;失败时保留界面和错误信息,便于重试。
    • 底部状态栏显示当前步骤:获取源文件路径、复制选区、粘贴、保存比较对象、打开比较器或启动终端等。
    • 执行中显示活动进度指示,不显示无法准确计算的百分比;HTML 转换及图片导入的粘贴会等待实际完成确认后再隐藏。
    • 执行期间锁定命令输入、目标和代码片段选项,并暂停命令按键监听;原生窗口按钮仍可使用,手动关闭只隐藏界面,不取消正在执行的任务。
  • Code Snippet Paste(代码片段粘贴)默认关闭,可点击复选框或按 F2 切换;选项在应用重启后保留。
    • 开启后作用于 z、vv、da、o1/o2/o3,不改变搜索、比较等其他命令。
    • 先复制源文件绝对路径,再复制选区,以纯文本生成 Markdown 路径代码块,保留缩进并自动加长围栏以容纳代码中的反引号。
    • 从应用自身已保存的笔记采集时,使用来源笔记路径;未保存来源文件时路径留空。
    • Windows 外部 IDE 沿用旧版复制路径快捷键:Visual Studio、Notepad++ 使用 Alt+Shift+F,VS Code、JetBrains 使用 Alt+Shift+C,需要 IDE 支持对应绑定。
    • 无法获取路径或路径无效时不报错,路径位置留空,仍插入代码片段;稍后在开始围栏后补填路径,即可使用检查、整理和比较功能。
    • 路径留空的代码块按普通代码块处理,不参与现有路径代码片段操作;选区没有文本时仍提示错误。
    • 生成的顶层路径代码块可直接使用现有代码片段检查、整理和比较功能;不生成旧版外层标记。
    • 分隔符、标题前缀、当前/临时笔记目标和粘贴后的额外换行继续生效,主窗口保持后台状态。
  • 当前笔记在光标处粘贴并替换选区;临时笔记首次使用时创建,后续追加到同一标签末尾。
    • z、vv、da、o1/o2/o3 在后台插入,保持主窗口原有的隐藏、最小化或可见状态,不抢夺来源应用焦点。
    • 所有粘贴命令在粘贴内容后额外追加一个换行符,光标停在换行之后;原内容已有的末尾换行也予以保留。
    • HTML 转换、内部 Markdown 引用重写和图片导入完成后再追加换行,不把换行插到内容前面。
    • 只有 s(全文搜索)和 n(标题检索)主动显示并激活主窗口,以便查看和操作结果。
    • 其他命令不会主动显示主窗口;cm 和比较命令按用途打开终端或第三方比较器。
    • 临时笔记走普通文档保存与草稿恢复流程;关闭该标签后再次采集会新建标签。
    • 目标只读、收集器锁定或存在打开的对话框时拒绝插入,并显示原因。

15.1 短命令

命令 行为
h 切换并保存全局热键启用状态,复用设置中的热键开关。禁用后保留 Quick Cmd Form 启动热键,可再次打开并输入 h 恢复其他热键;菜单和命令面板也可操作。
s 复制选中文本,填入常规笔记库全文搜索。
n 复制选中文本,在快速打开中检索全库标题节点;优先提取旧 <<node: 标题>> 标记。
z 复制并粘贴到目标笔记,不加分隔符;复用现有 HTML 转 Markdown、图片导入及粘贴规则。
vv 复制选中文本并以纯文本粘贴到目标笔记,保留原始文本中的空白和 Markdown 字符,不转换 HTML。
da 复制并粘贴,前置 Markdown 分隔符 --- 和空行。
o1/o2/o3 复制并粘贴,前置空行及对应 Markdown 标题前缀 #/##/###。
cc 清空主进程及应用窗口的控制台显示,保留磁盘日志。
cm 将选中的绝对目录路径作为工作目录打开 Windows cmd.exe;目录内容不作为 shell 命令执行。
q1/q2 保存第一/第二个比较对象;现有文件或目录直接复用路径,其他文本写入 UTF-8 临时快照。
q3 保存第二个比较对象后立即比较。
qq 比较已经保存的两个对象,不重新复制或覆盖第二项。

15.2 比较工具与错误处理

  • 全局热键开关不禁用 quickCmdForm.toggleWindow,但仍遵守它的自定义键位、平台覆盖和显式移除配置。

    • 配置草稿无效时,关闭开关仍会注销其他热键,并保留当前已注册的 Quick Cmd Form 启动键位。
  • 比较优先复用设置中的“外部冲突工具命令”,以两个独立路径参数启动文件、文本或目录比较。

    • 两项比较不使用四项冲突合并参数模板;原有冲突解决流程保持不变。
    • macOS Beyond Compare 仍复用已有 bcomp 可执行文件解析规则。
    • 未配置工具时,文件和文本比较沿用 VS Code;目录比较提示先配置外部冲突工具。
  • 比较对象保存在本次应用进程内,退出后需重新设置;临时快照退出时尽力清理。

  • 复制失败时拒绝使用旧剪贴板,恢复之前的文本、HTML、RTF 和图片内容。

  • 短命令窗口显示执行错误并允许重试;命令面板直接执行时通过应用通知显示错误。

AGENTS

README

点赞(0) 阅读(41) 举报
目录
标题