New :completion corfu module

This topic will cover the experimental work done on :completion corfu.

Corfu is a childframe-based completion selection package, like company or auto-complete do. Associated with Cape, it might easily reach feature-parity with Company while having less legacy code and using more of the recent Emacs changes to make package code simpler.

Waiting on Henrik to have a status on whether he wants to steer/control the module direction. But meanwhile, you can discuss my draft if you want to take a peek at it.

https://git.sr.ht/~gagbo/doom-config/tree/8e3014985774d68c6f768dd4e3c8045255cd87d1/item/modules/completion/corfu

This post supersedes the discussion that started on Discord about it

15 Likes

I’ve been meaning to try Corfu and Cape.
Thank you for lowering the barrier to entry.

I’ve just copied this module to my config and I’m using it now. I’ve been wanting corfu for a few weeks now. I tested it a little bit last night but found that ‘tabbing’ was a little bit jarring compared to how the company module works in doom. Of course it’s trivial to remap in my config.el, but may not be consistent with the rest of doom.

I’ve been testing this new capf with this module code, and am getting odd behavior, which the author of that package does not see with his non-doom corfu install.

I get the candidate list when in an org buffer, but when I try to select a candidate with RET, it adds a newline to the buffer, rather than inserts the candidate (well, really the result of the :exit-function run on the candidate).

I do not see the same behavior in other major modes (for example, lisp).

Is it possible there’s something in this code that could cause that behavior? Any suggestions on narrowing it down?

1 Like

Also re: testing.

I’ve been playing with this module a little bit while doing some eslisp stuff. I find that there is some conflict between doom’s :editor snippets and the TAB completion setup. For example, if I type (set then hit TAB for some corfu goodness, it auto-expands and wrecks the completion. For now I’ve just disabled snippets.

Yes, that is the main outstanding issue in what I’ve done yet, it triggers me so so hard.

When I get time I’ll try to find out why

1 Like

So far, what I’ve done is remap:

  • corfu-next to C-j
  • corfu-previous to C-k
  • corfu-quit, to [evil-escape] so I can just jk out of the prompt

I think I’ll also disable TAB as a point of entry too. I think C-SPC may be more appropriate, if not auto-completion, which is how doom’s company is set to trigger.

I’ll edit this post to add the actual config when I’m at the computer next. EDIT: Here’s my remap expression. I don’t know if it’s idiomatic or not, please correct me.

(with-eval-after-load 'corfu
  (let ((map corfu-map))
    (define-key map [remap +default/newline] #'corfu-next)
    (define-key map [remap evil-insert-digraph] #'corfu-previous)
    (define-key map (kbd "jk") #'corfu-quit)))

Mostly ignore the code in my last comment. On testing it only worked in elisp mode. I’m still using ‘C-n’ and ‘C-p’ for candidate selection, and ‘jk’ to exit completions.

Also, I think in the config.el of the corfu module, inside the (use-package! cape ... ) expression, we should be adding #'cape-file rather than #'cape-file-capf. This goes for all cape-* capfs in the above-mentioned expression. The latter was giving me errors. I don’t know if minad refactored or something.

Didn’t test it yet, but there might be a better TUI version of corfu now

https://elpa.nongnu.org/nongnu/corfu-terminal.html

Actually, I see the same thing when inserting an org block.

Can anyone else confirm this?

Just started using this, I’m much more satisfied with it than company.

Can you elab? I haven’t really hit any annoyances with company, but maybe I just don’t know what I’m missing

Faster, looks cleaner, more reliable completion for starters

I like it. Instead of waiting on Henrik, why not start a draft PR? That way, Henrik can have quick look and/or review comments whenever he wants, and the users get single point of reference on status and pull any new module-specific change?

I can confirm this, there’s some autoload behaviour going on with evil-org that forces RET to be the default behaviour no matter what.

Not sure how to resolve it honestly, @hlissner?

1 Like

Ended up solving this by advising +org/return as below, adjust as required :slight_smile:

(defadvice! +corfu--org-return (orig) :around '+org/return
    (if (and (featurep! :completion corfu) ;; omit if not using via a module
             corfu-mode
             (>= corfu--index 0)) ;; translates to "there are candidates to select"
        (corfu-insert)
      (funcall orig)))

Did any of you install corfu-terminal ? It seems that straight doesn’t know of NonGNU ELPA and it seems to bite me because it tries to find a popon package even if I mention the whole rpoe URL for corfu-terminal

FTR the tracking issue for NonGNU ELPA support in straight

Yeah I had to manually add both as recipes because of them not being in a repo in straight

https://github.com/elken/doom/blob/1a92f7e8d272e62e99de6e2041dee4b105424fe1/modules/completion/corfu/packages.el#L13-L18

It should be okay soon, the issue has been closed and straight can deal with NonGNU ELPA natively. It will needa bump of straight to pull the changes though

1 Like