Remap vim save commands to a custom function

This commit is contained in:
Michael Campagnaro 2021-12-15 21:49:17 -05:00
parent 54a8774f19
commit ac9fcce0e0

175
vimrc
View File

@ -385,65 +385,16 @@ augroup campoCmds
autocmd BufReadPre *.asm let g:asmsyntax = "fasm"
" Auto reload VIM when settings changed.
" Need to use silent! now because the save commands call a custom function
" and without the silent we would see an error after sourcing saying that
" we can't redefine the function that initiated the save. :ReloadVimrcError
"
" @fixme Reload lvimrc after sourcing this file on a save. I tried calling
" a function that does the source and a call to lvimrc's API but got an
" error complaining that the function cannot be created while it's in use.
autocmd BufWritePost .vimrc source $MYVIMRC
autocmd BufWritePost *.vim source $MYVIMRC
autocmd BufWritePost ~/.vimrc.private source $MYVIMRC
function! s:CreateCtags()
" Only allow one instance of ctags to run in this directory at any given time.
let l:lock_file = "ctags.lock"
if filereadable(l:lock_file) || filereadable("newtags")
" Don't print a warning because this will always show when saving multiple files at the same time with a :wa or :xa
return
endif
let l:extension = tolower(expand('%:e'))
if (g:campo_force_ctags_regardless_of_extension == 0) && (index(g:campo_extensions_that_run_ctags, l:extension) < 0)
echo "Skipping ctags generation"
return
endif
" Abort if we're editing a text file. This won't be an exhaustive
" filter. We can restrict what goes into the tag file
" First determine if we're in a root drive directory. If we are then
" we bail because we don't want to recurse across the entire drive!
let l:path = expand('%:p:h')
let l:path_without_slashes = substitute(l:path, "/", "", "g")
if (strchars(l:path) - strchars(l:path_without_slashes)) <= 1
call PrintError("Not going to run ctags because the file is in a root drive directory")
return
endif
" Always ignore .git and node_modules
let g:campo_ctags_exclude = g:campo_ctags_exclude + ['.git', 'node_modules']
let l:exclude_list = ""
for name in g:campo_ctags_exclude
let l:exclude_list = l:exclude_list . "--exclude=" . name . " "
endfor
" Include local variables for C-like languages.
let l:ctags_cmd = 'ctags '.l:exclude_list.' '.g:campo_custom_ctags_args.' --c-types=+l --c++-types=+l -o newtags'
" Add the filename to the ctags command if not running in recursive mode.
let l:recursive = matchstr(g:campo_custom_ctags_args, '\(-R\s\)\|\(-R$\)\|\(--recurse=yes\)\|\(--recurse\s\)\|\(--recurse$\)')
if l:recursive == ''
let l:ctags_cmd = l:ctags_cmd . ' ' . expand('%:t')
echo "Creating non-recursive ctags"
else
echo "Creating recursive ctags"
endif
" The ampersand at the end is to make this run in the background. I had to group the
" commands in parens to make the chained commands run in the background.
let l:cmd = '!(touch '.l:lock_file.'; '.l:ctags_cmd.'; mv newtags tags &>/dev/null; rm '.l:lock_file.') &'
silent! exec l:cmd
endfun
" Generate ctags on save.
autocmd BufWritePost * call s:CreateCtags()
autocmd BufWritePost .vimrc silent! source $MYVIMRC
autocmd BufWritePost *.vim silent! source $MYVIMRC
autocmd BufWritePost ~/.vimrc.private silent! source $MYVIMRC
" Remove trailing whitespace when saving any file.
function! s:StripTrailingWhitespaces()
@ -603,6 +554,10 @@ augroup END
"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
" MISC KEY MAPS
"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
" Lowercase the e (have a habit of making it uppercase).
:ca E e
" Mapping ESC in insert mode and command mode to double i.
imap jj <Esc>
@ -619,27 +574,107 @@ nnoremap <silent> <leader>rv :source $MYVIMRC<cr>
" the full %/ quickly otherwise it won't replace it.
cmap %/ %:p:h/
"------------------------------------------------------------
" Remap saving and quiting.
nnoremap <leader>w :w!<cr>
"
" I used to have a BufWritePost autocommand that ran the ctags generator but
" it ends up running multiple times when saving multiple buffers at once. In
" order to only call it once for a group of saves I've had to remap the
" various save commands to a function call.
function! s:CreateCtags()
" Only allow one instance of ctags to run in this directory at any given time.
let l:lock_file = "ctags.lock"
if filereadable(l:lock_file) || filereadable("newtags")
" Don't print a warning because this will always show when saving multiple files at the same time with a :wa or :xa
return
endif
let l:extension = tolower(expand('%:e'))
if (g:campo_force_ctags_regardless_of_extension == 0) && (index(g:campo_extensions_that_run_ctags, l:extension) < 0)
echo "Skipping ctags generation"
return
endif
" Abort if we're editing a text file. This won't be an exhaustive
" filter. We can restrict what goes into the tag file
" First determine if we're in a root drive directory. If we are then
" we bail because we don't want to recurse across the entire drive!
let l:path = expand('%:p:h')
let l:path_without_slashes = substitute(l:path, "/", "", "g")
if (strchars(l:path) - strchars(l:path_without_slashes)) <= 1
call PrintError("Not going to run ctags because the file is in a root drive directory")
return
endif
" Always ignore .git and node_modules
let g:campo_ctags_exclude = g:campo_ctags_exclude + ['.git', 'node_modules']
let l:exclude_list = ""
for name in g:campo_ctags_exclude
let l:exclude_list = l:exclude_list . "--exclude=" . name . " "
endfor
" Include local variables for C-like languages.
let l:ctags_cmd = 'ctags '.l:exclude_list.' '.g:campo_custom_ctags_args.' --c-types=+l --c++-types=+l -o newtags'
" Add the filename to the ctags command if not running in recursive mode.
let l:recursive = matchstr(g:campo_custom_ctags_args, '\(-R\s\)\|\(-R$\)\|\(--recurse=yes\)\|\(--recurse\s\)\|\(--recurse$\)')
if l:recursive == ''
let l:ctags_cmd = l:ctags_cmd . ' ' . expand('%:t')
echo "Creating non-recursive ctags"
else
echo "Creating recursive ctags"
endif
" The ampersand at the end is to make this run in the background. I had to group the
" commands in parens to make the chained commands run in the background.
let l:cmd = '!(touch '.l:lock_file.'; '.l:ctags_cmd.'; mv newtags tags &>/dev/null; rm '.l:lock_file.') &'
silent! exec l:cmd
endfun
" @note We have an autocmd that reloads the vimrc files after they're saved.
" These write functions below will not be reloaded because they initiate the
" save. So if you make changes to them then you need to manually reload this
" file using <leader>rv or whatever. :ReloadVimrcError
function! DoSingleWrite()
write
call s:CreateCtags()
endfunction
function! DoSingleWriteThenQuit()
write
call s:CreateCtags()
quit
endfunction
function! DoMultiWrite()
let l:current_buffer = bufnr("%")
bufdo wa
" Restore the last buffer because it may have changed.
exec "buffer " . l:current_buffer
call s:CreateCtags()
endfunction
cnoreabbrev w :call DoSingleWrite()
cnoreabbrev W :call DoSingleWrite()
cnoreabbrev wa :call DoMultiWrite()
cnoreabbrev Wa :call DoMultiWrite()
cnoreabbrev WA :call DoMultiWrite()
cnoreabbrev wq :call DoSingleWriteThenQuit()
cnoreabbrev Wq :call DoSingleWriteThenQuit()
cnoreabbrev WQ :call DoSingleWriteThenQuit()
nnoremap <leader>w :call DoSingleWrite()<cr>
nnoremap <leader>x :call DoSingleWriteThenQuit()<cr>
nnoremap <leader>q :q<cr>
nnoremap <leader>qq :q!<cr>
nnoremap <leader>x :x<cr>
:ca Wa wa!
:ca WA wa!
:ca WQ wq
:ca Wq wq
:ca W w!
:ca Q q
" Lowercase the e (have a habit of making it uppercase).
:ca E e
command! Q q " Bind :Q to :q
command! Qall qall
cnoreabbrev Q q
command! Qa qall
" Disable Ex mode.
noremap Q <Nop>
"------------------------------------------------------------
" Open a terminal within vim. Use `exit` to close it.
if exists(':terminal')
noremap <leader>t :terminal<cr>