Setting servername in vimrc as opposed to command line switch - vim

Is it possible to set vim's servername from my vimrc instead of using the --servername command line switch? If I try one of
set v:servername="TEX"
let v:servername="TEX"
I get unknown option error and cannot overwrite read-only variable error respectively.

According to documentation (:help v:servername) the v:servername variable is read only.
And according to source code serverRegisterName() in if_xcmdsrv.c is called from three places:
main() function
X11 main window initialization
GTK+ main window initialization
So the answer to your question is no, you can't set server name in your .vimrc or anywhere else except command line arguments.

For a sufficiently new of vim there's the function remote_startserver.
*remote_startserver()* *E941* *E942*
remote_startserver({name})
Become the server {name}. This fails if already running as a
server, when |v:servername| is not empty.
Can also be used as a |method|: >
ServerName()->remote_startserver()
Available since Vim version 8.0.475. according to VimTeX documentation
So you can simply start vim with no servername and start one in vimrc.
Note: Vim will automatically change the servername (append 1, 2, etc.) to avoid conflict if there are multiple running Vim instances.

Related

Make vim understand tcl script environment variables ('gf' command)

I often use gf in vim to open files under cursor. Often these file paths use environment variables but when in .tcl script files vim is unable to use the environment variable.
This works for gf:
$tcl_lib/myfile.tcl
These do NOT work for gf:
$env(tcl_lib)/myfile.tcl
$::env(tcl_lib)/myfile.tcl
These are some of the things I have tried:
:set isfname=#,48-57,/,.,-,_,+,,,#,$,%,~,=,{,},(,)
:set isfname=#,48-57,/,.,-,_,+,,,#,$,%,~,=,{,},40-41
:set includeexpr=substitute(v:fname,'\$env(\([^)]\+\))','\$\1','')
Is there a way to make vim understand the syntax for environment variables in tcl scripts (specifically for the 'gf' command)?
There are a few techniques:
Set 'path' & 'includeexpr'
In theory you can just add $tcl_lib to path. e.g. set path=.,$tcl_lib,,. However, any filename starting with / will fail. This can be remedied by removing the starting /.
Add to ~/.vim/after/ftplugin/tcl.vim:
set path=.,$tcl_lib,,
let &l:includeexpr="substitute(v:fname, '^/', '', 'g')"
Reading Environmental variables via 'includeexpr'
Can use a substitution to expand environment variables
let l:includeexpr = "substitute(v:fname, '$\\%(::\\)\\=env(\\([^)]*\\))', '\\=expand(\"$\".submatch(1))', 'g')"
This uses a sub-replace-expression (See :h sub-replace-expression) to use expand() to get the environmental variable.
This might require you to change 'isfname' to allow more characters tto be a part of a filename looking string.
Just map gf and friends
Make buffer-local mappings for gf, <c-w>f, etc which are specific to your language and check certain paths. This completely side-steps many of Vim's built in methods so it should be used as a last resort.
Finally got back to this and was able to solve it in a pretty good way. Add the following tcl.vim file to your ~/.vim/ftplugin and your "gf" should work!
https://github.com/stephenmm/dotfiles/blob/master/vim/ftplugin/tcl.vim
" Add charecters to possible filename types so vim will recognize:
" $::env(THIS)/as/a/file.tcl
set isfname+={,},(,),:
" Turn the string into something vim knows as a filename:
" $::env(THIS)/as/a/file.tcl => ${THIS}/as/a/file.tcl
function! TclGfIncludeExpr(fname)
if a:fname =~? '\$\(::\)\?env([^)]\+)'
return substitute(a:fname, '\$\(::\)\?env(\([^)]\+\))', '${\2}', 'g')
endif
return a:fname
endfunction
" Tie the function to includeexpr
set includeexpr=TclGfIncludeExpr(v:fname)
Adding below 2 lines in ~/.vimrc will work for me.
set isfname+={,},(,),:
let &l:includeexpr = "substitute(v:fname,'$\\%(::\\)\\=env(\\([^)]*\\))','\\=expand(\"$\".submatch(1))', 'g')"

