3

我提出这个问题是因为我认为这个问题和可能的答案都可能有助于 Emacs 用户编写 Lisp 代码来定义font-lock-keywords. 我提供了一个我认为有帮助的答案。我也对其他答案感兴趣。

该变量的值是一个表达式列表,每个表达式都可以指定一个或多个要匹配的模式或执行匹配的函数,以及一个或多个用于突出显示匹配文本的面孔。价值的可能性font-lock-keywords是无数和复杂的。(描述这个的文档是 Elisp 手册 node Search-based Fontification。)

在大多数情况下,列表包含多个元素,这意味着多个正则表达式模式。这些可以以不同的方式进行交互。有些可以阻止其他人生效,或者他们可以改变其他人的效果。例如,我的库Dired+font-lock-keywords在 Dired 模式下定义了 31 个条目(正则表达式),其中许多是交互的。

如何保持所有这些正常?在定义或修改此类列表时如何调试 ?您可以注释掉除一个列表项之外的所有项目,以便在单独时查看其效果。然后重复另一个。然后也许将几个加在一起,也许以不同的顺序。我想有各种可能性,但你是做什么的?

(好吧,我知道大多数 Elisp 编码人员不会编写超级复杂font-lock-keywords的定义。但即使对于简单的定义,这也会变得复杂。也许如果这个过程更容易,那么用户就不会不必要地将自己限制为一两个条目。)

4

2 回答 2

6

你可以使用我新发布的Font Lock Studio。以下内容来自自述文件:

font-lock-studio - 字体锁定关键字的交互式调试器

Font Lock Studio是Font Lock 关键字(Emacs 语法高亮规则)的交互式调试器。

介绍

Font Lock Studio 允许您单步执行Font Lock 关键字——匹配器、突出显示和锚定规则,这样您就可以看到缓冲区字体化时会发生什么。您可以在规则上或规则内设置断点并运行直到命中一个。在规则内时,匹配使用背景颜色的调色板进行可视化。解释器可以用 纯文本英语描述规则。与Edebug的紧密集成允许您进入作为 Font Lock 关键字一部分的 Lisp 表达式。

使用调试器时,会显示一个界面缓冲区,其中包含所有关键字,用于匹配数据的导航和可视化。

当 Font Lock Studio 启动时,注释和字符串是预先着色的,因为它们是早期语法阶段的一部分 (Font Lock Studio 不支持)。

通过键入“Mx font-lock-studio RET”启动调试器。按? 或查看可用命令的菜单。

例子

对于使用 的缓冲区html-mode,接口缓冲区如下所示。其他主要模式通常具有越来越复杂的规则。左侧的箭头表示当前的活动位置。源缓冲区中的相应箭头放置在当前搜索位置。

        ========================
        === Font Lock Studio ===
        ========================
    --------------------------------------------------
=>  "<\\([!?][_:[:alpha:]][-_.:[:alnum:]]*\\)"
      (1 font-lock-keyword-face)
    --------------------------------------------------
    "</?\\([_[:alpha:]][-_.[:alnum:]]*\\)\\(?::\\([_:[:alpha:]]
    [-_.:[:alnum:]]*\\)\\)?"
      (1
       (if
           (match-end 2)
           sgml-namespace-face font-lock-function-name-face))
      (2 font-lock-function-name-face nil t)
    --------------------------------------------------
    "\\(?:^\\|[ \t]\\)\\([_[:alpha:]][-_.[:alnum:]]*\\)\\(?::
    \\([_:[:alpha:]][-_.:[:alnum:]]*\\)\\)?=[\"']"
      (1
       (if
           (match-end 2)
           sgml-namespace-face font-lock-variable-name-face))
      (2 font-lock-variable-name-face nil t)
    --------------------------------------------------
    "[&%][_:[:alpha:]][-_.:[:alnum:]]*;?"
      (0 font-lock-variable-name-face)
    --------------------------------------------------
    "<\\(b\\(?:ig\\|link\\)\\|cite\\|em\\|h[1-6]\\|rev\\|s\\(?:
    mall\\|trong\\)\\|t\\(?:itle\\|t\\)\\|var\\|[bisu]\\)
    \\([ \t][^>]*\\)?>\\([^<]+\\)</\\1>"
      (3
       (cdr
        (assoc-string
         (match-string 1)
         sgml-tag-face-alist t))
       prepend)
    ==================================================
    Public state:
      Debug on error     : YES
      Debug on quit      : YES
      Explain rules      : YES
      Show compiled code : NO

按空格单步浏览所有关键字。"n" 将转到下一个关键字,"b" 将设置断点,"g" 将运行到最后(或下一个断点),"q" 将退出。

特征

步进

您可以单步进入结束退出字体锁定关键字。完全支持锚定规则。此外,您可以运行到末尾或下一个断点。

断点

您可以在部分关键字上设置断点,例如匹配器(例如正则表达式)、突出显示规则或锚定突出​​显示规则内。

如果您想在断点处不停止的情况下单步执行或运行,请在命令前加上C-u.

请注意,在锚定规则中,您可以在整个规则或单个部分上设置断点。在前一种情况下,仅突出显示外括号。

匹配数据可视化

在执行关键字或锚定突出​​显示的匹配器后,匹配数据(无论搜索到什么)都使用源缓冲区、正则表达式中的背景颜色以及相应的突出显示规则或规则进行可视化。如果正则表达式的一部分或突出显示不匹配,则它不会着色,例如,当使用后缀正则表达式运算符时会发生这种情况?

请注意,内部匹配组优先于外部组。这可能导致突出显示规则获得的颜色未出现在正则表达式或源缓冲区中的情况。例如,匹配器 "\(abc\)" 将使用匹配 1 的颜色着色,而高亮规则 `(0 a-face)' 将使用匹配 0 的颜色。

规范化关键字

界面中显示的关键字已规范化。例如,而不是

     ("xyz" . font-lock-type-face)

关键字

      ("xyz" (0 font-lock-type-face))

显示。详情请参阅font-lock-studio-normalize-keywords

解说员

解释器与 Font Lock 关键字当前部分的人类可读描述相呼应。这可以帮助您理解规则中的所有nil:s 和t:s 的实际含义。

使用自动解释器时,Font Lock Studio 会在每个命令后回显解释。

Edebug——Emacs Lisp 调试器

与 Edebug 的紧密集成允许您在接口缓冲区中的关键字中嵌入单步表达式,并允许您在源文件中检测调用的函数以进行调试。

跟随模式感知

源缓冲区中的搜索位置通过覆盖箭头和更新点来可视化。如果源缓冲区在多个并排窗口中可见并且启用了跟随模式,则搜索位置将显示在合适的窗口中以最小化滚动。

于 2014-01-27T21:03:35.793 回答
0

为了帮助解决这个问题,我编写了一个Icicles 多命令icicle-font-lock-keywords. 它允许您执行以下操作:

  • 在单独的条目(模式)之间循环,单独font-lock-keywords应用它们以查看每个单独的效果。

  • 选择单个条目并分别应用它们,以查看相同的内容。

  • 选择一条目并应用它,以条目出现在的相同顺序font-lock-keywords。您可以对任意数量的集合执行此操作。

  • 按您选择它们​​的顺序累积多组条目的效果。

  • 还原,以查看所有条目一起的效果,即所有font-lock-keywords.

您可以按任何顺序在一次命令调用中完成所有这些操作。

M-oM-o I是 Facemenu 和字体锁定的前缀键,所以我在Icicle模式下将此命令放在 key 上。

于 2014-01-14T22:50:08.017 回答