☰
Onivim 2 0.5.2 / 0.5.1 发布解读:Vim 风格面板导航、自动换行与 fzy 模糊匹配的落地实践
2026/9/27 9:38:34 网站建设 项目流程
  • 开发工具
  • 代码编辑器
  • 桌面应用

【免费下载链接】oni2

Native, lightweight modal code editor

项目地址:https://gitcode.com/gh_mirrors/on/oni2
点击查看免费下载

2021 年 1 月发布的 Onivim 2 0.5.2(连同 2020 年 12 月未正式公告的 0.5.1)是该项目迈向 0.6.0 里程碑的关键月度版本,集中交付了 Vim 风格跨面板导航、:!命令输出 UI、自动换行、自动更新、基于 fzy 的模糊匹配、可定制行高与 Windows ANGLE 渲染兼容等能力。本文以该版本公告为主体,结合当前仓库的配置与源码实现,逐项拆解这些功能的配置方式、操作方法与底层原理,帮助读者理解并直接上手验证。

版本发布概览

Onivim 2 是一个原生、轻量的模态(modal)代码编辑器,其核心卖点是把 Vim 的操作模型与现代编辑器的 UI、VSCode 扩展生态结合起来。0.5.2 与 0.5.1 作为连续的两个月度版本,功能亮点覆盖了日常编辑体验的多个维度:

  • Vim 风格导航(文件浏览器、搜索侧栏、符号大纲视图)
  • :!外 shell 命令输出在编辑器内的展示
  • 自动换行(word-wrap)支持
  • Windows / OSX 自动更新基础设施
  • fzy 模糊匹配算法集成
  • 全文件类型关键字补全
  • 可定制编辑器行高
  • Windows 上基于 ANGLE 的渲染兼容
  • OSX 首次运行体验优化
  • VSCode 扩展宿主与 Vim 内核的系列修复

下文按功能逐节展开,并在每节给出仓库中对应的配置项与源码位置,便于读者按图索骥。

Vim 风格跨面板导航

0.5.2 为多个 UI 元素接入了 Vim 风格的导航模型,包括:

  • 文件浏览器(file explorer)
  • 搜索侧栏(search sidebar)
  • 符号大纲视图(symbol outline):在普通模式下通过gO打开(前提是当前语言扩展提供了文档符号 DocumentSymbols 数据)

这些面板统一支持CTRL-W+h/j/k/l的方向键绑定在面板间移动焦点,并支持大量 Vim 惯用的导航与滚动命令,如gg、G、zz、zb、zt等。

从源码看,这套交互由统一的树形组件驱动:在 src/Feature/Explorer/Feature_Explorer.re 中,symbolOutline字段就是一个Component_VimTree(~rowHeight=20),而focusOutline函数会切换焦点并置isSymbolOutlineExpanded为implicitlyOpen;面板收到按键事件后直接调用Component_VimTree.keyPress(key, model.symbolOutline)完成导航,符号选中则派发SymbolSelected(DocumentSymbols.symbol)消息。也就是说,gg/G/zz这类动作并不是为某个面板单独实现的,而是树组件提供的通用能力,文件浏览器、搜索结果与符号大纲因此获得一致的键盘体验。

符号大纲的数据来源是扩展宿主(Extension Host)的provideDocumentSymbols请求,实现在 src/Exthost/Request.re,其返回的DocumentSymbols.symbol结构直接喂给大纲树。这解释了公告中"当语言扩展提供该能力时可用"的前提。

:!命令输出 UI

本次版本为 bang 命令:!增加了输出展示支持:执行外部 shell 命令后,其标准输出不再只落在终端日志里,而是可以在编辑器 UI 中查看。对于依赖:!跑构建、格式化或临时命令的 Vim 用户,这一改动让 Onivim 2 在 Ex 命令行为上更贴近原生 Vim 的交互预期。

自动换行(Word-wrap)支持

自动换行是本次公告明确标注"Finally"的功能,配置方式有二:

  1. 配置项方式:"editor.wordWrap": true(布尔值)
  2. Vim 命令方式::set wrap与:set nowrap

在仓库中该配置的实现位于 src/Feature/Editor/EditorConfiguration.re:

