15

I would like to map my CapsLock to Escape. How do I represent CapsLock in .vimrc?

I know to map space to a command I would do something like this:

:map <space> viw

How would I map CapsLock to Escape without doing a registry hack - I'm looking for a Vim command?

If that is not possible without a hack or additional software I would like to assign the shortcut jj to ESC in .vimrc . I'm currently doing this:

inoremap jj <esc>

However if I'm in visual mode this does not work. How could I make jj emulate the escape key?

1
  • 1
    Are you wanting this in X, the console or both? Also, please look at my edits and format your last edit as per the site styles.
    – jasonwryan
    Nov 2, 2014 at 0:30

6 Answers 6

17

I don't think you can map CapsLock from within Vim. You remap it within X using setxkbmap:

setxkbmap -option caps:swapescape

For remapping in the console, if your distro uses systemd, you can use a custom keyboard layout in /etc/vconsole.conf as described on the Arch Wiki, and for other init systems see this U&L answer.

2
  • I updated my question
    – Rajeshwar
    Nov 2, 2014 at 0:27
  • 6
    How do you set it so both are escape? Sep 2, 2016 at 22:50
10

If you want to map both Caps Lock and Escape to Escape, instead of swapping them, use

setxkbmap -option caps:escape

instead of ...:swapescape.

Use

setxkbmap -option

to clear any existing options, then the above should work.

1
4

You can use a call to xmodmap on Vim startup to map Capslock to Escape. The modification can be reverted once you leave Vim. Add the following lines to your .vimrc:

au VimEnter * silent! !xmodmap -e 'clear Lock' -e 'keycode 0x42 = Escape'
au VimLeave * silent! !xmodmap -e 'clear Lock' -e 'keycode 0x42 = Caps_Lock'

However, this will lead to problems if you have multiple Vim sessions. Once you close one of them, the modification is reverted for all of them, since xmodmap operates globally.

1
1

inoremap means insert mode non-recursive map. vnoremap is visual mode non-recursive map. So vnoremap jj <esc> is what you want.

0

Try this in your ~/.vimrc or ~/.vim/vimrc file :

:autocmd BufWinEnter * !setxkbmap -option caps:swapescape
:autocmd BufWinLeave * !setxkbmap -option

Instead of the first line, you can use an alias in ~/.bashrc or ~/.profile :

alias vim="setxkbmap -option caps:swapescape && vim"

The drawback in these approaches being that as long as you haven't closed the vim, your CapsLock will be your Escape and vice-versa, machine-wide.

Solution to that:

For this, I am using timeout with the key-binding swap only during the required mode (that is, InsertMode):
au CursorHoldI * stopinsert
au InsertEnter * silent! let updaterestore=&updatetime | set updatetime=15000 | execute "!setxkbmap -option caps:swapescape" | redraw!
au InsertLeave * silent! let &updatetime=updaterestore | execute "!setxkbmap -option" | redraw!

Now, during the InsertMode, the CapsLock and Escape will interchange machine-wide, but since I have set a time-out for the InsertMode to be 15000, I need not worry about it as it will automatically be reversed in 15 seconds of inactivity. ;-)

-Himanshu

2
  • Doesn't this method also mean that if you close one of two windows, then you loose the remap?
    – Krish
    Feb 8, 2021 at 13:52
  • Well I (personally) only want the remap during insert mode (during typing). Otherwise I'm happy to use the Esc key as escape key. Hence the solution.. Feb 22, 2021 at 20:14
0

For anyone coming from Ubuntu 22.04 and having issues with

setxkbmap -option caps:swapescape

An Ask Ubuntu answer provides an alternative method:

dconf write "/org/gnome/desktop/input-sources/xkb-options" "[ 'caps:swapescape']"
New contributor
tangoyankee is a new contributor to this site. Take care in asking for clarification, commenting, and answering. Check out our Code of Conduct.

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.