唯一时自动完成 (Emacs 自动补全)

3
如何编写自动完成代码以在只有一个唯一选项时立即触发? (或者当有多个选项,但它们都具有相同的基础时)
(eval-exp_[point-is-here]_)

自动完成功能提供以下优点:

(eval-expression
(eval-expression-print-format)

现在当它遇到唯一的选项时,如果能立即完整地输入(eval-expression那不是很好吗?然后如果我们输入"-",它会立即选择print-format吗?即使有2个选项,您也只需要"-p"即可完成,如下面的示例所示:
(eval-expression-print-format)
(eval-expression-something-else)

这种行为在Emacs中是否可行?

1
我曾经见过这种完成方式被称为“闪电完成”,而Emacs的minibuffer完成中也有一个名为“闪电完成”的包。 - Stefan
2个回答

2

它实现了所需的行为:

(defadvice ac-inline-show (after eab-ac-expand activate)
  (if (> (length ac-candidates) 1)
      (let ((ac-common-part (try-completion ac-prefix ac-candidates)))
        (ac-expand-common))
    (progn
      (ac-expand-string ac-common-part)
      (ac-inline-hide)))
  (setq eab-last-selected-candidate ac-selected-candidate))

停用操作:

(ad-remove-advice 'ac-inline-show 'after 'eab-ac-expand)
(ad-deactivate 'ac-inline-show)

编辑:

我尝试了一下工作流程,找到了一种取消错写的方法。例如您输入lam,它会自动扩展为lambda,但是您不小心多加了一个bd,这样就得到了lambdabd。所以我设置了

(global-set-key (kbd "C-<tab>") '(lambda () (interactive) (flet ((ac-candidates () `(,eab-last-selected-candidate))) (ac-fuzzy-complete)) (ac-expand)))

并将其使用: lambdabd 变为 lambda ,然后您可以像往常一样继续。

编辑2:

解决方案存在一个缺点:“进行模糊匹配时会稍微变慢”。通过将 ac-candidates 缩小到 eab-last-selected-candidate 以供 ac-fuzzy-complete 使用,已经解决了这个问题。现在速度很快!


我想尝试在非常短的“块”中构建覆盖字符的功能,即保留包含在该部分中的字符,您认为这是可能的吗?另外,“您的环境”是什么意思?您是指使用此示例还是通常使用的环境? - PascalVKooten
嗯,我的意思是它需要时间才能看到它的完成,通常在我还在输入这三个字符的时候就已经完成了。所以我的意思是,最终我会得到eval-expressionxpr而不是eval-expression(因为我输入了那些字符)。如果我们能够在它完成后阻止继续,并且只接受除了"xpr"之外的其他字母(也许只是"xp",但这需要测试),那将是很好的。你有什么想法吗? - PascalVKooten
我认为这种额外的错误按键引起的不良行为应该通过ac-fuzzy-complete函数来解决,可以参考下面的示例。 - artscan
2
哦,太棒了。我真的建议其他人给这个答案点赞,因为它超出了最初的要求。它只有两个缺点:在我的电脑上,当它进行模糊匹配时会有一点减速(我试图在自动模糊匹配完成后绑定到SPC,同时在后面插入一个空格)。另外,请尝试输入(beginning-of-line),然后进行模糊匹配:它将变成(beginning-of-buffer)。这是怎么可能的? - PascalVKooten
2
这是因为在(ac-fuzzy-complete)之后使用(ac-expand),它的作用类似于没有拼写错误的字符串中的ac-next。我只在有拼写错误的情况下使用这样的函数。如果你尝试将其应用于正确的字符串,比如beginning-of-line,你会从列表中得到下一个候选项。 - artscan
显示剩余2条评论

0

如果只有少数候选人,您可以通过M-1M-2等方式选择每个候选人。对于2-7个候选人,它的效果很好(与您示例中的按键-p进行比较)。您可以在还有几个候选人时使用M-<number>,以避免出现单个候选人的情况。

M-<number>是函数ac-complete-<number>的绑定键。

此外,函数ac-isearchC-s)也很有用。在eva_[point]_的开头,您可以通过按下C-s搜索字符串fopr,然后从缩小的列表中选择。


我知道 M-1 到 M-9 键,但我不想要去数哪个选项。 - PascalVKooten
我同意你的观点。我更愿意使用一些可视化工具,比如ace-jump。同时,使用ido-modeido-enable-flex-matching来缩小候选范围也是不错的选择。但是目前还没有人将它们与自动完成结合起来。此外,在你的例子中,如果字符串“expression”立即完成,那么如果出现打字错误,我该如何取消它?我必须取消已经完成的错误字符串,这会很烦人。我认为“ac-inline”是一个不错的折衷方案,因为它是“静默”的。 - artscan
错别字不会有完成的效果?如果你完成了一些你不想要的东西,你可以使用C-backspace向后删除,然后快速地写下你想表达的内容。我相信长期来看这样做会得到回报。不要忘记我们只谈论那些能够立即完成的独特的内容。 - PascalVKooten

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接