Git Product home page Git Product logo

Comments (18)

minad avatar minad commented on August 17, 2024 1

@manuel-uberti Yes, thanks for mentioning it. This is the option to exit directly with the current input. Furthermore you could bind exit-minibuffer to some key in order to force exiting even if the completion UI insists on a required match. I think @oantolin always binds exit-minibuffer, since he likes to keep footguns around.

from vertico.

minad avatar minad commented on August 17, 2024

Yes, I think this is intentional. The first candidate is selected and therefore the copy goes there. If you want to copy to the current directory you can select the prompt by moving upwards. Now the question is if this default behavior should be improved.

Multiple options:

  • I am filtering out ./ and ../. I would like to keep the filtering like this. I just want to mention it, since if ./ is the first candidate the problem would go away. The filtering is justified I think since the prompt can still be selected, which corresponds to the current directory.
  • It is possible to preselect the prompt in certain scenarios - I think Selectrum has some special casing for dired/directories, but I have to check what it is doing. For now I didn't add any special casing to Vertico in order to keep things simple.

from vertico.

protesilaos avatar protesilaos commented on August 17, 2024

I see, thank you! Just thought I would bring it to your attention.

from vertico.

minad avatar minad commented on August 17, 2024

Selectrum has the selectrum--fix-dired-read-dir-and-switches advice. Maybe this helps fixing this behavior and you want to give it a try? I will check later. But generally, I would like to avoid these kind of hacks in Vertico.

Yesterday I also did some small experiments with CRM (see the crm and crm2 branches). I tried:

  • Keeping all the candidates, selecting a selected candidate again removes it from the selected list
  • Remove the selected candidates from the candidates list (as you are doing in your prot-minibuffer and as Selectrum is doing)

But for now I also didn't merge any of this since I didn't find it that of a significant improvement over the status quo, where the completing-read-multiple completion table just does its thing and I am not interfering.

I think of Vertico as an experiment in what I can do with a minimal implementation instead of aiming to provide the very best UI by replacing everything here and there. In contrast, Selectrum for example has advices tweaking many details.

from vertico.

manuel-uberti avatar manuel-uberti commented on August 17, 2024

@protesilaos you could use vertico-exit-input to get what you are looking for, I guess.

from vertico.

protesilaos avatar protesilaos commented on August 17, 2024

Very well! That should go in the docs then. And yes, I also bind exit-minibuffer.

from vertico.

oantolin avatar oantolin commented on August 17, 2024

This thing about always submitting the first candidate even when the minibuffer contains a perfectly valid directory really messes with muscle memory acquired from using default completion. (I know that it's sensible, consistent behavior, but my finger don't seem to understand that.) I believe Selectrum does it too and it's one of the reasons I never really took to Selectrum. I didn't know about the advice @minad mentioned. Does it really change that behavior for the special case of dired while keeping it in other circumstances? If so, that sounds terrible, at least vertico does it consistently. Also, I think there was a long discussion of this behavior in the Selectrum issue tracker.

And yes, I do recommend binding exit-minibuffer. If I enjoyed other people deciding what I can and can't do in the privacy of my own computer, I wouldn't use Emacs. But more practically, not every function you find out there that uses require match has really thought carefully about what all the possible choices are. You hardly ever need it, but it's annoying to not have it bound when you do need it. (I used to use it slightly more back when I used minibuffer-force-complete, which in some unusual circumstances breaks down and doesn't let you exit; I wrote my own version of minibuffer-force-complete that really and truly always exits with the top completion and now I need exit-minibuffer only very rarely.)

from vertico.

protesilaos avatar protesilaos commented on August 17, 2024

To which map[s] do you bind exit-minibuffer? I am doing it for minibuffer-local-completion-map, though I thought of adding it to minibuffer-local-must-match-map as well. Though I will keep minibuffer-local-filename-must-match-map in tact.

from vertico.

oantolin avatar oantolin commented on August 17, 2024

I bind it only in minibuffer-local-map. That way it is available in all situations, including when using Selectrum, which for some reason doesn't use minibuffer-local-completion-map or minibuffer-local-must-match-map.

from vertico.

protesilaos avatar protesilaos commented on August 17, 2024

Good, thank you!

from vertico.

minad avatar minad commented on August 17, 2024

This thing about always submitting the first candidate even when the minibuffer contains a perfectly valid directory really messes with muscle memory acquired from using default completion.

Yes, this behavior can be perceived as problematic some times. But I wonder how you reconcile the two approaches then:

  • Either you use orderless and the input is not meant to be a candidate
  • Or you use TAB completion where the input is expanded such that it is a real candidate