vimrc how to invoke unix find?

i want to set the tags variable to the set of all gotags files i generated in specific folder(s) using exuberant Ctags. (gotags is nothing but the tags file renamed).
i put following lines in my .vimrc file.
set tags+=/usr/local/go/src/gotags
set tags+=`find /home/vimal/gowork/src -name gotags`
but it doesnt work and i get the following error
$ vi ~/.vimrc
Error detected while processing /home/vimal/.vimrc:
line 157:
E518: Unknown option: /home/vimal/gowork/src
Press ENTER or type command to continue
how can i fix the error and set the tags variable with the value: list of all the gotags files under one directory tree.
Inventing new syntax tends not to work that well in practice. Use system() to run external commands from Vim, not backticks. Also set in Vim is weird, it doesn't evaluate RHS the way you expect. Most of the time it's a lot simpler to use let &option = ... instead of set option=....
Anyway, to answer your question, you don't need to run find(1) for that, plain Vim functions are enough for what you want:
let &tags = join(extend([&tags, '/usr/local/go/src/gotags'],
\ findfile('gotags', '/home/vimal/gowork/src', -1)), ',')

the dollar sign `$` cannot be removed from iskeyword [duplicate]

In my vimrc, I have included a script (say, otherscript.vim, which I need to include for work reasons) that says:
autocmd FileType php setlocal iskeyword+=$
and I don't want this behaviour. So, sometime later in the vimrc, I say:
autocmd FileType php setlocal iskeyword-=$
(I also tried using set instead of setlocal.) But, when I open a php file, iskeyword still contains the $ symbol in it. I am using vim 7.2. The output of ':verbose set iskeyword' is
iskeyword=#,48-57,_,192-255,$
Last set from /path/to/otherscript.vim
The output of ':scriptnames' is:
...
7: /usr/share/vim/vim72/ftplugin.vim
8: /home/yogeshwer/.vimrc
...
74: /path/to/otherscript.vim
...
Can somebody help me how I can revert the changes to 'iskeyword' made by the other script? Thanks a bunch.
I like to avoid autocmds when I can and use the after directory structure.
$ mkdir -p ~/.vim/after/{ftplugin,syntax,indent}
$ echo 'setlocal iskeyword-=$' >> ~/.vim/after/ftplugin/php.vim
This sets up a basic after directory in your user-specific vim config folder. Whereas ~/.vim/ftplugin/$FILETYPE.vim would be used in lieu of vim's standard $FILETYPE.vim file, files in an after directory get executed after, allowing you to override or change the behavior of your ftplugins, syntax definitions, and indent commands.
As an additional example to show you how these work, I'll include part of my local after/syntax/python.vim file here. I like all the "structural punctuation" of my code to stand out when I read it, so I do this:
syn match pythonParen /[()]/
syn match pythonBrack /[][]/
syn match pythonCurly /[{}]/
hi def link pythonParen Paren
hi def link pythonBrack Brack
hi def link pythonCurly Curly
I've also got an after/indent/php.vim file that was supposed to fix some of the annoying indent issues I ran into with the indent behavior when switching in and out of <?php ?> regions in a template file, but the code is a mess and never really worked in the first place, so I won't reproduce it here. I mention it only to give you an example of what can be done with the after hooks.

Removing a character from 'iskeyword' in vim

