2

When I press <Esc> in visual mode, I don't immediately return to normal mode (the selection persists). I think that is because I have a mapping defined in visual mode shat starts from <Esc>. I tried doing the following to find that mapping:

:redir! > vim_keys.txt
:silent verbose map
:redir END

But there are no mappings that start with <Esc>:

v  ["          *@:<C-U>exe "normal! gv"|call search('\%(^\s*".*\n\)\%(^\s*"\)\@!', "bW")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
n  ["          *@:call search('\%(^\s*".*\n\)\%(^\s*"\)\@!', "bW")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
v  []          *@m':<C-U>exe "normal! gv"|call search('^\s*endf*\%[unction]\>', "bW")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
n  []          *@m':call search('^\s*endf*\%[unction]\>', "bW")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
v  [[          *@m':<C-U>exe "normal! gv"|call search('^\s*fu\%[nction]\>', "bW")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim n  [[          *@m':call search('^\s*fu\%[nction]\>', "bW")<CR> Last set from /usr/share/vim/vim80/ftplugin/vim.vim
v  ]"          *@:<C-U>exe "normal! gv"|call search('^\(\s*".*\n\)\@<!\(\s*"\)', "W")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
n  ]"          *@:call search('^\(\s*".*\n\)\@<!\(\s*"\)', "W")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
v  ][          *@m':<C-U>exe "normal! gv"|call search('^\s*endf*\%[unction]\>', "W")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
n  ][          *@m':call search('^\s*endf*\%[unction]\>', "W")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
v  ]]          *@m':<C-U>exe "normal! gv"|call search('^\s*fu\%[nction]\>', "W")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
n  ]]          *@m':call search('^\s*fu\%[nction]\>', "W")<CR>
    Last set from /usr/share/vim/vim80/ftplugin/vim.vim
v  <C-Z>       * <Nop>
    Last set from ~/.vimrc
n  <Space>     * zR
    Last set from ~/.vimrc
n  ,bd         * :Bclose<CR>
    Last set from ~/.dotfiles/.vim/plugin/bclose.vim
   ,             <Plug>(easymotion-prefix)
    Last set from ~/.vimrc
n  ,gl         * :!git log<CR>
    Last set from ~/.vimrc
n  ,gp         * :!git push<CR>
    Last set from ~/.vimrc
n  ,gc         * :!git commit -m '
    Last set from ~/.vimrc
n  ,ga         * :!git add
    Last set from ~/.vimrc
n  ,gs         * :!git status<CR>
    Last set from ~/.vimrc
n  ,rs         * :so $MYVIMRC<CR>
    Last set from ~/.vimrc
n  ,rr         * :vsplit $MYVIMRC<CR>
    Last set from ~/.vimrc
n  ,sc         * :SessionClose<CR>
    Last set from ~/.vimrc
n  ,ss         * :SessionSave<CR>
    Last set from ~/.vimrc
n  ,sl         * :SessionList<CR>
    Last set from ~/.vimrc
n  =A          * gg=G<C-O><C-O>
    Last set from ~/.vimrc
n  H           * ^
    Last set from ~/.vimrc
n  L           * $
    Last set from ~/.vimrc
n  Q           * :q<CR>
    Last set from ~/.vimrc
v  gx            <Plug>NetrwBrowseXVis
    Last set from /usr/share/vim/vim80/plugin/netrwPlugin.vim
n  gx            <Plug>NetrwBrowseX
    Last set from /usr/share/vim/vim80/plugin/netrwPlugin.vim
o  p           * i(
    Last set from ~/.vimrc
v  <Plug>NetrwBrowseXVis * :<C-U>call netrw#BrowseXVis()<CR>
    Last set from /usr/share/vim/vim80/plugin/netrwPlugin.vim
n  <Plug>NetrwBrowseX * :call netrw#BrowseX(expand((exists("g:netrw_gx")? g:netrw_gx : '<cfile>')),netrw#CheckIfRemote())<CR>
    Last set from /usr/share/vim/vim80/plugin/netrwPlugin.vim
n  <F2>        * :wq<CR>
    Last set from ~/.vimrc
n  <F1>        * <Nop>
    Last set from ~/.vimrc
n  ´           * :set list!<CR>:echo "List is ".&expandtab<CR>
    Last set from ~/.vimrc
n  ³           * :set expandtab!<CR>:echo "Expand tab is ".&expandtab<CR>
    Last set from ~/.vimrc
n  ö           * :vs<CR>
    Last set from ~/.vimrc
n  ó           * :%s/
    Last set from ~/.vimrc
n  ÷           * :set wrap!<CR>
    Last set from ~/.vimrc
n  î           * :tabnext<CR>
    Last set from ~/.vimrc
n  ð           * :tabprevious<CR>
    Last set from ~/.vimrc
n  ì           * :!ls<CR>
    Last set from ~/.vimrc
n  æ           * :Grep
    Last set from ~/.vimrc
n  å           * :e
    Last set from ~/.vimrc
n  ï           * :b
    Last set from ~/.vimrc
n  ô           * :call ReportFileSaveMark()<CR>
    Last set from ~/.vimrc

How do I find out why my Vim doesn't immediately exit visual mode when I press <Esc>?

  • 2
    You have mappings whose lhs are <Left>, <Right>, <S-Tab>. On my machine, they all produce a sequence of keys beginning with Escape. To check whether this is the case on your machine too, try to insert them literally on the command-line, by pressing C-v Left, C-v Right, C-v S-Tab. You may need to tweak the options 'timeoutlen' and 'ttimeoutlen'. What are their values? Does the issue persist if you execute: set timeout timeoutlen=3000 ttimeoutlen=100 (taken from :h 'ttm)? – user938271 Sep 24 '18 at 17:26
  • 1
    @user938271 timeoutlen=1000, ttimeoutlen=-1. I removed all mappings that start with Left, Right or S-Tab and it didn't help. But setting ttimeoutlen=100 did help, thanks. – jojman Sep 24 '18 at 17:37
  • @user938271 When you get around to it, you should add your comment as an answer so that it can help others that stumble upon this question, and so that jojman can accept it. – ZeroKnight Sep 24 '18 at 17:59
3

It's possible that you had a mapping in visual mode whose {lhs} produces a sequence of key codes beginning with Escape. You can check what is the sequence of key codes produced by a key by pressing on the command-line:

C-v <key>

For example, on my machine, F1 produces:

^[OP

^[ is the caret notation of the Escape key.

If you have a visual-mode mapping whose {lhs} is F1, when you press Escape in visual mode, Vim may wait for OP to come.

You can tweak the amount of time Vim waits for a sequence of key codes to complete with the option 'ttimeoutlen'. By default, its value is -1, which means that Vim uses the value of 'timeoutlen'.
This other option controls the amount of time Vim waits for the {lhs} of a mapping to complete. The default value of the latter is 1000ms.

The help at :h 'ttm suggests the following command:

:set timeout timeoutlen=3000 ttimeoutlen=100
     ├─────┘ ├─────────────┘ ├─────────────┘
     │       │               └ wait 0.1s for a sequence of key codes to complete
     │       │
     │       └ waits 3s for a mapping to complete
     │
     └ don't wait indefinitely for the `{lhs}` a mapping or a sequence of key code to complete

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.