I bind it only in minibuffer-local-map. That way it is available in all situations, including when using Selectrum, which for some reason doesn't use minibuffer-local-completion-map or minibuffer-local-must-match-map.

Regarding the keymaps. I am also using minibuffer-local-map as parent keymap of the Vertico keymap. Selectrum does the same. This is easier than unbinding/rebinding all the keybindings imposed by default completion minibuffer-completeand friends. But this is something where I cannot claim that Vertico really follows the default since it mostly deactivates all these commands and replaces it by two simple commands vertico-insert and vertico-exit. But this does not mean that I am perfectly happy with these choices. If you have a better proposal how this could be done please let me know. Do you suggest to keep all these minibuffer-complete commands around and inheriting the current local keymap instead of simply replacing the keymap altogether?

You hardly ever need it, but it's annoying to not have it bound when you do need it. (I used to use it slightly more back when I used minibuffer-force-complete, which in some unusual circumstances breaks down and doesn't let you exit; I wrote my own version of minibuffer-force-complete that really and truly always exits with the top completion and now I need exit-minibuffer only very rarely.)

This sounds like you have a different variant of vertico-exit, but I wonder how that actually differs. If the input matches a candidate exactly, Vertico already puts it at the top. Then the default value is at the top. Selectrum essentially does the same.

from vertico.

oantolin avatar oantolin commented on August 17, 2024

@minad, about the keymaps: I don't really like how many different keymaps default completion has, so I think the approach in Vertico and Selectrum is absolutely fine. You could almost set minibuffer-local-completion-map as the parent instead, since minibuffer-local-must-match-map inherits from it, but unfortunately the file name completion maps don't. That's arguably a tiny bug in Emacs.

Yes, this behavior can be perceived as problematic some times. But I wonder how you reconcile the two approaches then:

  • Either you use orderless and the input is not meant to be a candidate
  • Or you use TAB completion where the input is expanded such that it is a real candidate

Those are not mutually exclusive, of course! I use orderless until I think I've narrowed things done enough and then press TAB. If there is a unique candidate, TAB will insert it. You can also set up TAB cycling, which I use with a threshold of 3, that way TAB also inserts the candidate if there are at most 3 matches and cycles among them. I find that a threshold of 3 is a very good balance, in that if there are more than 3 candidates it is usually less annoying to me to narrow further than to move among candidates.