In my vimrc, I have included a script (say, otherscript.vim, which I need to include for work reasons) that says:
autocmd FileType php setlocal iskeyword+=$
and I don't want this behaviour. So, sometime later in the vimrc, I say:
autocmd FileType php setlocal iskeyword-=$
(I also tried using set instead of setlocal.) But, when I open a php file, iskeyword still contains the $ symbol in it. I am using vim 7.2. The output of ':verbose set iskeyword' is
iskeyword=#,48-57,_,192-255,$
Last set from /path/to/otherscript.vim
The output of ':scriptnames' is:
...
7: /usr/share/vim/vim72/ftplugin.vim
8: /home/yogeshwer/.vimrc
...
74: /path/to/otherscript.vim
...
Can somebody help me how I can revert the changes to 'iskeyword' made by the other script? Thanks a bunch.
I like to avoid autocmds when I can and use the after directory structure.
$ mkdir -p ~/.vim/after/{ftplugin,syntax,indent}
$ echo 'setlocal iskeyword-=$' >> ~/.vim/after/ftplugin/php.vim
This sets up a basic after directory in your user-specific vim config folder. Whereas ~/.vim/ftplugin/$FILETYPE.vim would be used in lieu of vim's standard $FILETYPE.vim file, files in an after directory get executed after, allowing you to override or change the behavior of your ftplugins, syntax definitions, and indent commands.
As an additional example to show you how these work, I'll include part of my local after/syntax/python.vim file here. I like all the "structural punctuation" of my code to stand out when I read it, so I do this:
syn match pythonParen /[()]/
syn match pythonBrack /[][]/
syn match pythonCurly /[{}]/
hi def link pythonParen Paren
hi def link pythonBrack Brack
hi def link pythonCurly Curly
I've also got an after/indent/php.vim file that was supposed to fix some of the annoying indent issues I ran into with the indent behavior when switching in and out of <?php ?> regions in a template file, but the code is a mess and never really worked in the first place, so I won't reproduce it here. I mention it only to give you an example of what can be done with the after hooks.

Vim with Powershell

I'm using gvim on Windows.
In my _vimrc I've added:
set shell=powershell.exe
set shellcmdflag=-c
set shellpipe=>
set shellredir=>
function! Test()
echo system("dir -name")
endfunction
command! -nargs=0 Test :call Test()
If I execute this function (:Test) I see nonsense characters (non number/letter ASCII characters).
If I use cmd as the shell, it works (without the -name), so the problem seems to be with getting output from powershell into vim.
Interestingly, this works great:
:!dir -name
As does this:
:r !dir -name
UPDATE: confirming behavior mentioned by David
If you execute the set commands mentioned above in the _vimrc, :Test outputs nonsense. However, if you execute them directly in vim instead of in the _vimrc, :Test works as expected.
Also, I've tried using iconv in case it was an encoding problem:
:echo iconv( system("dir -name"), "unicode", &enc )
But this didn't make any difference. I could be using the wrong encoding types though.
Anyone know how to make this work?
It is a bit of a hack, but the following works in Vim 7.2. Notice, I am running Powershell within a CMD session.
if has("win32")
set shell=cmd.exe
set shellcmdflag=/c\ powershell.exe\ -NoLogo\ -NoProfile\ -NonInteractive\ -ExecutionPolicy\ RemoteSigned
set shellpipe=|
set shellredir=>
endif
function! Test()
echo system("dir -name")
endfunction
Tested with the following...
:!dir -name
:call Test()
I ran into a similar problem described by many here.
Specifically, calling
:set shell=powershell
manually from within vim would cause powershell to work fine, but as soon as I added:
set shell=powershell
to my vimrc file I would get the error "Unable to open temp file .... "
The problem is that by default when shell is modified, vim automatically sets shellxquote to " which means that shell commands will look like the following:
powershell -c "cmd > tmpfile"
Where as this command needs to look like this, in order for vim to read the temp file:
powershell -c "cmd" > tmpfile
Setting shellquote to " in my vimrc file and unsetting shellxquote (i.e. setting it to a blank space) seem to fix all my problems:
set shell=powershell
set shellcmdflag=-c
set shellquote=\"
set shellxquote=
I've also tried taking this further and scripting vim a bit using the system() call:
system() with powershell in vim
I suspect that the problem is that Powershell uses the native String encoding for .NET, which is UTF-16 plus a byte-order-mark.
When it's piping objects between commands it's not a problem. It's a total PITA for external programs though.
You can pipe the output through out-file, which does support changing the encoding, but still formats the output for the terminal that it's in by default (arrgh!), so things like "Get-Process" will truncate with ellipses, etc. You can specify the width of the virtual terminal that Out-File uses though.
Not sure how useful this information is, but it does illuminate the problem a bit more.
Try replacing
"dir \*vim\*"
with
" -command { dir \*vim\* }"
EDIT: Try using cmd.exe as the shell and put "powershell.exe" before "-command"
Interesting question - here is something else to add to the confusion. Without making any changes to my .vimrc file, if I then run the following commands in gvim:
:set shell=powershell.exe
:set shellcmdflag=-noprofile
:echo system("dir -name")
It behaves as expected!
If I make the same changes to my .vimrc file, though (the shell and shellcmdflag options), running :echo system("dir -name") returns the nonsense characters!
The initial example code works fine for me when I plop it in vimrc.
So now I'm trying to figure out what in my vimrc is making it function. Possibly:
set encoding=utf8
Edit: Yep, that appears to do it. You probably want to have VIM defaulting to unicode anyway, these days...
None of the answers on this page were working for me until I found this hint from https://github.com/dougireton/mirror_pond/blob/master/vimrc - set shellxquote= [space character] was the missing piece.
if has("win32") || has("gui_win32")
if executable("PowerShell")
" Set PowerShell as the shell for running external ! commands
" http://stackoverflow.com/questions/7605917/system-with-powershell-in-vim
set shell=PowerShell
set shellcmdflag=-ExecutionPolicy\ RemoteSigned\ -Command
set shellquote=\"
" shellxquote must be a literal space character.
set shellxquote=
endif
endif
Combining the answers in this and the related thread, add the following to your $profile assuming you installed diffutils from chocolatey:
Remove-Item Alias:diff -force
And add the following to your ~/.vimrc:
if (has('win32') || has('gui_win32')) && executable('pwsh')
set shell=pwsh
set shellcmdflag=\ -ExecutionPolicy\ RemoteSigned\ -NoProfile\ -Nologo\ -NonInteractive\ -Command
endif
make sure shellcmdflag is exactly as shown
All credit for these solutions to their respective contributors, this is merely an aggregation post.
I propose an hackish solution. It doesn't really solve the problem, but it get the job done somehow.
This Vim plugin automate the creation of a temporary script file, powershell call through cmd.exe and paste of the result. It's not as nice as a proper powershell handling by vim, but it works.
Try instead
set shellcmdflag=\ -c
Explanation:
Vim uses tempname() to generate a temp file path that system() reads.
If &shell contains 'sh' and &shellcmdflag starts with '-'
then tempname() generates a temp file path with forward slashes.
Thus, if
set shell=powershell
set shellcmdflag=-c
then Vim will try to read a temp file with forward slashes that
cannot be found.
A remedy is to set instead
set shellcmdflag=\ -c
that is, add a whitespace to &shellcmdflag so that the first character
is no longer '-' and tempname() produces a temp file path with backward
slashes that can be found by system().
I remarked on the vim_dev mailing list ( https://groups.google.com/forum/#!topic/vim_dev/vTR05EZyfE0 ) that this deserves better documentation.
actf answer works for me, but because of Powershell built in DIFF (which is different from the Linux one) you must add this line to your Powershell profile to have diff working again in VIM:
Remove-Item Alias:diff -force
I'm running GVim v8.2 (Windows).
Using the fullpath to the executable works for me:
set shell=C:\\Windows\\System32\\WindowsPowerShell\\v1.0\\powershell.exe
I don't use VIM but Powershell's default output is Unicode. Notepad can read unicode, you could use it to see if you are getting the output you expect.

Resources