let wordWrap = setting("editor.wordWrap", ~vim=VimSettings.wrap, wordWrap, ~default=`On); let wordWrapColumn = setting("editor.wordWrapColumn", int, ~default=80);

几点值得注意的细节:

  • 默认值为On(与公告示例中"设置为 true"的提法一致,布尔true解码为On)。
  • 配置键通过~vim=VimSettings.wrap与 Vim 的wrap设置双向绑定,因此:set wrap/:set nowrap与配置文件中的editor.wordWrap是同一状态的两种表达。
  • 解码器wordWrapDecode(同文件第 42–65 行)同时接受布尔值与字符串值:true/false,以及"on"/"off"(其他字符串一律按Off处理),保证配置文件的书写宽容度。
  • 配套的editor.wordWrapColumn默认 80,用于控制换行列位置。
  • 渲染端在 src/Feature/Editor/Editor.re 与 L577 处根据EditorConfiguration.wordWrap.get(config) == \On` 决定是否进入换行布局路径,实现层面由编辑器视图的换行排版逻辑承担。

自动更新(Auto-update)

0.5.2 通过 Sparkle Framework 为Windows 与 OSX接入了自动更新能力,公告将其描述为基础设施级别的进展,更新界面会提示用户下载新版本。Linux 侧的方案仍在调研中,公告提到了 AppImageUpdate 与 Snap store 两条候选路线,属于当时未定的开放事项。

值得注意的是,本仓库内确实保留了 Sparkle 相关的桥接代码:目录 src/oni2-sparkle 包含.c/.h与 Reason 绑定文件,用于在 Onivim 2 中调用 Sparkle 的更新检查与安装流程,这与公告所述"OSX 上通过 Sparkle 集成自动更新"相互印证。

模糊匹配改进:集成 fzy

此前 Onivim 2 的模糊匹配算法在匹配精度与性能上都有瓶颈。0.5.x 系列通过为fzy编写 ReasonML / OCaml 包装库(reason-fzy),将 fzy 的评分与命中位置算法引入编辑器,显著改善了两方面:

  • 匹配准确度:对子序列命中、连续命中、首字母命中等的打分更合理;
  • 性能:搜索响应更快,适合在键入过程中实时过滤大量候选。

模糊匹配在 Onivim 2 中的三个典型应用场景为:

  • QuickOpen 快速打开(Control+P/Command+P)
  • 命令面板 Command Palette(Control+Shift+P/Command+Shift+P)
  • 补全项的模糊匹配

仓库中该集成的核心在 src/Core/Filter.re:rank函数对候选列表逐项格式化后调用Fzy.fzySearchList(searchStrings, query, ()),再按result.original_index还原到原始条目,并通过match.positions生成高亮区间、match.score保留评分。返回结果{item, highlight, score}被 QuickOpen 与补全列表共用,这也解释了公告中"既用于 QuickOpen 又用于补全"的描述。score同时被作为排序依据,确保最相关的候选排在最前。

关键字补全(Keyword completion)

在 0.5.1 之前,Onivim 2 只支持来自语言扩展的补全;0.5.1 起,所有文件类型都获得了基于缓冲区内容的关键字补全。也就是说,即使没有安装对应语言的补全提供方,用户依然可以基于当前打开文件的词汇获得基础补全提示,这大幅降低了日常编辑对扩展的依赖。

可定制的编辑器行高

行高此前是写死的,0.5.x 将其开放为配置项:

  1. 配置项方式:"editor.lineHeight"
  2. Vim 命令方式::set linespace

实现上,该配置位于 src/Feature/Configuration/GlobalConfiguration.re,通过~vim=VimSettings.lineSpace与 Vim 的linespace关联;而VimSettings.lineSpace(同文件第 225–231 行)把 Vim 的整数值linespace映射为LineHeight.padding,默认值为LineHeight.default。

行高类型定义在 src/Core/LineHeight.re 中,支持三种取值形态:

形态含义示例
Proportional(float)按字体测量高度的倍数计算,lineHeight = 字体高度 × size{ "proportional": 1.2 }
Absolute(float)固定像素高度{ "absolute": 24 }
Padding(int)在字体高度之上增加像素内边距,lineHeight = 字体高度 + padding{ "padding": 4 }

值得注意的默认与解码细节:

  • 默认值LineHeight.default = proportional(1.2),即 1.2 倍字体行高;
  • 配置解码器支持直接写一个浮点数:justFloat规定数值 ≥ 5 时按Absolute(绝对像素)解释,否则回退到Proportional(1.2)默认值,兼顾了"直接写像素"与"防呆回退"两种需求;
  • 渲染侧通过LineHeight.calculate(~measuredFontHeight)将三种形态统一换算为像素,并广泛用于 src/Feature/Editor/Draw.re 的绘制逻辑(光标、选区、装饰等均以行高为基准布局),因此行高的变化会整体影响编辑器的垂直排版。

:set linespace与editor.lineHeight的桥接意味着两种写法最终落到同一个行高模型上,用户按习惯选择即可。

Windows 渲染兼容:ANGLE

公告指出一个 Windows 上的实际问题:OpenGL 在 Windows(尤其是虚拟机)中的驱动支持远不如 DirectX 成熟,部分环境只有 OpenGL 1.0,而 Onivim 2 需要 3.0+,导致启动崩溃或黑屏。为此 0.5.x 引入了ANGLE——一个以 DirectX 为后端实现的 OpenGL API 层。通过 ANGLE,Onivim 2 在不改上层渲染代码的前提下,借用 DirectX 更完善的驱动、硬件与平台支持,显著改善了 Windows 兼容性。这一改动是渲染管线的底层替换,用户无需任何配置即可受益。

OSX 首次运行体验

此前 OSX 用户首次启动 Onivim 2 会连续遭遇两个不必要的权限弹窗:一是通知权限,二是"访问 Documents 文件夹"的授权请求——后者源于旧逻辑默认自动打开 Documents 目录。0.5.x 移除了"启动即打开 Documents"的行为,改为默认不打开任何文件夹,从而消除了这条令人困惑的权限链路,让首次启动直接进入干净的编辑界面。

VSCode 扩展宿主修复

0.5.1 与 0.5.2 延续了对 VSCode 插件兼容性的持续投入,公告列出的代表性改进包括:

  • 新增 XML 语言扩展支持;
  • 扩展宿主(vscode-exthost)多次升级:1.46.0 → 1.47.1 → 1.50.1;
  • 修复 vscode-spell-checker 的阻塞问题;
  • 修复扩展搜索 / 下载过程中的多类错误;
  • 修复补全详情出错时的崩溃;
  • 为补全提供方增加additionalTextEdits(自动导入)支持。

这些改动共同指向一个目标:让越来越多依赖语言服务器与扩展 API 的 VSCode 插件在 Onivim 2 中开箱即用。扩展宿主相关的实现集中在 src/Exthost 目录(消息传输、请求/响应编解码与扩展 API 桥接都在此),测试用例则位于 test/Exthost。

Vim 修复与 VimL 插件进展

公告特别强调,Vim 侧的工作重点是为 VimL 插件(如 vim-surround)铺路,这暴露了底层 libvim 的一系列缺陷并逐一修复。0.5.x 中值得关注的修复包括:

  • 修复:enew崩溃;
  • 状态栏增加宏录制指示器;
  • 状态栏显示待处理的操作符(pending operator);
  • 修复可视模式内部运动(viw/vi")命令;
  • 修复退出插入模式后光标定位的抖动问题;
  • 实现getchar()处理器(VimL 插件支持的前提);
  • 接通:messages与:messages clearEx 命令;
  • 为插入模式命令处理计数(count)。

公告同时注明:getchar()的按键显示功能当时仍有一个已知 bug(按键序列cs(}能正确执行,但按键可视化无法捕获),插件支持"尚未到生产可用阶段",属于持续前进中的工作。

0.6.0 路线图与月度发布策略

公告披露了 0.6.0 里程碑的目标清单与计划调整:

  • 0.6.0 目标:VimL 插件集成、Snippet(代码片段)支持、Vim 代码折叠集成、Code Lens、Code Actions;
  • 计划调整:原定 2020 年 12 月底的 0.6.0 被推迟,改为"完成即发布"(When It's Done),期间以 0.5.x 月度版本持续迭代;
  • 优先级模型:0.6.0 之后,后续里程碑(0.7.0+)将依据社区投票最高的 issue 确定,日常开发则需要在里程碑目标、每日阻塞/崩溃、高票 issue、Vim 工作流、VSCode 扩展宿主工作流之间权衡。

对读者而言,这意味着 0.5.x 系列是通往完整插件生态的过渡版本,其每月的修复与基础设施(如自动更新、扩展宿主升级)都在为 0.6.0 铺路。完整的逐项变更记录可查阅仓库根目录的 CHANGES_CURRENT.md(对应发布时点的快照版本)。

总结

0.5.2 / 0.5.1 是一个典型的"体验完善型"月度版本:Vim 风格导航把键盘操作模型统一扩展到文件浏览器、搜索与符号大纲;自动换行与可定制行高补齐了编辑器排版的基础配置(对应editor.wordWrap/editor.lineHeight,并分别与:set wrap、:set linespace双向绑定);fzy 的引入从算法层面提升了 QuickOpen、命令面板与补全的匹配质量;ANGLE 与 Sparkle 则分别解决 Windows 渲染兼容与更新分发两个平台级问题。结合本仓库源码(EditorConfiguration.re、LineHeight.re、Filter.re、Feature_Explorer.re)可以确认,这些能力在代码中均有对应的配置定义、解码逻辑与调用链支撑,读者可按本文给出的键位与配置项直接上手验证。

  • 开发工具
  • 代码编辑器
  • 桌面应用

【免费下载链接】oni2

Native, lightweight modal code editor

项目地址:https://gitcode.com/gh_mirrors/on/oni2
点击查看免费下载

相关推荐

上一篇:渔人的直感:终极FF14钓鱼计时器完整指南
下一篇:Erlang/OTP epmd 端口映射守护进程完全指南:命令行选项、协议原理与集群配置

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询