Skip to content
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

Esc + H in Vi mode opens manpage causing undesirable functionality #3904

Closed
RomanSC opened this issue Mar 20, 2017 · 13 comments
Closed

Esc + H in Vi mode opens manpage causing undesirable functionality #3904

RomanSC opened this issue Mar 20, 2017 · 13 comments

Comments

@RomanSC
Copy link

@RomanSC RomanSC commented Mar 20, 2017

Version: fish, version 2.5.0
OS: Arch Linux 4.10.3-1-ARCH
Terminal: Termite

So I ran fish vi mode in sh -c 'env HOME=$(mktemp -d) fish' and problem should be immediately reproducable. In the default env enable fish_vi_key_bindings, type out a command like 'sudo fun foo' then press Esc and H, but quickly. Fish will then open a manpage for sudo. The user must then press q, but all they are trying to do is press Esc to exit insert mode then H to move back characters as in normal vi/vim

Seems to be some kind of default binding as pressing Esc then H in non-vi mode also opens a manpage for the first typed command.

Is there a workaround?

Thanks for the awesome shell.

@faho
Copy link
Member

@faho faho commented Mar 20, 2017

The issue here is that opening the man page is bound to "\eh", which is meant to be alt+h, but because of the way terminals work will also be triggered by escape+h. vi-mode obviously also has a binding for escape by itself (switching modes).

