-
Notifications
You must be signed in to change notification settings - Fork 200
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix eglot-completion-at-point so it can be used from the minibuffer #505
Fix eglot-completion-at-point so it can be used from the minibuffer #505
Conversation
@joaotavora, did you have a chance to look at this? I can rebase. |
640b5aa
to
55765a5
Compare
Should be up to date now. |
Hi @andschwa I'm sorry for the delay. I've had a looked at this some days ago, and I remember thinking of an objection that I can't seem to remember now. I'll think a bit harder in the next few days, or just let it go, since it doesn't look bad in theory. |
Thanks @joaotavora! I've been using this patch locally (with the capf variant I linked) for a while now and it's working well at least in that scenario. |
55765a5
to
0c6bea0
Compare
Hm, I don't remember those tests failing before I rebased 🤔 |
It looks like these failing tests are unrelated, as they also failed in #515 which only touched the readme:
|
Related to #505. * eglot-tests.el (eglot--eldoc-on-demand): Don't rely on gone eldoc-display-message-p.
Hi @andschwa , I'm looking at this again. Can you explain how this works, from a user's standpoint? I'm having trouble visualizing its use. Is it that you complete something in the minibuffer but it somehow has an effect in the buffer of the window selected just before you switched to the minibuffer? A small video or Also, can you comment on whether or not you think your patch should be applied to all of Emacs' use of |
Absolutely! So instead of using company-mode, as someone who really likes ;; Inspirations: oantolin’s `completing-read-in-region’, selectrum’s
;; `selectrum-completion-in-region’, minibuffer’s
;; `completion--do-completion’, and `minibuffer-completion-help’.
;; TBH I can't believe something like this isn't available in Emacs because
;; *completions* is archaic compared to `completing-read`.
(defun completion-in-region+ (start end collection &optional predicate)
"Completion in region using `completing-read’.
See `completion-in-region’ for START END COLLECTION PREDICATE.
Set `completion-in-region-function’ to use, remember to press ?
to open `*completions*’ buffer (perhaps with annotations)."
(if (and (minibufferp) (not (string= (minibuffer-prompt) "Eval: ")))
(unless completion-fail-discreetly
(ding) (completion--message "Press `?’ for `*completions*’ buffer") nil)
(let* ((input (buffer-substring-no-properties start end))
(limit (car (completion-boundaries input collection predicate "")))
(md (completion--field-metadata start))
(all (completion-all-completions input collection predicate
(- end start) md))
(comp (cond
((atom all) nil)
((and (consp all) (atom (cdr all)))
(concat (substring input 0 limit) (car all)))
(t (completing-read
"Completion: " collection predicate t input)))))
(if (null comp)
(unless completion-fail-discreetly
(ding) (completion--message "No completions") nil)
(delete-region start end)
(insert (substring-no-properties comp))
t))))
(setq completion-in-region-function #'completion-in-region+) Here's it in use when Eglot is broken in this way: Hitting I exited the second time using That error message is:
Which I tracked to two places, And here's it working with For what it's worth, there's probably a better way to fix this, it's just what I came up with. I'm no expert here. |
I have been playing with a `completing-read` version of `completion-at-point`, and got it just about working, except with `minibuffer-force-complete` was called I’d run into errors. Debugged it to the `exit-function`, which was written assuming the current buffer was still the code buffer. The fix was fairly trivial: change the current buffer to the one from which the minibuffer was called, if applicable. An alternative considered was to apply this logic in `eglot--current-server-or-lose` and `eglot--TextDocumentPositionParams`, which is were the errors came from, but that didn’t make sense.
0c6bea0
to
08faf92
Compare
I have no idea honestly. I think anything that uses a completing-read replacement for completions would run into this, so perhaps it would make sense for all exit-functions to work like this. I ran into similar issues with |
I added a comment and pushed this, presumably fixing your problem. I think you must now open an Emacs bug report (with
Please include me (and Stefan Monnier (@monnier)) in that bug report (using the Also, Andrew, I think you must soon sign a copyright assigment to Emacs if you want to keep contributing code. I marked this small contribution as a "Copyright-paperwork-exempt: yes". |
Sweet, thank you! And I will do 1) and 2) 😄
I have one signed! However, it's stuck in the FSF copyright office...let me follow up with them again to see if everything is settled 😅 |
…uffer To design a completion-in-region-function replacement that leverages the elements in completion-at-point-functions, we must ensure that their :exit-function parts execute in the correct buffer. That is the buffer where the text to be completed lives, not necessarily the buffer being used for user interaction. Later on, this guarantee should be provided by Emacs itself, perhaps by putting the correct with-current-buffer call in completion--done. Copyright-paperwork-exempt: yes Co-authored-by: João Távora <joaotavora@gmail.com> * eglot.el (eglot-completion-at-point): Ensure :exit-function's buffer is where the source is.
…uffer To design a completion-in-region-function replacement that leverages the elements in completion-at-point-functions, we must ensure that their :exit-function parts execute in the correct buffer. That is the buffer where the text to be completed lives, not necessarily the buffer being used for user interaction. Later on, this guarantee should be provided by Emacs itself, perhaps by putting the correct with-current-buffer call in completion--done. Copyright-paperwork-exempt: yes Co-authored-by: João Távora <joaotavora@gmail.com> * eglot.el (eglot-completion-at-point): Ensure :exit-function's buffer is where the source is.
To design a completion-in-region-function replacement that leverages the elements in completion-at-point-functions, we must ensure that their :exit-function parts execute in the correct buffer. That is the buffer where the text to be completed lives, not necessarily the buffer being used for user interaction. Later on, this guarantee should be provided by Emacs itself, perhaps by putting the correct with-current-buffer call in completion--done. Copyright-paperwork-exempt: yes Co-authored-by: João Távora <joaotavora@gmail.com> * eglot.el (eglot-completion-at-point): Ensure :exit-function's buffer is where the source is. #505: joaotavora/eglot#505
To design a completion-in-region-function replacement that leverages the elements in completion-at-point-functions, we must ensure that their :exit-function parts execute in the correct buffer. That is the buffer where the text to be completed lives, not necessarily the buffer being used for user interaction. Later on, this guarantee should be provided by Emacs itself, perhaps by putting the correct with-current-buffer call in completion--done. Copyright-paperwork-exempt: yes Co-authored-by: João Távora <joaotavora@gmail.com> * eglot.el (eglot-completion-at-point): Ensure :exit-function's buffer is where the source is. GitHub-reference: close joaotavora/eglot#505
I have been playing with a
completing-read
version ofcompletion-at-point
, and got it just about working, except withminibuffer-force-complete
was called I’d run into errors. Debugged itto the
exit-function
, which was written assuming the current bufferwas still the code buffer. The fix was fairly trivial: change the
current buffer to the one from which the minibuffer was called, if
applicable. An alternative considered was to apply this logic in
eglot--current-server-or-lose
andeglot--TextDocumentPositionParams
,which is were the errors came from, but that didn’t make sense.