Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 2 years ago.
Improve this question
Which custom key bindings do you use to increase productivity in Vim?
My two favorites are:
inoremap jj <Esc>
" Clear screen clears search highlighting.
nnoremap <C-L> :nohl<CR><C-L>
Window Management
" Window splitting
nmap <silent> <leader>sh :leftabove vnew<cr>
nmap <silent> <leader>sl :rightbelow vnew<cr>
nmap <silent> <leader>sk :leftabove new<cr>
nmap <silent> <leader>sj :rightbelow new<cr>
nmap <silent> <leader>swh :topleft vnew<cr>
nmap <silent> <leader>swl :botright vnew<cr>
nmap <silent> <leader>swk :topleft new<cr>
nmap <silent> <leader>swj :botright new<cr>
" Scroll the window next to the current one
" (especially useful for two-window splits)
nmap <silent> <leader>j <c-w>w<c-d><c-w>W
nmap <silent> <leader>k <c-w>w<c-u><c-w>W
Text Editing
" Toggle search highlighting
nmap <silent> <leader>/ :set hlsearch!<cr>
" Toggle paste mode
" (prefer this over 'pastetoggle' to echo the current state)
nmap <leader>p :setlocal paste! paste?<cr>
" Select the last edited (or pasted) text
nmap gv `[v`]
" Keep lines that do (or do not) contain the last search term
nmap <leader>v/ :v/<c-r>//d<cr>gg
nmap <leader>g/ :g/<c-r>//d<cr>gg
" Email (de-)quotation
nmap <leader>q vip:s/^/> /<cr>
vmap <leader>q :s/^/> /<cr>
nmap <leader>Q vip:s/^> //<cr>
vmap <leader>Q :s/^> //<cr>
File Opening and Saving
" Save and restore session
nmap <leader>ss :wa<cr>:mksession! $HOME/.vim/sessions/
nmap <leader>rs :wa<cr>:source $HOME/.vim/sessions/
" Write buffer through sudo
cnoreabbrev w!! w !sudo tee % >/dev/null
" Change the current directory to the directory of the file in buffer
nmap <silent> <leader>cd :cd %:p:h<cr>:pwd<cr>
" Open file located in the same directory as the current one
nmap <leader>e :e <c-r>=expand('%:p:h').'/'<cr>
Grep the word under cursor:
Using the following grepprg options it will search recursively into the current directory excluding and including some specific files.
" Quick Grep
noremap <Leader>g :grep<space><C-r><C-w><CR>:copen<CR><CR><C-W>b
set grepprg=grep\ -nH
\\--include='*.c'
\\--include='*.cpp'
\\--include='*.h'
\\--exclude-dir='.svn'
\\--exclude='*.svn-base'
\\--exclude-dir='OBJ'
\\--exclude='symTbl.c'
\\ $*
\\ -R\ .
It greps the word under cursor, then open the Quickfix Window and move the cursor to the bottow window (which should be the list of grep results)
This is probably one of the shortcut I use the most, and it saves lots of typing !
Moving around quickly between windows
noremap <C-j> <C-W>j
noremap <C-k> <C-W>k
noremap <C-h> <C-W>h
noremap <C-l> <C-W>l
It is quite intuitive and handy to move around when your screen is split horizontally and vertically.
The following command remaps ; to : in command mode, saving you from wasting precious milliseconds holding and releasing the Shift key when typing commands like :wq:
" Remap ";" to ":"
map ; :
noremap ;; ;
If you need to type an actual ;, just press it twice.
Insert mode
" <esc> in normal mode clears highlight
nnoremap <silent> <esc> :noh<cr><esc>
Command Line Editing
" copy an entire word from the line above instead of just one
inoremap <expr> <c-y> matchstr(getline(line('.')-1), '\%' .
\ virtcol('.') . 'v\%(\k\+\\|.\)')
" Insert Directory of current buffer and open completion
cnoremap <expr> <c-k> getcmdline()[getcmdpos()-2] == " " ?
\ expand("%:h") . "/\<c-d>" : "\<c-d>"
let mapleader=","
" omnicompletion : words
inoremap <leader>, <C-x><C-o>
" omnicompletion : filepaths
inoremap <leader>: <C-x><C-f>
" omnicompletion : lines
inoremap <leader>= <C-x><C-l>
" toggle TagList
nnoremap <leader>l :TlistToggle<CR>
" toggle NERDTree
nnoremap <leader>n :NERDTreeToggle<CR>
" I like vertically aligned assignation operators
nnoremap <leader>a :Tabularize<Space>
" with | marking the cursor
" it turns this
" function foo(){|}
" into this
" function foo(){
" |
" }
inoremap <C-Return> <CR><CR><C-o>k<Tab>
" push the current ligne up and down
nnoremap <M-D-Up> ddKp
nnoremap <M-D-Down> ddP
" swap word under the cursor with previous word on the left
" from the Vim wiki
nnoremap <M-D-Left> "_yiw?\w\+\_W\+\%#<CR>:s/\(\%#\w\+\)\(\_W\+\)\(\w\+\)/\3\2\1/<CR><C-o><C-l>
" swap word under the cursor with next word on the right
" from the Vim wiki
nnoremap <M-D-Right> "_yiw:s/\(\%#\w\+\)\(\_W\+\)\(\w\+\)/\3\2\1/<CR><C-o>/\w\+\_W\+<CR><C-l>
" and I have lusty-explorers "modes" mapped to:
" "files" <leader>f
" "buffers" <leader>b
" "grep" <leader>g
Useful for navigating up/down long lines that wrap to multiple lines on your display: Alt + ↑ or ↓ arrow keys move through screen lines rather than file lines.
map <A-Down> gj
map <A-Up> gk
imap <A-Up> <ESC>gki
imap <A-Down> <ESC>gji
Related
I have an existing .vimrc which was created on macintosh computer and contains mappings like this:
"------------------------------------------------------------
" keyboard shortcuts
"------------------------------------------------------------
nmap <S-Tab> :wincmd W<CR>
nmap <S-q> :bp\|bd #<CR>
nmap « :bp\|bd #<CR>
nmap ¢ :sp<CR>
nmap ¶ :vsp\|wincmd w<CR>
nmap :Q :qa<CR>
nmap :W :wqa<CR>
nmap ≠ :q<CR>
nmap ESC[1;9B 15j
nmap ESC[1;9A 15k
nmap ^? :w<CR>
nmap ø :edit
nmap ESC[1;5B 15j
nmap ESC[1;5A 15k
vmap ESC[1;5B 15j
vmap ESC[1;5A 15k
nmap ^\ :edit
nmap ^] :wincmd w<CR>
nmap <F9> :w<CR>:Make<CR><CR>
imap <F9> <ESC>:w<CR>:Make<CR>
nmap <C-n> :cnext<CR>
nmap <C-p> :cprev<CR>
nmap <F5> :Grep
nmap # g~w w
nmap <F10> :ConqueGdb
nmap ^A :sav %:h/filename
nmap ESC[1;2D :NERDTreeToggle<CR>
nmap ESC[1;2B :sp\|wincmd w<CR>
nmap ESC[1;2C :vsp\|wincmd w<CR>
nmap ESC[1;5D :q<CR>
nmap ESC[1;5F :BuffergatorToggle<CR>
nmap ESC[1;6D w
nmap ESC[1;6B b
Now I have transferred this .vimrc to a new linux computer (debian-based), but half of the shortcuts don't work anymore. I guess thats because the mac interpretes some of the keystrokes differently as compared to the linux computer (both computers do have vim v8.1).
When creating shortcuts, I remember that there was a function in vim which would print out the key codes when you press the keys, however that was about 10 years ago and I don't remember it, and I can't find via google.
To be precise, it was like "press XYZ in vim, then press e.g. CTRL+S, then vim would print the corresponding key code to be used in the mappings".
How can I do this now, in order to make those shortcuts work on linux also?
You're looking for :help i_CTRL-V:
For special keys, the terminal code is inserted.
For example, in my Gnome Terminal pressing <C-V><Right> gives ^[OC and <C-V><F12> gives ^[[24~.
In general, you should prefer Vim's key-notation whenever possible. If you do need to insert specific escape codes and need to support multiple platforms with a single ~/.vimrc, you can wrap the mapping definitions in conditions like if has('mac') or if $TERM ==# 'screen256-color'.
Here are the vim commands/configs I'm working with:
noremap ' <NOP>
let mapleader = "'"
noremap <leader>cc :leftabove new<CR>
noremap <leader>hh :leftabove vnew<CR>
noremap <leader>tt :rightbelow new<CR>
noremap <leader>nn :rightbelow vnew<CR>
For key choices / positional context: I'm using dvorak, so the apostrophe is the equivalent of qwerty "q", and chtn is equivalent of ijkl
What I'm experiencing is that when I do <leader>hh, I correctly get a new pane to the left. But, none of the other commands work.
Any ideas why?
Update
So, I've found that these work:
" Pane Creating
nmap <leader><A-c> :leftabove new<CR>
nmap <leader><A-h> :leftabove vnew<CR>
nmap <leader><A-t> :rightbelow new<CR>
nmap <leader><A-n> :rightbelow vnew<CR>
But I don't know why.
As far as I know, I don't have any <leader> chtn mappings
Update
output of :verbos map <leader>
At present I have the following mappings in my Vimrc:
" Quick Buffer switch mappings {{{
" The idea is to press <leader> and then the number from normal mode to switch
" e.g. `,2` would switch to the second buffer (listed at the top of the
" airline strip
nnoremap <Leader>1 :1b<CR>
nnoremap <Leader>2 :2b<CR>
nnoremap <Leader>3 :3b<CR>
nnoremap <Leader>4 :4b<CR>
nnoremap <Leader>5 :5b<CR>
nnoremap <Leader>6 :6b<CR>
nnoremap <Leader>7 :7b<CR>
nnoremap <Leader>8 :8b<CR>
nnoremap <Leader>9 :9b<CR>
nnoremap <Leader>10 :10b<CR>
nnoremap <Leader>11 :11b<CR>
nnoremap <Leader>12 :12b<CR>
nnoremap <Leader>13 :13b<CR>
nnoremap <Leader>14 :14b<CR>
nnoremap <Leader>15 :15b<CR>
nnoremap <Leader>16 :16b<CR>
" Quick Buffer wipe/delete keys. Press <Leader> and then d and buffer number
" e.g. `,d2` would wipe buffer 2
nnoremap <Leader>d1 :Bdelete 1<CR>
nnoremap <Leader>d2 :Bdelete 2<CR>
nnoremap <Leader>d3 :Bdelete 3<CR>
nnoremap <Leader>d4 :Bdelete 4<CR>
nnoremap <Leader>d5 :Bdelete 5<CR>
nnoremap <Leader>d6 :Bdelete 6<CR>
nnoremap <Leader>d7 :Bdelete 7<CR>
nnoremap <Leader>d8 :Bdelete 8<CR>
nnoremap <Leader>d9 :Bdelete 9<CR>
nnoremap <Leader>d10 :Bdelete 10<CR>
nnoremap <Leader>d11 :Bdelete 11<CR>
nnoremap <Leader>d12 :Bdelete 12<CR>
nnoremap <Leader>d13 :Bdelete 13<CR>
nnoremap <Leader>d14 :Bdelete 14<CR>
nnoremap <Leader>d15 :Bdelete 15<CR>
nnoremap <Leader>d16 :Bdelete 16<CR>
" }}}
They work great but I can't help thinking this should be smarter/DRYer in the vimrc. What about if I open a buffer with number 17 for example.
Is there a way of intelligently mapping these so that a user could enter and then any buffer number to have the buffer open?
You can use meta-programming with :execute to automate the creation of those mappings:
for i in range(1, 99)
execute printf('nnoremap <Leader>%d :%db<CR>', i, i)
endfor
It is also possible to define a single mapping (with just a prefix), that then queries the number via getchar(). The challenge here is to determine when to end this, something that you get for free (due to 'timeout') with the separate mappings. That's why I would prefer the first solution here.
<c-6> switches to the previous buffer. However you can also provide a count which will be used to switch to that buffer. E.g. 6<c-6> is equivalent to :b 6.
I still can't help but think these buffer commands are a bit awkward because have to keep buffer numbers and files straight in your head. I think using some of :b native features could be of some help to you:
:b command can take a partial filenames. e.g. :b foo
:b can use globs so you can add some fuzziness. e.g. :b foo*bar.c
<tab> to complete the filenames
<c-d> for listing out the buffer names
split with the :sb command which takes all the same arguments as :b
I find :bdelete a bit dangerous they way you have it. I would suggest you just switch to a buffer and then do :bd to delete the current buffer. However :bd can take partial filenames and globs as well just like :b.
I have also seen ~/.vimrc files where people use a mapping to call :ls and then start the prompt with :b. Think of more of a menu based approach.
nnoremap <leader>b :ls<cr>:b<space>
For more help see:
:h ctrl-6
:h :b
:h :sb
:h :bd
:h :ls
Here is a slightly different strategy that only uses a single mapping:
:nnoremap <silent> <key> :<C-u>try \| execute "b" . v:count \| catch \| endtry<CR>
Now you can do 3<key> to go to buffer number 3. I'll leave it up to you to find the right <key>.
This question already has answers here:
Remapping :Wq to :wq in vim
(3 answers)
Closed 8 years ago.
I have the following keymappings in my vimrc
nmap :Q<CR> :q<CR>
nmap :W<CR> :w<CR>
nmap :WQ<CR> :wq<CR>
However, they do nothing. Vim complains that Q isn't a valid command. Same for W and WQ. I restarted vim and everything. I'm trying to figure this out and I'm also hoping to map Ctrl+W and the arrow keys to just Ctrl+h for changing windows left and etc. How can I go about doing that?
For your second question:
nnoremap <C-h> <C-w>h
nnoremap <C-j> <C-w>j
nnoremap <C-k> <C-w>k
nnoremap <C-l> <C-w>l
Every time I enter the Insert mode in vim using A and press Enter to go to the next line, vim automatically removes all indentation from the current line. For instance, ideally, it should be like this -
14 echo $sample;
15 $ai = system("python ai.py " + $sample, $retVal);
If I press A on line 15 and then <CR>, this is what my vim looks like -
14 echo $sample;
15 $ai = system("python ai.py " + $sample, $retVal);
16
This is my .vimrc -
"General
set nu " Set line numbers
set hlsearch " Set search highlight
set shiftwidth=2
set tabstop=2
"Pathogen
execute pathogen#infect()
call pathogen#helptags()
syntax on
filetype plugin indent on
"ConqueTerm
command Cterm split | ConqueTerm bash
nnoremap <silent> sh :Cterm<CR>
"NerdTree -
"Fs open Nerdtree on the same tab. Nfs opens NerdTree in new tab.
command Fs NERDTree
command Nfs tabedit | NERDTree
nnoremap <silent> fs :Fs<CR>
"TagBar
nnoremap <silent> tt :TagbarToggle<CR>
"Omni Completion
filetype plugin on
filetype indent on
inoremap <C-Space> <C-X><C-o>
"Editor
command Ide NERDTree | TagbarToggle
"Move between split windows
nmap <silent> <A-Up> :wincmd k<CR>
nmap <silent> <A-Down> :wincmd j<CR>
nmap <silent> <A-Left> :wincmd h<CR>
nmap <silent> <A-Right> :wincmd l<CR>
"Drag words like in Windows
nnoremap <C-Left> b
vnoremap <C-S-Left> b
nnoremap <C-S-Left> gh<C-O>b
inoremap <C-S-Left> <C-\><C-O>gh<C-O>b
nnoremap <C-Right> w
vnoremap <C-S-Right> w
nnoremap <C-S-Right> gh<C-O>w
inoremap <C-S-Right> <C-\><C-O>gh<C-O>wA
" Start Syntastic in passive mode
let g:syntastic_mode_map = { 'mode': 'passive' }
nnoremap <silent> ch :SyntasticCheck<CR>
Any idea what's going on?
You probably want to set autoindent in your vimrc file:
:set ai
You can also verify if autoindent was previously set (for example through the filetype plugins) by checking its value with
:set ai?