如何找出键序列真正的作用


14

我不时观察到编辑文本时的意外行为。我的第一个方法通常是C-h k用来查找给定键序列正在调用的功能。但是,有时文档与观察到的行为不一致。在这些情况下,我通常假定其他软件包已挂接到该函数或键序列中,并且正在修改其行为。

我如何找出 哪些 功能挂接到我的按键序列中?

我最近遇到的一个示例是,我按下了"键,并且在活动区域​​的开始和结尾处都插入了引号。我怀疑这不是Emacs的默认行为,因此我过去常常C-h k "查明实际上是在调用什么函数。

describe-key文件告诉我,该函数self-insert-command被调用,这是一个内置的功能。长话短说,经过反复试验,我能够确定该行为是由引起的electric-pair-mode。将来,有没有比一次关闭一个可疑包裹直到找到罪魁祸首的结论更快的方法呢?


可能electric-pair-mode仅在某些主要模式下激活了吗?你仍然可以看到self-insert-command",当你做C-h kelectric-pair-mode被激活?
Kaushal Modi 2014年

@kaushalmodi:事实证明,该方法electric-pair-mode可以通过挂钩post-self-insert-hook而不是通过更改键绑定来实现。
nispio 2014年

C-h k告诉您按键的确切情况。如果查看的文档self-insert-command,则很清楚地说post-self-insert-hook该命令在命令完成后运行。
shosti

@shosti:在这个简单的例子中,是的。但是,如果扩展程序使用after-change-functions乔丹在回答中提到的怎么办?函数的文档可能不会特别提及该钩子,是吗?
nispio

抱歉,我应该更具体一些。C-h k+标准钩子==完整的行为(或多或少)。当然,有时会留下很多可能性,但是它比我所知道的任何其他复杂软件系统都透明得多。
shosti

Answers:


13

没有一种简单的方法可以确切地知道单个按键将执行的操作。

如果看到其他行为,请始终检查通用钩子。请参阅此处的列表:http : //www.gnu.org/software/emacs/manual/html_node/elisp/Standard-Hooks.html

在大多数情况下,重要的是:

  • 变更后功能
  • 变更前功能
  • 首次挂机
  • 命令钩后
  • 命令前挂机
  • 自我插入后钩

您需要检查这些钩子,并查看它们包含的功能,以查看哪个钩子正在修改您的行为。

如果这些挂钩中的功能不能完全描述所观察到的行为,请查看这些功能以获取建议,这些建议将在参考资料中显示describe-function


编辑:我已经编写了一些函数来帮助描述一个钩子,而不是一个接一个地更好地描述钩子:https : //gist.github.com/jordonbiondo/bad03e44bb053db0f1eb 可以describe-hook像其他描述函数一样使用在那里定义。这是它的输出示例:

这是所有代码,以防主意消失:

(defun guess-all-hooks ()
  "Return a list of all variables that are probably hook lists."
  (let ((syms '()))
    (mapatoms
     (lambda (sym)
       (if (ignore-errors (symbol-value sym))
           (let ((name (symbol-name sym)))
             (when (string-match "-\\(hook[s]?\\|functions\\)$" name)
               (push sym syms))))))
    syms))

(defun face-it (str face)
  "Apply FACE to STR and return."
  (propertize str 'face face))

(defun describe-hook (hook)
  "Display documentation about a hook variable and the
functions it contains."
  (interactive
   (list (completing-read
          "Hook: " (mapcar (lambda (x) (cons x nil)) (guess-all-hooks)))))
  (let* ((sym (intern hook))
         (sym-doc (documentation-property sym 'variable-documentation))
         (hook-docs (mapcar
                     (lambda (func)
                       (cons func (ignore-errors (documentation func))))
                     (symbol-value sym))))
    (switch-to-buffer
     (with-current-buffer (get-buffer-create "*describe-hook*")
       (let ((inhibit-read-only t))
         (delete-region (point-min) (point-max))
         (insert (face-it "Hook: " 'font-lock-constant-face) "\n\n")
         (insert (face-it (concat "`" hook "'") 'font-lock-variable-name-face))
         (replace-string "\n" "\n\t" nil
                         (point)
                         (save-excursion
                           (insert "\n" sym-doc "\n\n")
                           (1- (point))))
         (goto-char (point-max))
         (insert (face-it "Hook Functions: " 'font-lock-constant-face) "\n\n")
         (dolist (hd hook-docs)
           (insert (face-it (concat "`" (symbol-name (car hd)) "'")
                            'font-lock-function-name-face)
                   ": \n\t")
           (replace-string "\n" "\n\t" nil
                           (point)
                           (save-excursion
                             (insert (or (cdr hd) "No Documentation") "\n\n")
                             (1- (point))))
           (goto-char (point-max))))
       (help-mode)
       (help-make-xrefs)
       (read-only-mode t)
       (setq truncate-lines nil)
       (current-buffer)))))

这是否意味着在建议功能时,文档会自动更新以反映更改?
nispio 2014年

我不知道实际的属性是否得到更新,但是更新的返回值documentation可以反映出来。
Jordon Biondo

1
@nispio是的,是的。
马拉巴巴2014年

1
我认为,可以将gist.github.com/jordonbiondo/bad03e44bb053db0f1eb中的代码/功能 包括在答案中。我认为SE答案的上限是30,000个字符。
Faheem Mitha 2014年

4

也许不是您问题的完整答案,但是该软件包 helm-descbinds可帮助您从快捷方式的ascii表示中搜索所有已定义的键盘绑定。对于每次匹配,它都会向您显示与键盘快捷键关联的交互功能,您可以要求对其helm-descbinds进行描述,也可以直接从搜索结果中执行

在此处输入图片说明

这是GitHub站点上的软件包描述:

Helm Descbinds提供了与emacs的describe-bindings的接口,使当前活动的键绑定可与helm交互地进行搜索。

此外,您还有以下操作

  • 执行命令
  • 描述命令
  • 查找命令

并且C-z将为您提供当前命令的持久描述。


2
这很棒。我一定会绑定到C-h b。我唯一的愿望是,我可以输入实际的键序列而不用键入来跳到列表中的内容C - c _ C - p
nispio
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.