How to toggle (Vimplug) plugins on and off on the fly? - vim

Using COC on multiple instances can really take a toll on my intel i3+4GB machine.
So I was wondering if I could toggle it on demand.
I have managed to turn it off by default and toggle it on using Vimplug's built in feature like the following.
Plug 'neoclide/coc.nvim', {'branch': 'release', 'on': 'CocToggle' }
However, I'm not sure how to toggle it off.
Any help would be highly appreciated!
P.S.: I have tried CocDisable and didn't notice any practical benefits that would minimize the resource usage like killing the gazillion node processes started by COC for each instances!
Solution
I ended up writing the following function for my use case.
Plug 'neoclide/coc.nvim', {'branch': 'release' }
let g:coc_start_at_startup = 0
let s:coc_enabled = 0
function! ToggleCoc()
if s:coc_enabled == 0
let s:coc_enabled = 1
CocStart
echo 'COC on'
else
let s:coc_enabled = 0
echo 'COC off'
call coc#rpc#stop()
endif
endfunction
nnoremap <silent> <leader>h :call ToggleCoc()<cr>

My use case (I use vim-plug) can be different but it could help. Normally my nerdtrhee is disabled until I call it throught a mapping
Plug 'scrooloose/nerdtree', { 'on': 'NERDTreeToggle' }
nnoremap <F2> :NERDTreeToggle<cr>
And I have a function to load any plugin that is disabled on startup
if !exists('*LoadPluginFunction')
fun! LoadPluginFunction(pluginname)
let l:curpos = getcurpos()
execute plug#load(a:pluginname)
call cursor(l:curpos[1], l:curpos[2])
return ''
endfun
endif
command! -nargs=1 LoadPlugin :call LoadPluginFunction(<q-args>)
If I want to load it manyally I call:
:LoadPlugin nerdtree
Finally I have found a coc option that can help you:
let g:coc_start_at_startup = 0
You can start your vim and create a mapping to load the coc plugin manually

Related

Vim phpcomplete (omnifunc) doesn't work, detects error while processing function phpcomplete#CompletePHP

while writing PHP, when I press (C-X) + (C-O) for auto completion this is the error I get
Error detected while processing function phpcomplete#CompletePHP[131]..function phpcomplete#CompletePHP[63]..phpcomplete#GetCurrentName
Space:
and when I retry pressing the keys this is the error I get
E565: Not allowed to change text or change window
and I can't reproduce the first error ("Error detected while processing...") unless I close vim and reopen it.
my .vimrc config is the following:
syntax on
call plug#begin()
Plug 'rust-lang/rust.vim'
Plug 'dense-analysis/ale'
Plug 'Valloric/YouCompleteMe'
Plug 'mattn/emmet-vim'
call plug#end()
set background=dark
set t_Co=256
set cmdheight=4
let g:ale_completion_enabled = 1
let g:ale_linters = {'rust': ['analyzer']}
let g:ale_sign_column_always = 1
let g:ale_fixers = { 'rust': ['rustfmt', 'trim_whitespace', 'remove_trailing_l ines'] }
let g:rustfmt_autosave = 1
:set omnifunc=phpcomplete#CompletePHP
:set omnifunc=csscomplete#CompleteCSS
:set omnifunc=htmlcomplete#CompleteTags
:set omnifunc=javascriptcomplete#CompleteJS
I use it for Rust, PHP and front end. autocompletion works well and smoothly for HTML, CSS and Javascript but not for PHP.
I'm on Debian 11 (Bullseye) and my vim version is 8.2.2434
thanks in advance :)

Why does Vim highlight all my JSON comments in red?

I've got some comments in a JSON file that were autogenerated by, and unfortunately it seems like vim can't recognize that they're just comments.
They're all red - which one of my plugins is doing this?
I don't really want to turn all of my syntax highlighting off, and I also don't want to clear the errors manually each time I run into the red highlighting.
" Enable syntax highlighting
syntax enable
" PLUGINS
call plug#begin('~/.vim/plugged')
" deoplete - code completion
if has('nvim')
" Add in a syntax file for deoplete typescripe, then add deoplete
Plug 'HerringtonDarkholme/yats.vim'
Plug 'mhartington/nvim-typescript', {'do': './install.sh'}
Plug 'Shougo/deoplete.nvim', { 'do': ':UpdateRemotePlugins' }
else
Plug 'Shougo/deoplete.nvim'
Plug 'roxma/nvim-yarp'
Plug 'roxma/vim-hug-neovim-rpc'
Plug 'ternjs/tern_for_vim', { 'do': 'npm install' }
endif
" fzf - fuzzy find
Plug 'junegunn/fzf', { 'dir': '~/.vim/installed/fzf' }
" lightline - a nice looking bottom bar
Plug 'itchyny/lightline.vim'
" also get rid of the useless -- INSERT -- since we have a nice bar
set noshowmode
" nerdtree - a little tree file browser
Plug 'scrooloose/nerdtree', { 'on': 'NERDTreeToggle' }
" map it to control-O
map <C-o> :NERDTreeToggle<CR>
" gitgutter - adds some git context to the left side bar
Plug 'airblade/vim-gitgutter'
set updatetime=100
" ale - asynchronous linting engine, highlights stuff
Plug 'w0rp/ale'
" deoplete-ternjs - adds javascript to deoplete
Plug 'carlitux/deoplete-ternjs'
" tern_for_vim - adds in the tern 'engine' or whatever to vim
Plug 'ternjs/tern_for_vim', { 'do': 'npm install && npm install -g tern' }
" vimproc - async execution for things
Plug 'Shougo/vimproc.vim', { 'do': 'make' }
" tsuquyomi - unpronouncable client for TSServer for completion and more
Plug 'Quramy/tsuquyomi', { 'do': 'npm install -g typescript' }
call plug#end()
" CONFIGURE - some of our plugins need configurations so add that in
let g:deoplete#enable_at_startup = 1
let g:deoplete#enable_ignore_case = 1
let g:deoplete#enable_smart_case = 1
let g:deoplete#enable_camel_case = 1
let g:deoplete#enable_refresh_always = 1
let g:deoplete#max_abbr_width = 0
let g:deoplete#max_menu_width = 0
let g:deoplete#omni#input_patterns = get(g:,'deoplete#omni#input_patterns',{})
let g:tern_request_timeout = 1
let g:tern_request_timeout = 6000
let g:tern#command = ["tern"]
let g:tern#arguments = ["--persistent"]
let g:deoplete#sources#tss#javascript_support = 1
let g:tsuquyomi_javascript_support = 1
let g:tsuquyomi_auto_open = 1
let g:tsuquyomi_disable_quickfix = 1
As #Michail mentioned, JSON syntax does not support comments, so Vim marks them as error.
There is a plugin for commented json that I found to solve this issue: jsonc. You should check it out.
This fixed it for me:
autocmd FileType json syntax match Comment +\/\/.\+$+
Not sure where i got it from.
EDIT:
NOTE that for this to work you must let vim handle filetype detection by, filetype on. put that somewhere above the autocmd ...
While looking for some other weird things to do with (Neo)Vim's JSON highlighting, I found that you can disable such warnings with let g:vim_json_warnings=0. This is not really a "solution" as such (the proper solution would be adding comments to JSON syntax, even if it was an optional feature), but it certainly removes the giant ugly red boxes everywhere.
As mentioned in comments and the accepted answer, JSON doesn't have comments, but as it's such a common extension it is nice to be able to disable the warnings at the very least.
To turn the JSON comment error highlighting off, add the following file in the user configuration folder.
after/syntax/json.vim
syntax clear jsonCommentError
syntax match jsonComment "//.*"
syntax match jsonComment "\(/\*\)\|\(\*/\)"
hi def link jsonComment Comment
To extend rules for NERDCommenter, add the following to vimrc.
let NERDCustomDelimiters = {'json': { 'left': '//', 'right': '' }}
packadd nerdcommenter

UltiSnips and YouCompleteMe

I have bundles ultisnips and youcompleteme installed on my macvim.
The problem is that ultisnips doesn't work because tab is bound by ycm.
I tried putting let g:UltiSnipsExpandTrigger = "<s-tab>" so that I can trigger the snippet completion with shift-tab, but it doesn't work for some unknown reason. I could use caps as the trigger, but so far I've found no way to do that.
Do any of you use those two add-ons together?
What can I do to make shift-tab work?
Can you recommend another key to trigger snippets?
Another option is using the SuperTab plugin:
" if you use Vundle, load plugins:
Bundle 'ervandew/supertab'
Bundle 'Valloric/YouCompleteMe'
Bundle 'SirVer/ultisnips'
" make YCM compatible with UltiSnips (using supertab)
let g:ycm_key_list_select_completion = ['<C-n>', '<Down>']
let g:ycm_key_list_previous_completion = ['<C-p>', '<Up>']
let g:SuperTabDefaultCompletionType = '<C-n>'
" better key bindings for UltiSnipsExpandTrigger
let g:UltiSnipsExpandTrigger = "<tab>"
let g:UltiSnipsJumpForwardTrigger = "<tab>"
let g:UltiSnipsJumpBackwardTrigger = "<s-tab>"
Here YouCompleteMe is bound to a different combination Ctrln, but then that combination is bound to tab through SuperTab. UltiSnips and SuperTab play nice together, so you can then just bind UltiSnips to tab directly and everything will work out.
Try this suggestion on a page from the YouCompleteMe issue tracker. In your .vimrc:
let g:UltiSnipsExpandTrigger="<c-j>"
While this setting will make expanding a snippet share the default mapping for jumping forward within a snippet, it simulates TextMates' behavior as mentioned in the UltiSnips help tags.
Since I've mapped my Caps Lock key to Ctrl, this mapping works pretty smoothly.
copy the following code to your vimrc, and enjoy. This function will handle all issues between YCM and UltiSnips.
function! g:UltiSnips_Complete()
call UltiSnips#ExpandSnippet()
if g:ulti_expand_res == 0
if pumvisible()
return "\<C-n>"
else
call UltiSnips#JumpForwards()
if g:ulti_jump_forwards_res == 0
return "\<TAB>"
endif
endif
endif
return ""
endfunction
au BufEnter * exec "inoremap <silent> " . g:UltiSnipsExpandTrigger . " <C-R>=g:UltiSnips_Complete()<cr>"
let g:UltiSnipsJumpForwardTrigger="<tab>"
let g:UltiSnipsListSnippets="<c-e>"
" this mapping Enter key to <C-y> to chose the current highlight item
" and close the selection list, same as other IDEs.
" CONFLICT with some plugins like tpope/Endwise
inoremap <expr> <CR> pumvisible() ? "\<C-y>" : "\<C-g>u\<CR>"
i have this in my vimrc
"" YouCompleteMe
let g:ycm_key_list_previous_completion=['<Up>']
"" Ultisnips
let g:UltiSnipsExpandTrigger="<c-tab>"
let g:UltiSnipsListSnippets="<c-s-tab>"
thats what i did on my first try, but i misspelled UltiSnips with Ultisnips.. oh well, worked out in the end!
I personally chose to not use <tab> with YouCompleteMe but navigate it manually.
So I added this to my .vimrc:
let g:ycm_key_list_select_completion=[]
let g:ycm_key_list_previous_completion=[]
which simply disables the tab key for YCM. Instead you use the movement keys (arrows or CTRL-N/CTRL-P) and select the entry with CR. UltiSnips works default with tab.
Just putting together answers by Michaelslec, Joey Liu and along with solutions I found in this issue thread and this guy's vimrc, I now have this which solved pretty much all problems.
function! g:UltiSnips_Complete()
call UltiSnips#ExpandSnippet()
if g:ulti_expand_res == 0
if pumvisible()
return "\<C-n>"
else
call UltiSnips#JumpForwards()
if g:ulti_jump_forwards_res == 0
return "\<TAB>"
endif
endif
endif
return ""
endfunction
function! g:UltiSnips_Reverse()
call UltiSnips#JumpBackwards()
if g:ulti_jump_backwards_res == 0
return "\<C-P>"
endif
return ""
endfunction
if !exists("g:UltiSnipsJumpForwardTrigger")
let g:UltiSnipsJumpForwardTrigger = "<tab>"
endif
if !exists("g:UltiSnipsJumpBackwardTrigger")
let g:UltiSnipsJumpBackwardTrigger="<s-tab>"
endif
au InsertEnter * exec "inoremap <silent> " . g:UltiSnipsExpandTrigger . " <C-R>=g:UltiSnips_Complete()<cr>"
au InsertEnter * exec "inoremap <silent> " . g:UltiSnipsJumpBackwardTrigger . " <C-R>=g:UltiSnips_Reverse()<cr>"
Based on Siegfried's answer, I am using the following which seems more natural:
let g:ycm_key_list_select_completion = ['<C-j>']
let g:ycm_key_list_previous_completion = ['<C-k>']
let g:UltiSnipsExpandTrigger = "<C-l>"
let g:UltiSnipsJumpForwardTrigger = "<C-j>"
let g:UltiSnipsJumpBackwardTrigger = "<C-k>"
I also use the c-hjkl bindings somewhere else (switching from a pane to another), but that would only be in normal mode, so there's no problem.
Although I know this post is a little old, I have my own function that is a little more optimized than the one given above:
function! g:UltiSnips_Complete()
call UltiSnips#ExpandSnippetOrJump()
if g:ulti_expand_or_jump_res == 0
if pumvisible()
return "\<C-N>"
else
return "\<TAB>"
endif
endif
return ""
endfunction
Of course, if you just keep the settings that Joey Liu provided and then just use this function everything will work just perfectly!
EDIT: Also, I use another function to increase back-stepping functionality between YouCompleteMe and UltiSnips. I'll show you what I mean:
function! g:UltiSnips_Reverse()
call UltiSnips#JumpBackwards()
if g:ulti_jump_backwards_res == 0
return "\<C-P>"
endif
return ""
endfunction
Then just put this in your .vimrc:
au BufEnter * exec "inoremap <silent> " . g:UltiSnipsJumpBackwardTrigger . " <C-R>=g:UltiSnips_Reverse()<cr>"
As well as let g:UltiSnipsJumpBackwardTrigger="<s-tab>" and your set!
I use both of them together. By default YouCompleteMe binds <Tab> and <Down> to select the next completion item and also <S-Tab> and <Up> to select the previous completion item. You can change the YouCompleteMe bindings with the g:ycm_key_list_select_completion and g:ycm_key_list_previous_completion options. Note that the names of these options were recently changed when the option was changed from a single string to a list of strings.
While Many answer works fine in this post, I just want to say that the problem is caused by key binding collision between YCM and UltiSnip, while YCM support UltiSnip snippets by default, it takes the default UltiSnip expand trigger <tab> as its completion select key, so UltiSnip snippets will not be expaned by <tab>. Give them different key binding will solve the problem, I personally use <c-n and <c-p> for YCM and use the default <tab> for UltiSnip. You can get more details with help youcompleteme doc in vim.
I installed the UltiSnips plugin after the YouCompleteMe plugin so I thought they were conflicting, but in reality I had something more interfering:
set paste
Make sure to remove that from .vimrc if it's present.
I use ; to expand UltiSnips, it's so nifty for me
let g:UltiSnipsExpandTrigger = ";"
I use kj. This is what is in my .vimrc:
let g:UltisnipsExpandTrigger="kj".
It rarely happens that I run into word that has kj in it. If this is the case I would just wait a couple of seconds after typing k and that type j.
As mentioned by others, mapping C-j to ultisnips works great.
let g:UltiSnipsExpandTrigger="<c-j>"
Now, if you go a bit further and install xcape and use
xcape -e "Shift_L=Control_R|J"
You unleash the power of using just the shift key for utlitsnips.

Get Vimwiki working with SnipMate (the vim plugins)

My issue is that <Tab> completion for SnipMate does not work when I'm in a vimwiki file. I am testing by typing APACHE<Tab> in insert mode, but I don't get the snippet as I do when I'm in, say, .vimrc.
And even though i_<Tab> doesn't work in a vimwikie file, i_<C-R><Tab> does. I get a list of available snippets. Strange.
To make it stranger (well, to me at least), here's the partial output of :imap in a vimwiki file:
i <Tab> * <C-G>u<C-R>=snipMate#TriggerSnippet()<CR>
i <C-R><Tab> * <C-R>=snipMate#ShowAvailableSnips()<CR>
I think these are correct, and in other files where <Tab> completion does work, the mappings are the same.
oh, and in case you are thinking to suggest putting let g:vimwiki_table_auto_fmt = 0 in my .vimrc as suggested in http://code.google.com/p/vimwiki/wiki/ChangeLog, I tried it and it doesn't solve my problem. That's the only suggestion I found in my search, so that's why I'm here.
I don't know how much of my .vimrc you would want, so I'm just going to give you the ones I think are relevant to keep this question short:
" Vundle: The plugin manager for vim.
set runtimepath+=~/.vim/bundle/vundle/
call vundle#rc()
Bundle 'gmarik/vundle'
" SnipMate: TextMate snippets for vim.
Bundle "MarcWeber/vim-addon-mw-utils"
Bundle "tomtom/tlib_vim"
Bundle "honza/snipmate-snippets"
Bundle "garbas/vim-snipmate"
" Vimwiki: A personal wiki for vim.
Bundle 'vim-scripts/vimwiki'
let g:vimwiki_hl_headers = 1
let g:vimwiki_hl_cb_checked = 1
let g:vimwiki_folding = 1
let g:vimwiki_fold_lists = 1
let s:vimwiki = {}
let s:vimwiki.path = '~/Vimwiki/wiki'
let s:vimwiki.path_html = '~/Vimwiki/html'
let s:vimwiki.ext = '.md'
let s:vimwiki.syntax = 'markdown'
let s:vimwiki.maxhi = 1
let s:vimwiki.diary_rel_path = 'Journal/'
let s:vimwiki.diary_index = 'index'
let s:vimwiki.diary_header = 'Journal'
let s:vimwiki.diary_sort = 'asc'
let g:vimwiki_list = [s:vimwiki]
Thanks
Edit:
I don't know why I forgot about this while writing the above. The output of :imap above is incomplete. It also shows:
i <Tab> *#vimwiki#tbl#kbd_tab()
Regardless of the value of g:vimwiki_table_auto_fmt. It's probably the source of my problem.. and if so I'd like to get rid of it from .vimrc somehow.
The # in the :imap output shows that Vimwiki defines a buffer-local <Tab> mapping that overrides snipMate's global one. A
:iunmap <buffer> <Tab>
should fix that. You can put that command into ~/.vim/after/ftplugin/vimwiki.vim to make it permanent. But apparently Vimwiki allows customization:
" Table mappings
if g:vimwiki_table_mappings
inoremap <expr> <buffer> <Tab> vimwiki#tbl#kbd_tab()
inoremap <expr> <buffer> <S-Tab> vimwiki#tbl#kbd_shift_tab()
endif
So, :let g:vimwiki_table_mappings = 0 in your .vimrc should work, too.
Used Ingo Karkat's solution for the longest time but Shift-Tab in insert mode is broken again.
" New fix.
" SOURCE: https://github.com/vimwiki/vimwiki/issues/1268#issuecomment-1312192484
" SOURCE[*g:vimwiki_key_mappings*]: https://github.com/vimwiki/vimwiki/blob/0629b39815c97f1e4ee31e26faa6891b0e13d2d5/doc/vimwiki.txt#L3671
"
" Disable table mappings:
let g:vimwiki_key_mappings =
\ {
\ 'table_mappings': 0,
\ 'table_format': 0,
\ }

Vim script: Buffer/CheatSheet Toggle

I want to make a vim cheat sheet plugin. It's real simple:
I want to toggle my cheatsheets. A vertsplit toggle, like Taglist or NERDTree.
I want the cheatsheet to be filetype specific. So I toggle my c++ cheatsheet when I have opened a .cpp file.
I want the cheatsheet to be horizontally split. So it shows two files, my syntax cheat sheet and my snippet trigger cheat sheet.
I already have a collection of these cheatsheets, in vimhelp format, but now I have to manually open them.
I haven't really done any vim scripting, but I imagine this would be really simple to put together. I'm sorta sick of googling unrelated codesnippets, so what I'm asking here is:
Could anyone give me a short sum-up of what I need to learn in regards to vim scripting to piece this together. What I have a hard time finding is how to toggle the buffer window.
If you know any intro tutorials that covers the material I need to get this up and running, please provide a link.
tx,
aktivb
The function below may not do exactly what you want, and I haven't tested it, but it should give you some ideas.
The main idea is that the function reads the filetype of the current buffer (you can test this by typing :echo &ft) and then sets the path of the appropriate cheat sheat. If it exists, this path is then opened (read-only and non-modifiable) in a split window. You can then call this function any way you wish, for example by mapping it to the {F5} key as shown.
I'm not sure about the toggling possibilities (is this really easier than just closing the split window?) but you could look at the bufloaded() function, which returns whether or not a given file is currently being accessed.
function! Load_Cheat_Sheet()
let l:ft = &ft
if l:ft == 'html'
let l:path = 'path/to/html/cheat/sheet'
elseif l:ft == 'c'
let l:path = 'path/to/c/cheat/sheet'
elseif l:ft == 'tex'
let l:path = 'path/to/tex/cheat/sheet'
endif
if l:path != '' && filereadable(l:path)
execute ':split +setlocal\ noma\ ro ' l:path
endif
endfunction
map <F5> :call Load_Cheat_Sheet()<CR>
Hope this helps. Just shout if anything is unclear, or you want to know more.
I had forgotten about this until I got a notice about Eduan's answer. Since I posted this question I've done quite a bit of vim scripting, including getting this to work:
let g:cheatsheet_dir = "~/.vim/bundle/cheatsheet/doc/"
let g:cheatsheet_ext = ".cs.txt"
command! -nargs=? -complete=customlist,CheatSheetComplete CS call ToggleCheatSheet(<f-args>)
nmap <F5> :CS<CR>
" strip extension from complete list
function! CheatSheetComplete(A,L,P)
return map(split(globpath(g:cheatsheet_dir, a:A.'*'.g:cheatsheet_ext)),
\ "v:val[".strlen(expand(g:cheatsheet_dir)).
\ ":-".(strlen(g:cheatsheet_ext) + 1)."]")
endfun
" specify cheatsheet or use filetype of open buffer as default
" instead of saving window status in a boolean variable,
" test if the file is open (by name). If a boolean is used,
" you'll run into trouble if you close the window manually with :wq etc
function! ToggleCheatSheet(...)
if a:0
let s:file = g:cheatsheet_dir.a:1.g:cheatsheet_ext
else
if !exists("s:file") || bufwinnr(s:file) == -1
let s:file = g:cheatsheet_dir.&ft.g:cheatsheet_ext
endif
endif
if bufwinnr(s:file) != -1
call ToggleWindowClose(s:file)
else
call ToggleWindowOpen(s:file)
endif
endfun
" stateless open and close so it can be used with other plugins
function! ToggleWindowOpen(file)
let splitr = &splitright
set splitright
exe ":vsp ".a:file
exe ":vertical resize 84"
if !splitr
set splitright
endif
endfun
function! ToggleWindowClose(file)
let w_orig = bufwinnr('%')
let w = bufwinnr(a:file)
exe w.'wincmd w'
exe ':silent wq!'
if w != w_orig
exe w_orig.'wincmd w'
endif
endfun
Thought I would add to Goulash's answer.
I think in order to implement the toggle you would simply use some if statements and a global variable.
let g:cheatsheet_toggle_on=0
if (g:cheatsheet_toggle_on == 0)
" Turn the cheatsheet on
" Also make sure to know that the toggle is on:
let g:cheatsheet_toggle_on=1
elseif (g:cheatsheet_toggle_on=1
" Do whatever you need to turn it off, here
endif
Hope this figures out that logic. :)

Resources