I also bind RET to a command that first checks to see if the minibuffer contents are a valid candidate and if so just exits the minibuffer, if they aren't a valid candidate, it inserts the top completion into the minibuffer and exits. This way when I'm sure I've narrowed enough, I just press RET and am done. The built-in minibuffer-force-complete-and-exit is supposed to do exactly that, but I replaced because it didn't work for me in all circumstances. Sometimes it even refuses to exit (I can't remember exactly under what circumstances that happens).

You may ask, "how do you know if you have narrowed enough to press RET if you can't see the candidates?". It's really not a problem in practice: Consult's previews often confirm for me I have the right top candidate, memory often is good enough too, and in rare cases where I'm not sure, I can press TAB or popup an embark collect completions buffer (which I bind to M-SPC).

This sounds like you have a different variant of vertico-exit, but I wonder how that actually differs. If the input matches a candidate exactly, Vertico already puts it at the top. Then the default value is at the top. Selectrum essentially does the same.

It is indeed very similar. As I said above the only difference is that if the minibuffer contents are a valid completion (as reported by test-completion), it exits immediately. This fixes the "how do I choose the current directory in file completion?" problem that people with default completion muscle memory experience in Selectrum and Vertico ---as this issue illustrates.

That rule is very subtly different from "If the input matches a candidate exactly, Vertico already puts it at the top", because in this directory example, the portion of the input between the completion boundaries is empty, and the empty string is not one of the candidates, i.e., is not the name of a file in the current directory (usually). So your rule says that the directory plus an empty user input string is not valid and that you must add the top candidate; my rule says instead that the directory is valid on its own, and RET will choose it. And in this directory example it's not just the function I bind to RET that would select the directory, the default RET (minibuffer-complete-and-exit) and minibuffer-force-complete-and-exit do too.

Here's the code I use, in case you are curious:

(defun exit-with-top-completion ()
  "Exit minibuffer with top completion candidate."
  (interactive)
  (let ((content (minibuffer-contents-no-properties)))
    (unless (test-completion content
                             minibuffer-completion-table
                             minibuffer-completion-predicate)
      (when-let ((completions (completion-all-sorted-completions)))
        (delete-minibuffer-contents)
        (insert
         (concat
          (substring content 0 (or (cdr (last completions)) 0))
          (car completions)))))
    (exit-minibuffer)))

You'll notice another small difference with vertico-exit: it does not patronize me with any "Match required" messages 😉. Heaven!

from vertico.

oantolin avatar oantolin commented on August 17, 2024

Oh, wow, I apologize for the length of that comment!

from vertico.

oantolin avatar oantolin commented on August 17, 2024

By the way, I finally tried Vertico and it's fantastic. I think I like it better than Selectrum already. I think, if I'm honest, that my biggest complaint with Selectrum is how slow it is to use embark-act in a non-mini buffer. Try embark-act h on some symbol, for example; on my machine the help buffer takes between 1 and 2 seconds to pop up! But with Vertico this use of embark-act is almost as fast as with default completion or with icomplete (with default completion and icomplete it is instant, with Vertico I think I feel a tiny pause, but certainly much less than one second). Both Selectrum and Vertico have this "problem" we've been discussing with selecting a directory, but I can easily adapt vertico-exit to use my preferred criterion.

from vertico.

oantolin avatar oantolin commented on August 17, 2024

I still don't understand why embark-act h is so slow under Selectrum, when C-h f itself under Selectrum is quite snappy. It's weird that for normal usage Selectrum feels a little snappier than Vertico for those big candidate lists (like M-x and C-h v) but under embark-act in non-mini buffers it's the other way around, then Vertico is much faster!

Both Selectrum and Vertico have pretty poor formatting if you use Marginalia and a narrow Emacs frame (I think you guys probably always maximize!), so maybe I'll stick with not showing completions most of the time and using Embark with its orderly tabulated lists when I do want to see them, but I do like Vertico a lot, easily more than Icomplete-vertical, for example.

from vertico.

minad avatar minad commented on August 17, 2024

@oantolin Thank you for your lengthy response. I agree with you that the two approaches are not mutually exclusive. If you remember for Capf/Company I wanted exactly that behavior since I am already initiating the search with TAB. But in the minibuffer I don't need the TAB since I can use up/down to go to the correct candidate instead of tabbing. Tabbing would essentially do the same.

So your rule says that the directory plus an empty user input string is not valid and that you must add the top candidate; my rule says instead that the directory is valid on its own, and RET will choose it. And in this directory example it's not just the function I bind to RET that would select the directory, the default RET (minibuffer-complete-and-exit) and minibuffer-force-complete-and-exit do too.

I see. This is actually a reasonable rule which makes sense for completions with completion-boundaries, including file completion. Maybe I will adopt your rule. It is actually easy to do - select the prompt if the current input test-completes successfully and as long as no other candidate has been selected before explicity. You may have seen the vertico--keep variable which remembers if the user performed some manual selection.

You'll notice another small difference with vertico-exit: it does not patronize me with any "Match required" messages wink. Heaven!

Yes, but this is Emacs' fault ;) I am just following the spec. I don't want to unnecessarily deviate from the defaults. Users who feel patronized can use your version!

Both Selectrum and Vertico have pretty poor formatting if you use Marginalia and a narrow Emacs frame

Yes, but this is Marginalia's fault ;) I could try to align all the annotations but this would not work well I guess, since for example the M-x keybinding annotations are supposed to be displayed directly after the candidates. Only the docstring is supposed to the right.

I still don't understand why embark-act h is so slow under Selectrum, when C-h f itself under Selectrum is quite snappy. It's weird that for normal usage Selectrum feels a little snappier than Vertico for those big candidate lists (like M-x and C-h v) but under embark-act in non-mini buffers it's the other way around, then Vertico is much faster!

This is no wonder since Selectrum does not sort every time. As of now Selectrum does not support dynamic tables correctly since it just assumes that tables are static, Vertico instead recomputes and sorts every time. However I could also add a static table optimization to Vertico, by M-x prompt detection for example. But Vertico tries to avoid any hacks as much as possible. For me Vertico is mostly fast enough. Then I also have a vertico-sort-threshold which simply avoids the sorting for many candidates. Please don't ask why sorting is slow, this is an Emacs feature.

But why Selectrum is slow for Embark, I have no idea!

from vertico.

oantolin avatar oantolin commented on August 17, 2024

I didn't know about the advice @minad mentioned. Does it really change that behavior for the special case of dired while keeping it in other circumstances?

Wow, Selectrum really does change this behavior just for dired, keeping it other instances. Seems a little weird.

from vertico.

minad avatar minad commented on August 17, 2024

@oantolin Did you try the current Vertico prompt-selection branch? Maybe this behavior used there would make sense for Selectrum too. It seems to me that Selectrum already works mostly like this, thanks to how it determines what to select and maybe also thanks to the advice. But the rules are more complicated overall.

from vertico.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.