【问题标题】:Emacs : Redefining command in Haskell-mode (haskell-mode-hook)Emacs : 在 Haskell-mode (haskell-mode-hook) 中重新定义命令
【发布时间】:2012-08-11 18:19:21
【问题描述】:

在haskell-mode的emacs中,我想改变命令

  • “C-x C-s”

  • “C-x C-s”后跟“C-c C-l”。

Haskell.org : Emacs/Keybindings and simple usage 得到提示我尝试将以下变体插入到 .emacs 文件中,但它们不起作用。任何关于我如何实现上述功能的建议都将受到欢迎!谢谢。

变体 1

(defun haskell-hook ()
  (define-key haskell-mode-map (kbd "C-x C-s") (kbd "C-x C-s C-c C-l"))

(add-hook 'haskell-mode-hook 'haskell-hook)

变体 2

(defun haskell-hook ()
  (define-key haskell-mode-map (kbd "C-x C-s") 'my-haskell-mode-save-buffer)

(defun my-haskell-mode-save-buffer ()
  (interactive)
  (execute-kbd-macro [?\C-s ?\C-x ?\C-c ?\C-l return]))

(add-hook 'haskell-mode-hook 'haskell-hook)


[EDIT 1] @Tikhon Jelvis:这绝对是一个很好的学习练习!谢谢。使用您帖子中概述的方法,我将您的功能更改为:

(defun my-haskell-mode-save-buffer ()
  (interactive)
  (save-buffer)
  (inferior-haskell-load-file)
  (other-window 1))

最后一行以编程方式将光标切换到交互式窗口。谢谢。

[EDIT2] 其他变体包括:

(defun my-haskell-mode-save-buffer ()
  (interactive)
  (execute-kbd-macro (read-kbd-macro "C-c C-l"))
  (other-window 1)) 

和:

(defun my-haskell-mode-save-buffer ()
  (interactive)
  (execute-kbd-macro [?\C-c ?\C-l])
  (other-window 1))

【问题讨论】:

  • 您可以将键盘序列绑定到命令,而不是另一个键盘序列。你想完成什么?
  • 基本上我希望“C-s C-x”先保存文件,然后在启动器中自动加载文件,而不仅仅是保存文件。谢谢
  • 寻找haskell-mode-after-save-hook 或创建一个执行此操作的函数。 (defun my-haskell-save-buffer (buf) (interactive ...) (save-buffer buf) (haskell-launch buf) ) ... 概念证明,查看如何使用 interactive 和“启动器”的确切命令传递当前缓冲区。
  • 绑定保存文件然后加载到C-c C-l 可能比每次保存时都加载文件更有意义。
  • @vivian :这只是我学习 emacs 的一个实验。正如 Tikhon Jelvis 指出的那样,“C-c C-l”已经保存了(除了在缓冲区之间移动光标)上面的功能并没有真正增加任何价值!谢谢

标签: haskell emacs macros elisp haskell-mode


【解决方案1】:

您要做的是运行C-x C-s 运行的函数,然后运行C-c C-l 运行的函数。您可以通过C-h k 找出某个键绑定运行的功能。也就是说,首先输入C-h k,然后输入您感兴趣的键盘命令。

这给了我们(save-buffer &optional ARGS) 对应C-x C-s(inferior-haskell-load-file &optional RELOAD) 对应C-c C-l&optional 的含义正是您认为的那样——该参数是可选的,所以我们不关心它。

现在写两个函数:

(defun my-haskell-mode-save-buffer ()
  (interactive)
  (save-buffer)
  (inferior-haskell-load-file)) 

现在您可以在 Haskell 模式下将此函数绑定到 C-x C-s,这正是您一直以来的做法:

(add-hook 'haskell-mode-hook (lambda () 
                                (local-set-key (kbd "C-x C-s") 'my-haskell-mode-save-buffer)))

编辑:似乎C-c C-l 在加载之前默认保存您的文件。这意味着你可以写

(add-hook 'haskell-mode-hook (lambda ()
                            (local-set-key (kbd "C-x C-s") 'inferior-haskell-load-file)))

并且无需编写自己的函数即可获得完全相同的效果。但是,我认为以我的方式编写它是一个很好的学习练习:P。每当您想将多个不同的键绑定组合成一个时,这种方法都可以使用。

【讨论】:

  • 哇,这可以让我每天节省 1 小时。谢谢
【解决方案2】:

接受的答案在 2020 年不起作用。要修复它,您必须将 (inferior-haskell-load-file) 替换为 (haskell-process-load-file)

所以修复后的功能是

(defun haskell-mode-save-load-buffer ()
      (interactive)
      (save-buffer)
      (haskell-process-load-file))

【讨论】: