Added corfu-candidate-overlay-complete-at-point function
This commit is contained in:
parent
56b5d12641
commit
6cdc33aa21
2 changed files with 111 additions and 87 deletions
|
@ -5,7 +5,7 @@
|
||||||
;; Author: Adam Kruszewski <adam@kruszewski.name>
|
;; Author: Adam Kruszewski <adam@kruszewski.name>
|
||||||
;; Maintainer: Adam Kruszewski <adam@kruszewski.name>
|
;; Maintainer: Adam Kruszewski <adam@kruszewski.name>
|
||||||
;; Created: 2023
|
;; Created: 2023
|
||||||
;; Version: 1.3
|
;; Version: 1.4
|
||||||
;; Package-Requires: ((emacs "28.1") (corfu "0.36"))
|
;; Package-Requires: ((emacs "28.1") (corfu "0.36"))
|
||||||
;; Homepage: https://code.bsdgeek.org/adam/corfu-candidate-overlay/
|
;; Homepage: https://code.bsdgeek.org/adam/corfu-candidate-overlay/
|
||||||
|
|
||||||
|
@ -232,6 +232,20 @@ Otherwise the overlay can influence movement commands (i.e. the cursor is
|
||||||
is-delete-command))))
|
is-delete-command))))
|
||||||
(corfu-candidate-overlay--hide)))))
|
(corfu-candidate-overlay--hide)))))
|
||||||
|
|
||||||
|
(defun corfu-candidate-overlay-at-word-boundary-p ()
|
||||||
|
"Return non-nil when cursor is at the word boundary for completion purposes.
|
||||||
|
Or nil otherwise."
|
||||||
|
(let ((next-char (char-after)))
|
||||||
|
(or (not next-char) ;; end of file
|
||||||
|
;; one of whitespace, quoting character, punctuation,
|
||||||
|
;; closing bracket, etc is next.
|
||||||
|
;; When those characters follow next completion won't trigger
|
||||||
|
;; either-way: ' = * - + / ~ _ (have not investigated further),
|
||||||
|
;; so they are not in the list.
|
||||||
|
(memq next-char '(?\s ?\t ?\r ?\n
|
||||||
|
?\" ?\` ?\) ?\] ?\>
|
||||||
|
?\. ?\, ?\: ?\;)))))
|
||||||
|
|
||||||
(defun corfu-candidate-overlay--post-command ()
|
(defun corfu-candidate-overlay--post-command ()
|
||||||
"Post command hook to update candidate overlay.
|
"Post command hook to update candidate overlay.
|
||||||
Update happens when the user types character and the cursor is at
|
Update happens when the user types character and the cursor is at
|
||||||
|
@ -246,8 +260,8 @@ the end of word."
|
||||||
(corfu--match-symbol-p corfu-auto-commands this-command))
|
(corfu--match-symbol-p corfu-auto-commands this-command))
|
||||||
(is-delete-command
|
(is-delete-command
|
||||||
(corfu--match-symbol-p corfu-candidate-overlay-auto-commands this-command)))
|
(corfu--match-symbol-p corfu-candidate-overlay-auto-commands this-command)))
|
||||||
;; short-circuit conditions -- the earlier we return if don't need to do
|
;; short-circuit conditions -- the earlier we return, if don't need to do
|
||||||
;; anything the better.
|
;; anything, the better.
|
||||||
(if (and
|
(if (and
|
||||||
;; we are not in minibuffer, as it looks awkward.
|
;; we are not in minibuffer, as it looks awkward.
|
||||||
(not (minibuffer-window-active-p (selected-window)))
|
(not (minibuffer-window-active-p (selected-window)))
|
||||||
|
@ -259,24 +273,16 @@ the end of word."
|
||||||
(= corfu-candidate-overlay--last-point (point))))
|
(= corfu-candidate-overlay--last-point (point))))
|
||||||
(or ;; do not update if it is not one of the insert or delete commands.
|
(or ;; do not update if it is not one of the insert or delete commands.
|
||||||
is-insert-command
|
is-insert-command
|
||||||
is-delete-command))
|
is-delete-command)
|
||||||
;; now we check additional short-circuit conditions, but those operate on
|
;; check whether we are at word boundardy.
|
||||||
;; next character.
|
(corfu-candidate-overlay-at-word-boundary-p))
|
||||||
(let ((next-char (char-after)))
|
;; ...when main compound conditions is true clause...
|
||||||
(when (or ;; do not update if we are not at the end of the word.
|
(progn
|
||||||
(not next-char) ;; end of file
|
|
||||||
;; one of whitespace, quoting character, punctuation,
|
|
||||||
;; closing bracket, etc is next.
|
|
||||||
;; When those characters follow next completion won't trigger
|
|
||||||
;; either-way: ' = * - + / ~ _ (have not investigated further)
|
|
||||||
(memq next-char '(?\s ?\t ?\r ?\n
|
|
||||||
?\" ?\` ?\) ?\] ?\>
|
|
||||||
?\. ?\, ?\: ?\;)))
|
|
||||||
;; When the completion backend is SLOW, i.e. like every LSP client,
|
;; When the completion backend is SLOW, i.e. like every LSP client,
|
||||||
;; then the overlay will often not update and will interfere with the typing.
|
;; then the overlay will often not update and will interfere with the typing.
|
||||||
;; That's why we operate on stored prefix and candidate giving an illusion
|
;; That's why we operate on stored prefix and candidate giving an illusion
|
||||||
;; of updating the overlay -- but using the previous auto suggestion candidate.
|
;; of updating the overlay -- but using the previous auto suggestion candidate.
|
||||||
(when corfu-candidate-overlay--overlay ;; need overlay active
|
(when corfu-candidate-overlay--overlay
|
||||||
(let* ((candidate
|
(let* ((candidate
|
||||||
(corfu-candidate-overlay--get-overlay-property 'corfu-candidate))
|
(corfu-candidate-overlay--get-overlay-property 'corfu-candidate))
|
||||||
(prefix
|
(prefix
|
||||||
|
@ -323,10 +329,22 @@ the end of word."
|
||||||
;; the corfu-candidate-overlay--show CAN be interrupted, that's why
|
;; the corfu-candidate-overlay--show CAN be interrupted, that's why
|
||||||
;; we did the shuffling above.
|
;; we did the shuffling above.
|
||||||
(setq corfu-candidate-overlay--last-point (point))
|
(setq corfu-candidate-overlay--last-point (point))
|
||||||
(corfu-candidate-overlay--show)))
|
(corfu-candidate-overlay--show))
|
||||||
;; or hide the overlay if the conditions to show the overlay where not met.
|
;; ...when main compound conditions is false clause...
|
||||||
|
;; so hide the overlay if the conditions to show the overlay where not met.
|
||||||
(corfu-candidate-overlay--hide)))))
|
(corfu-candidate-overlay--hide)))))
|
||||||
|
|
||||||
|
;;;###autoload
|
||||||
|
(defun corfu-candidate-overlay-complete-at-point ()
|
||||||
|
"Insert the first completion candidate shown in the overlay."
|
||||||
|
(interactive)
|
||||||
|
(when
|
||||||
|
(and corfu-candidate-overlay--overlay
|
||||||
|
(overlayp corfu-candidate-overlay--overlay)
|
||||||
|
(corfu-candidate-overlay-at-word-boundary-p))
|
||||||
|
|
||||||
|
(insert (corfu-candidate-overlay--get-overlay-property 'corfu-candidate))))
|
||||||
|
|
||||||
;;;###autoload
|
;;;###autoload
|
||||||
(define-minor-mode corfu-candidate-overlay-mode
|
(define-minor-mode corfu-candidate-overlay-mode
|
||||||
"Show first candidate in an overlay while typing."
|
"Show first candidate in an overlay while typing."
|
||||||
|
|
10
readme.org
10
readme.org
|
@ -12,6 +12,8 @@ Overlay showing auto-completion candidate when there is only one available (so i
|
||||||
[[./readme-images/corfu-candidate-overlay-one.png]]
|
[[./readme-images/corfu-candidate-overlay-one.png]]
|
||||||
|
|
||||||
It show the first auto-suggestion from [[https://github.com/minad/corfu][corfu]] and when there is only one it will show it underlined (face attributes can be configured). In case of many suggestions available, invoking =completion-at-point= will open the corfu popup menu to choose from, in case of single completion available (i.e. underlined) it will get auto-completed seeing the menu when invoked =completion-at-point=.
|
It show the first auto-suggestion from [[https://github.com/minad/corfu][corfu]] and when there is only one it will show it underlined (face attributes can be configured). In case of many suggestions available, invoking =completion-at-point= will open the corfu popup menu to choose from, in case of single completion available (i.e. underlined) it will get auto-completed seeing the menu when invoked =completion-at-point=.
|
||||||
|
|
||||||
|
Package exposes also one interactive function =corfu-candidate-overlay-complete-at-point= which you can bind to a key combination. Invoking the function will complete the exact candidate overlay is currently showing[fn:4] (i.e. it will not show corfu's popup even if there are more candidates present, just complete what you see).
|
||||||
** Motivation
|
** Motivation
|
||||||
Similarly to Michell Hashimoto[fn:1] of HashiCorp fame, I like my editor to do less than more. I'm not as ascetic though ;-) From time to time I do use the auto-suggestion menu of [[https://github.com/minad/corfu][corfu]], especially when I forget the exact wording of a function. I do however trigger the auto-suggestion popup manually.
|
Similarly to Michell Hashimoto[fn:1] of HashiCorp fame, I like my editor to do less than more. I'm not as ascetic though ;-) From time to time I do use the auto-suggestion menu of [[https://github.com/minad/corfu][corfu]], especially when I forget the exact wording of a function. I do however trigger the auto-suggestion popup manually.
|
||||||
|
|
||||||
|
@ -40,8 +42,11 @@ When using slow or cpu-heavy corfu backends (e.g. [[https://github.com/minad/cap
|
||||||
;; enable corfu-candidate-overlay mode globally
|
;; enable corfu-candidate-overlay mode globally
|
||||||
;; this relies on having corfu-auto set to nil
|
;; this relies on having corfu-auto set to nil
|
||||||
(corfu-candidate-overlay-mode +1)
|
(corfu-candidate-overlay-mode +1)
|
||||||
;; bind Ctr + TAB to trigger the completion popup of corfu
|
;; bind Ctrl + TAB to trigger the completion popup of corfu
|
||||||
(global-set-key (kbd "C-<tab>") 'completion-at-point))
|
(global-set-key (kbd "C-<tab>") 'completion-at-point)
|
||||||
|
;; bind Ctrl + Shift + Tab to trigger completion of the first candidate
|
||||||
|
;; (keybing <iso-lefttab> may not work for your keyboard model)
|
||||||
|
(global-set-key (kbd "C-<iso-lefttab>") 'corfu-candidate-overlay-complete-at-point))
|
||||||
#+end_src
|
#+end_src
|
||||||
** Customization
|
** Customization
|
||||||
Faces available for customization:
|
Faces available for customization:
|
||||||
|
@ -72,6 +77,7 @@ Issue reports, questions, comments and code patches are welcome -- you can send
|
||||||
If you haven't sent code patches via e-mail yet and would like to learn how to work with an e-mail based workflow, you can read more at [[https://git-scm.com/docs/git-format-patch][git format-patch]] man page or at [[https://git-send-email.io/][git-send-email.io]].
|
If you haven't sent code patches via e-mail yet and would like to learn how to work with an e-mail based workflow, you can read more at [[https://git-scm.com/docs/git-format-patch][git format-patch]] man page or at [[https://git-send-email.io/][git-send-email.io]].
|
||||||
|
|
||||||
* Footnotes
|
* Footnotes
|
||||||
|
[fn:4] Thanks to [[https://github.com/terlar][Terje Larsen]] for suggestion!
|
||||||
|
|
||||||
[fn:1] See video cast:
|
[fn:1] See video cast:
|
||||||
[[https://www.youtube.com/watch?v=rysgxl35EGc][Worst Practices in Software Development: Mitchell Hashimoto uses a simple code editor]].
|
[[https://www.youtube.com/watch?v=rysgxl35EGc][Worst Practices in Software Development: Mitchell Hashimoto uses a simple code editor]].
|
||||||
|
|
Loading…
Reference in a new issue