The way we figure out whether you pressed escape, then pressed "h" or pressed alt+h is waiting for a certain timeout between the keys. This is set to 100ms by default (in vi-mode, in emacs-mode it's set to 300ms), so you'll need to wait for that amount of time before pressing another key if the corresponding sequence is also bound.

This timeout can be configured through the "fish_escape_delay_ms" variable. E.g. set -g fish_escape_delay_ms 10.

Alternatively, you could remove the \eh binding - add bind -e \eh to your "fish_user_key_bindings" function.


@krader1961: I've noticed when running fish_key_reader on my machine that I'm getting less than 1 ms between characters for \eh, and I can't recall an issue where it was >1ms. (In fact I had that misconception in #3739).

Maybe our timeout is still too long? 10ms still seems like it'd leave an order of magnitude of slack for slow machines?

@krader1961
Copy link
Contributor

@krader1961 krader1961 commented Mar 21, 2017

@faho: The problem with 10ms is that is is too short except for extremely fast typists. Too, that was the original value which was causing problems which is why we increased it. A value of 100ms may be too long for moderately fast typists. I wouldn't be surprised if we conducted actual HCI (human computer interaction) tests that we would find a value in the range of 20 to 30ms to be optimal. Someone with some strong google-fu may be able to find such studies or documents describing the optimal value. Alternatively, simply figuring out how Vim handles this might be instructive.

@krader1961
Copy link
Contributor

@krader1961 krader1961 commented Mar 21, 2017

Also, the delay isn't for the meta-key case. Except for extreme situations such as running fish inside tmux on both the client and server system over generally slow connections (e.g., dialup) with extreme latency variability it is unlikely the escape and subsequent characters will ever be received with more than a millisecond between them.

@RomanSC
Copy link
Author

@RomanSC RomanSC commented Mar 21, 2017

@faho Thank you very much, that's exactly what I was looking for just a simple workaround will do. Optimally this binding could change depending on if the user is in vi_mode or not.

I tested Bash and Zsh and did some research to see if they bind to another key, but it didn't work in my other shells and these pages seem to indicate it's not default in Bash or Zsh either.
https://unix.stackexchange.com/questions/323125/is-it-possible-to-hit-shift-k-and-open-a-manual-for-a-command-in-bash
https://www.reddit.com/r/commandline/comments/3uv04b/zsh_fish_use_alth_to_view_manpage_while_editing/

The default behavior seems to be a useful feature if the user is not using vi mode though.

@faho
Copy link
Member

@faho faho commented Mar 21, 2017

Optimally this binding could change depending on if the user is in vi_mode or not.

The issue there is if we remove it, we'll just get users asking to add it back. What we've come up with is that emacs-mode and vi-mode should share all bindings that don't specifically relate to "editing text" (i.e. moving the cursor or inserting/removing characters).

It's also not specific to this binding - anything bound to alt+something will have this issue, as will most "special" keys (you know, unusual stuff like the arrow keys).

So: No, we will not remove it.


Now, what we IMHO should do here is to make it harder to accidentally hit.

The problem with 10ms is that is is too short except for extremely fast typists.

@krader1961: The way I see it, the usual way to execute a \ewhatever binding is to press alt+whatever (or another key combination that ends up sending it). In emacs-mode, we can also support escape+whatever, but since escape by itself is so important in vi-mode it seems rather unlikely that someone pressing escape+h meant \eh. It's more likely that someone wanted to move left, so they pressed escape to enter normal mode and then h to go left.

So the timeout in vi-mode should be purely for slow terminals, not slow users. That would be something like 10-20ms, not 100ms.

Note: It's unfortunate that there's a need to choose here, but given that need, we should pick the usual case over the unusual one.

@krader1961
Copy link
Contributor

@krader1961 krader1961 commented Mar 22, 2017

Yes, @faho, but the reason we increased the delay is that someone pointed out that even a fast typist could not reliably perform sequences prefaced by an escape character when typing each character independently. And at least a few people felt it was reasonable to make it possible to invoke behaviors introduced by an escape character by typing each character, including the escape, one at a time. As opposed to something like pressing [alt-X] which would send \eX. That was invented many years after the "vi" editor established the mechanism to switch from insert to command mode. I'd have to do some research to give a firm number but am confident it was more than ten years later.

It is extremely annoying that Bill Joy (the person who wrote the original vi editor) chose to use escape, character \x1B, rather than some other control character for the transition from insert to command mode. Especially since at that time the standard established by the DEC VT100 (now ANSI X3.64) to preface other magic sequences by the escape character was well known.

@RomanSC: Can you explore various values for fish_escape_delay_ms and report which value seems optimal for you? Obviously we would like you to not be deliberately trying to type [escape] followed by "h" as fast as you can. I know that I can do so fast enough to trigger the problem you observed if I try to do so. What we are trying to understand is whether 20 milliseconds, 30 ms, or some other value is optimal for disambiguating these cases.

The problem here is that any non-zero delay is problematic given "vi"editor semantics for the escape character.

@RomanSC
Copy link
Author

@RomanSC RomanSC commented Mar 22, 2017

@krader1961
man fish_key_reader ?

If I could pipe the output of fish_key_reader -c into a text file for each terminal opened somehow then let it run for a while I could give you guys a case study for this after formatting the file to only contain:

          hex:   1B  char: \c[  (or \e)

( 32.653 ms) hex: 68 char: h
bind \eh 'do something'

Otherwise it seems for me that around 30 ms is good, but I think in that case @faho has a good point.

Seems that would only be useful with more users' test cases, and especially those who use ssh/tmux etc.

@krader1961
Copy link
Contributor

@krader1961 krader1961 commented Mar 23, 2017

See also issue #3398. The $fish_escape_delay_ms value affects recognition of all multi-char sequences, not just those beginning with an escape character. Do the following:

bind \cx 'echo saw cx'
bind \cx\ce 'echo saw cxce'

Now type [ctrl-X][ctrl-E] with various delays between the two control characters. Then set fish_escape_delay_ms to various values to see how that affects your ability to invoke the second binding.

@krader1961
Copy link
Contributor

@krader1961 krader1961 commented Mar 23, 2017

Also, I just ran fish_key_reader -c (for continuous mode) and typed various sequences of characters as fast as I could. Sequences like jkl. I've got a pretty fast Mac server with a USB keyboard and some deltas were as low as 10 ms but most were in the 50-60 ms range. So I'm leaning strongly towards not lowering the default. We might want to find ways to better document how to tune the threshold.

@krader1961
Copy link
Contributor

@krader1961 krader1961 commented Mar 23, 2017

Too, a fast typist (e.g., 60 words/minute) is still typing characters at a rate that has approximately 125 ms between characters.

@linsomniac
Copy link

@linsomniac linsomniac commented Jan 23, 2018

I'm also running into problems with getting into the man pages fairly frequently, 3-5 times a day. If I push the esc time down to 10ms, I then probably can't type "ESC+e" to get enhanced editing of commands, and "Alt+e" doesn't work for me (that seems to type an a with a halo).

I do really like the suggestion features in fish, but it has been a hard transition from zsh as a vi user.

@krader1961
Copy link
Contributor

@krader1961 krader1961 commented Jan 23, 2018

@linsomniac, The reason [alt]+letter doesn't work is because your terminal is treating [alt] as a unicode compose key rather than a meta key that prefixes an escape char to the next key. That has nothing to do with fish and you'll see the same behavior with bash and zsh. If you're using iTerm2 open the terminal profile you're using, switch to the "Keys" tab and find the following settings:

iterm

Other terminals have similar config options.

@linsomniac
Copy link

@linsomniac linsomniac commented Jan 23, 2018

Thanks. I did understand that it was my terminal, not fish. It's just that the issue is particularly bad for me and the person who opened this issue because ESC+h is something that is frequently typed as just a normal part of editing in vi mode.

I ended up unbinding \eh in regular and insert modes and changed it instead to \eH

@faho faho added the vi-mode label Sep 18, 2018
@faho faho removed this from the fish-future milestone Feb 20, 2019
@faho faho added this to the fish 3.1.0 milestone Feb 20, 2019
@github-actions github-actions bot locked as resolved and limited conversation to collaborators Apr 17, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

4 participants