我已在日常使用的 Emacs 31 变更
摘要
Emacs 31 引入了 tree-sitter 的改进,简化了语法安装,并新增了一个内置的 markdown-ts-mode。作者一直在开发分支上日常使用这些变更。
<p><a href="https://lobste.rs/s/b0mp2e/changes_emacs_31_i_m_already_daily_driving">评论</a></p>
查看缓存全文
缓存时间: 2026/06/18 05:59
# Emacs 31 即将到来:我已日常在用的那些变化
来源:https://www.rahuljuliato.com/posts/emacs-31-around-the-corner
Karthik Chikmagalur 最近发表了另一篇精彩的《*"Even More Batteries Included with Emacs"*》(https://karthinks.com/software/even-more-batteries-included-with-emacs/),深入探讨了 Emacs 已经自带的一些不那么为人所知的功能。我想写一篇它的镜像。他的文章讲的是已经装在盒子里的电池。而我的文章讲的是即将在 Emacs 31 中到来的那些。
Emacs 31 尚未发布,但我一直从 `emacs-31` 分支和 `master` 构建它,并且已经日常使用了几个月。每当有新的有用功能落地,我就把它整合到 [Emacs Solo](https://github.com/LionyxML/emacs-solo)(我的无外部包配置)中,并用一个小小的 `; EMACS-31` 注释标记,以便在正式发布后重新审视。
这篇文章就沿着这些面包屑展开。下面的每项变化都是我当前配置中正在使用的,并附有说明其功能以及我保留它的原因。所有这些都不需要任何包。它们要么已经在 `master` 上,要么很快就要同步。
一个免责声明:Emacs 31 仍在开发中(实际上处于预发布阶段),因此在最终发布之前,名称和默认设置可能会有变动。以下所有内容都是我在 2026 年中期运行的情况。如果你不是从 `emacs-31` 分支或 `master` 构建的,请将此视为对即将到来的功能的预览。
## 开箱即用的 Tree-sitter
如果要选出一个我最开心的变化,那就是这个了。多年来,要让一个 `*-ts-mode` 运行起来,需要手动填充 `treesit-language-source-alist`、调用 `treesit-install-language-grammar`,并祈祷你的工具链能编译语法。在 Emacs 31 中,很多这些繁琐步骤都消失了:
将 `treesit-enabled-modes` 设为 `t` 会切换到拥有 tree-sitter 变体的主要模式,而 `treesit-auto-install-grammar` 使得 Emacs 在缺少语法时主动提供获取和构建语法,而不是直接报错。这就像是 `treesit-auto` 包的体验,只不过现在核心完成了这项工作。
这个连锁反应体现在我配置的各个地方。我以前需要保留这样的行来告诉 Emacs 每个语法所在的位置:
在 Emacs 31 中,TypeScript、TSX、Rust、TOML、YAML 和 Dockerfile 等语言的语法源已经包含在模式本身中,所以我有一串 `;; EMACS-31 这现在在模式代码中定义了` 的注释,标记了所有一旦 31 发布就可以删除的代码块。用更少的配置做同样的工作,我举双手赞成。
emacs_31 demo 01
还有更多 tree-sitter 的改进即将到来。开发者们一直在不知疲倦地工作,Yuan Fu 和其他许多人在多个方面持续改进 tree-sitter 的体验。从更好的语言支持到可用性和性能增强,Emacs 中的 tree-sitter 正以惊人的速度发展。
## 内置的 markdown-ts-mode(实验性)
Emacs 31 自带了一个 `markdown-ts-mode`,这个功能对我来说意义重大。它是我发起的。它源于我在 2025 年初向 [emacs-devel](https://lists.gnu.org/archive/html/emacs-devel/2025-02/msg00810.html) 发送的一个提案,其中想法和代码的第一个版本都出自于我。
如果让你觉得这是我一个人的功劳,那就是对这个模式的不公了。**Stéphane Marks** 后来出现,撸起袖子,成为了该模式的共同作者。他是让这个模式今天这么好用的主要推动力。他并没有发一两个补丁就走人;他留了下来,推动这个模式远远超出了我最初的构想,并精心打磨那些将“能用”变成“好用”的细节。我即将夸耀的许多改进都是他的功劳。这个模式现在是我们*共同*的,也变得更好了。
看着一个想法从邮件列表的消息一路走到核心代码,并在此过程中收获一位优秀的合作者,这是我在 Emacs 社区中最有收获的经历之一。
它提供的远不止颜色,下面是我想要展示的部分:
✔️ **Org 用户会感到宾至如归。** 键绑定和编辑感受与 Org 非常接近:导航标题、折叠章节、在结构元素之间移动。如果你的手指熟悉 Org,你不需要重新学习 Markdown。
✔️ **实时的、彩色代码块,即使是那些没有 tree-sitter 的语言。** 这是我最喜欢的花招。一个围栏代码块会使用该语言的*真实*主要模式进行字体锁定,而不是被当作扁平的等宽文本。它也能访问 Emacs 自己的内部模式,所以一个 ```elisp` 代码块会用真正的 Emacs Lisp 字体锁定亮起,其他内置模式也是如此。无需额外设置,就能在代码示例中获得正确的语法高亮。
✔️ **内联图像查看。** 图像链接会在缓冲区中渲染,因此带有截图或图表的 Markdown 文档读起来就像一份文档,而不是一堆 `\![]\(path)` 噪音。
还有更多功能有待发现和开发。
这些一起让它在 Emacs 内部成为一个舒适的*写作*和阅读 Markdown 的地方,而不仅仅是一个附着在 `.md` 文件上的语法高亮器。
有一个注意事项我想坦诚相告: `markdown-ts-mode` 仍然是*实验性*的,你需要主动选择使用它。正如 `markdown-ts-mode.el` 的文件头所注,它还没有连接到 `auto-mode-alist`,因此它不会自动接管 `.md` 文件。目前你需要用 `M-x load-library RET markdown-ts-mode` 引入库,然后在缓冲区中启用它,或者如果你胆子大,也可以自己将其添加到 `auto-mode-alist` 中。
Stéphane 和我正在努力让它在下一个 Emacs 版本中被视为*准备好*,这就是你发挥作用的地方。如果你尝试后发现存在粗糙的边缘,或者它工作得很好,我们都想听听。请通过 `M-x report-emacs-bug` 向 [bug 列表](https://debbugs.gnu.org/cgi/pkgreport.cgi?package=emacs) 发送反馈,或者直接联系我和 Stéphane。真实世界中的使用才能将一个模式从“实验性”推向“完成”,所以不要害羞。
emacs_31 demo 02
更多截图请点击[这里](https://github.com/LionyxML/markdown-ts-mode-lab/tree/main/demo)。
## Eglot 使用 markdown-ts 渲染文档(仍然是实验性的)
说到 Markdown,Emacs 31 中的 Eglot 可以使用相同的内部模式来渲染 LSP 文档,而不是回退到纯文本:
`markdown-ts-view-mode` 让你获得格式化的悬停文档,而无需引入任何额外内容。这里同样适用*实验性*的注意事项,因为它依赖于 `markdown-ts-mode`,所以请将其视为需要主动选择的功能,而不是一个成品默认设置。我还关闭了 `eglot-code-action-indications`。新的内联“你在这里可以执行代码操作”提示很聪明,但某些语言服务器会让它们变得很嘈杂,所以我选择关闭。
emacs_31 demo 03
这里也有一些变动:`eglot-events-buffer-size` 正在被 `eglot-events-buffer-config` 取代,所以我在旧变量上留下了一个 `;; EMACS-31 -- 我们还需要它吗?`的注释,以便以后清理。
## 光标处的 eldoc
一个我比较喜欢的小功能:
启用后,eldoc 会显示光标下任何内容的帮助文本,无需我调用任何东西。与 `eldoc-echo-area-prefer-doc-buffer` 配对使用时,它让浏览不熟悉的代码感觉更有指导性。
## 更智能、更积极的补全
迷你缓冲区和补全机制获得了一些新的开关:
`completion-eager-update` 和 `completion-eager-display` 会在你输入时刷新补全界面,而不是等你来请求。如果你没有运行像 icomplete 这样的工具,将积极显示设置为 `t` 本身就能提供一个令人满意的开箱即用体验。而将 `minibuffer-visible-completions` 设为 `'up-down` 可以让你用方向键在可见候选项之间移动,这终于感觉很自然了。
icomplete 也得到了关注,这是另一个我有直接参与的功能。Emacs 31 包含了来自 [bug#75784](https://lists.gnu.org/archive/html/bug-gnu-emacs/2025-03/msg02638.html) 的补丁,这是我提出并参与完成的。它为 icomplete 带来了垂直的*缓冲区内部*行为和前缀指示器。我喜欢的副作用是:我之前配置中一个大的兼容性块终于可以删除了:
## 窗口布局操作
这是一组有趣的命令,用于重新排列窗口布局,而无需手动分割和关闭窗口:
转置会交换你的水平和垂直排列,旋转会旋转整个布局,翻转命令则会左右或上下镜像布局。如果你曾经构建了一个三窗口布局,然后又希望编辑器窗格在另一侧,这些命令就能搞定,而且在操作时会保持每个缓冲区不动。
## 停留在侧边窗口中的 Speedbar
Speedbar 已经存在很久了,但在 Emacs 31 中,它学会了驻留在一个合适的侧边窗口中,而不是一个独立的框架:
`speedbar-window` 将它停靠在侧面,像一个现代的文件树一样。在平铺桌面或多显示器笔记本上,这比旧的浮动框架行为好太多了。宽度上限防止它与其他窗口争夺空间。
emacs_31 demo 04
## VC 的贴心改进
有几个版本控制的改进我已经愉快地启用了:
`vc-dir-hide-up-to-date-on-revert` 是我最满意的一个。现在刷新一个 `vc-dir` 缓冲区会自动隐藏已是最新的文件,所以我再也不需要我那绑定到 `g` 键的黑科技了——它先调用 `vc-dir-refresh` 再调用 `vc-dir-hide-up-to-date`。又一个可以标记删除的块。`vc-allow-rewriting-published-history` 则是对像 Jujutsu 以及强制推送功能分支这类工作流的承认,在这些场景中,重写已经推送的历史是一种有意的操作。
## 可编辑的 xref 缓冲区
这个不是一个变量,而是我配置中的一个注释,提醒我*删除*一个自定义黑科技:
我想让自己多说一点这个功能,因为我参与了其中,它也展示了功能是如何进入 Emacs 的。
痛点是这样的。Dired 和 grep 缓冲区一直以来都有一种“编辑”工作流。在 Dired 中你可以切换到 `wdired-mode`;在 grep 缓冲区中按 `e` 进入 `grep-edit-mode`。批量重命名和批量搜索替换在那里很自然。但 xref 缓冲区没有这样的功能。唯一的编辑操作是 `r`(`xref-query-replace-in-results`),它只能做正则替换,不允许你编辑单行。我严重依赖 `project.el` 和 xref 来导航和重构代码,我发现自己经常为了得到一个可编辑的缓冲区而用 `M-x grep` 重新执行相同的搜索。这是一个烦人的弯路,因为 xref 已经拥有所有所需的信息了。
所以在 2026 年 3 月,我向 `bug-gnu-emacs` 发送了一个补丁,提议一个小命令 `xref-export-to-grep`,绑定到 `*xref*` 缓冲区中的 `E`。它会重新获取 xref 项,格式化为 `file:line:content`,然后将它们放到一个 grep-mode 缓冲区中,在那里你可以按 `e` 并按通常方式编辑。没什么花哨的。它只是连接了两个已经存在的功能,我作为个人片段已经携带了一段时间了。
接下来发生的事情正是我热爱这个社区的原因。维护 xref 的 Dmitry Gutov 看了之后,对我方法的*用户界面*提出了异议。我的命令在缓冲区之间创建了一个跳转,一旦你进入 grep 缓冲区,你还得知道要按哪个键。他提出了一个比我回答的更加尖锐的问题:我是在乎 grep 导出,还是说如果 **xref 缓冲区让你直接内联编辑**会更好?
这个重新思考是对的。我告诉他,我对 grep 这个弯路没有执念。在 xref 缓冲区本身内联编辑,并支持跨匹配项的多行编辑,可以省去整个来回过程。几天后,他编写并推送了 `xref-edit-mode`。它去掉了多余的步骤,并且在大型 xref 缓冲区上运行得更快。我最初的 `xref-export-to-grep` 仍然可以作为可选命令加入,但没有默认绑定,但内联模式是更好的答案,也是我现在使用的。
讨论并没有就此停止。它引发了一场与 Juri Linkov 关于 `*-edit-mode` 系列(occur/grep/xref,它们正常写入每个缓冲区)与 `wdired` 的“全部排队再按 `C-x C-s`”模型之间更广泛的设计对话,以及未来“实时”搜索界面是否可能以不同方式呈现结果。作为记录,这是我那次讨论中提到的安全网,一个我从 Protesilaos 那里学到的技巧,让我在 `save-some-buffers` 期间可以在保存之前按 `d` 将缓冲区与文件进行差异比较:
回到主题,最终结果:Emacs 31 提供了可编辑的 xref 缓冲区,我的配置中删除了一个自制的变通方案,落地的功能比我提出的更好,因为维护者问了正确的问题。能在这个循环中扮演一个小角色,是我喜欢生活在 `master` 上的很大一部分原因。如果你好奇,完整的来回讨论可以在 [bug#80616](https://debbugs.gnu.org/cgi/bugreport.cgi?bug=80616) 公开查看。
所以,如果你想尝试一下。在 `C-x p g` 之后,搜索类似 `FontAwesomeIcon` 的内容。现在按 `e` 启动编辑模式,进行你的编辑,然后按 `C-c C-c` 确认。
emacs_31 demo 05
## ERC 变得更整洁
一些 IRC 的改进,因为我平时用 ERC:
这使得 ERC 只在新打开的目标缓冲区中插入之前的日志,这是我在重新加入频道时想要的行为。还有我最喜欢的一个小修复:在 Emacs 31 中,`scrolltobottom` 模块不再依赖于 `erc-fill-wrap`,所以我可以删除那些为了旧版本手动添加它的条件性代码。感谢解开这个纠结的人。
## 生活质量调节旋钮的杂项
然后是一长串小的改进,它们不需要每个都单独一节,但绝对值得占有一席之地:
其中几个值得一句话说明:
✔️ **`kill-region-dwim`** 修复了一个几十年的小毛病。将其设为 `'emacs-word`后,在没有活动区域的情况下按 `C-w` 会向后删除一个词,而不是报错。不再有“mark is not active”的中断了。
✔️ **`view-lossage-auto-refresh`** 将 `C-h l` 变成一个显示你最近按键的实时视图。当我进行屏幕共享或教学时,人们可以实时看到我按下的键。
✔️ **`ielm-history-file-name`** 让我的 IELM 临时缓冲区能在重启后保留,就像 `comint` 和 shell 已经能做到的那样。
✔️ **`native-comp-async-on-battery-power nil`** 节省笔记本电量:当我在火车上拔掉电源时,不会有后台原生编译引起的意外风扇旋转。
✔️ **`tty-tip-mode`** 将工具提示带到终端,这对于那些在 `-nw` 下运行 Emacs 的人来说是一个很好的点缀。
## 荣誉提名:term 不再吞行
这个没有配置行,因为没什么可配置的。一个 bug 被修复了,它带来的快乐远超其应有的程度。
长期以来,`term`(和 `ansi-term`)有一个讨厌的习惯:*吞行*。全屏、光标寻址程序会让显示变得混乱,当程序重绘时,行会被吃掉或放错位置。这正好影响了你最需要真正终端来运行的程序:`htop`、`nethack`,任何基于 curses 的程序在 Emacs 的终端内几乎无法使用。
Emacs 31 修复了这个问题。`term` 现在能正确重绘了,我可以运行 `htop` 来监视进程,或者打开 `nethack` 来个“快速”休息,而不会让缓冲区变成五彩纸屑。听起来很小,但它消除了我不得不转向外部终端模拟器的最后一个原因之一。
emacs_31 demo 06
emacs_31 demo 07
## 荣誉提名 2:Modus 5 主题!
感谢 Protesilaos,Emacs 现在自带了几个 modus 主题:
✔️ `modus-operandi-deuteranopia`——针对绿色盲优化的主题,白色背景。
✔️ `modus-operandi`——优雅、高可读性的主题,白色背景。
✔️ `modus-operandi-tinted`——优雅、高可读性的主题,浅赭色背景。
✔️ `modus-operandi-tritanopia`——针对蓝黄色盲优化的主题,白色背景。
✔️ `modus-vivendi-deuteranopia`——针对绿色盲优化的主题,黑色背景。
✔️ `modus-vivendi`——优雅、高可读性的主题,黑色背景。
✔️ `modus-vivendi-tinted`——优雅、高可读性的主题,黑色背景。
相似文章
Emacs 31 即将到来:我日常使用的变化
Emacs 31 即将到来,带来了更简单的 tree-sitter 配置和内置的 markdown-ts-mode 等改进。本文详细介绍了作者在开发分支中使用的一些特性,强调了配置工作量的减少。
软件界的Emacs化
作者讲述了在终端中阅读 Markdown 的烦恼,并描述了如何使用 Claude 快速构建一个自定义的 macOS Markdown 查看器(MDV.app),展示了 AI 如何让人能够迅速创建个人软件工具。
Emacs 的更多内置功能
一篇博客文章,介绍了Emacs中不太为人所知但实用的内置功能,延续了一个旨在提高原版Emacs功能可发现性的系列。
离开 Magit 后的 Emacs
作者讲述了他们离开 Emacs 的 Magit Git 界面,转而采用 VC-mode 和自定义 Git 脚本等替代方案的经历,重点介绍了其中的调整和所学到的经验教训。
还有人用 Emacs 吗?
作者对与 Emacs 数十年关系的个人反思,包括转向 VSCode 和 IntelliJ,最终因其独特功能回归 Emacs。