Check if using Windows console in Vim while in Windows Subsystem for Linux? - vim

I am using Vim inside the Windows Subsystem for Linux. The windows command prompt has a bug which renders the background color incorrectly.
The fix is set t_ut=. Rather than applying this fix in all situations, I assume it would make sense to only apply it when Vim is being used inside the Windows console.
Unfortunately, I am not sure how to detect whether the Windows console is being used, because I am inside the Windows Subsystem for Linux.

I used the following code that implemented Roadowl's comment.
let uname = substitute(system('uname'),'\n','','')
if uname == 'Linux'
if system('$PATH')=~ '/mnt/c/WINDOWS'
" We are in Windows Subsystem
endif
endif
Update: I combined roadowl's and bk2204's answer:
let uname = substitute(system('uname'),'\n','','')
if uname == 'Linux'
let lines = readfile("/proc/version")
if lines[0] =~ "Microsoft"
return 1
endif
endif

Typically, one addresses issues like this by detecting the terminal type, but it seems Microsoft Terminal reports xterm-256color when it really doesn't support this.
It's possible to detect whether one is running WSL with a function like the following:
function! IsWSL()
if has("unix")
let lines = readfile("/proc/version")
if lines[0] =~ "Microsoft"
return 1
endif
endif
return 0
endfunction
This is consistent with the way that Microsoft suggests that WSL be detected.

Related

How to detect REAL Operating System in VimScript?

I need to decide which binary executable file I need to choose, so I have to know the OS which Vim is running on.
I find there is related question here. But the has('win32') || has('win64') solution doesn't work for me, since when I'm using msys2 Vim on Windows, I will get 0 from the has solution, because the has solution only tells the OS which vim is compiled for, not the real OS which it is running on.
And when I need to decide which binary executable file I need to choose, I have to know the real OS. Is there any good idea about this problem?
From this Gist:
Define a global variable containing the current environment's name if it hasn't been already defined.
if !exists('g:env')
if has('win64') || has('win32') || has('win16')
let g:env = 'WINDOWS'
else
let g:env = toupper(substitute(system('uname'), '\n', '', ''))
endif
endif
Use that global variable…
if g:env =~ 'DARWIN'
" ... to do Mac OS X-specific stuff.
endif
if g:env =~ 'LINUX'
" ... to do Linux-specific stuff.
endif
if g:env =~ 'WINDOWS'
" ... to do Windows-specific stuff.
endif
if g:env =~ 'CYGWIN'
" ... to do Cygwin-specific stuff.
endif
if g:env =~ 'MINGW'
" ... to do MinGW-specific stuff (Git Bash, mainly).
endif
And so on.

VIM source file on OS condition using interpolation in .vimrc?

I'd like to source files based on my OS platform in my .vimrc configuration file. I'd like to do something like this:
source .vimrc/{uname -S}.vim
I'm doing this because I'd like to source files based on operating system. I know my syntax is wrong, but I think you get the idea. How would I do this? Thank you.
I think OP wants to source the vim file in vim (e.g. vimrc) not in shell. so you could try to add this line in your vimrc:
execute 'source path/to/'. substitute(system('uname -s'), "\n", "", "") . '.vim'
This what I have in my vimrc:
let os=substitute(system('uname'), '\n', '', '')
if os == 'Darwin'
" settings for Mac OS X
elseif os == 'Linux'
" settings for Linux
endif
-- EDIT --
For what it's worth, I've written that snippet a "long" time ago and I can't remember why I added Mac. I initially thought that, maybe, I had found out that uname reported Mac in some context for some reason, but no, it appears to be Darwin everywhere. So I've removed Mac for that snippet to make more sense and will do the same to my vimrc.

VIM GTK-UI font

The vim manual states:
On systems where 'guifontset' is supported (X11) and 'guifontset' is
not empty, then 'guifont' is not used.
Spaces after a comma are ignored. To include a comma in a font name
precede it with a backslash. Setting an option requires an extra
backslash before a space and a backslash. See also
|option-backslash|. For example: >
:set guifont=Screen15,\ 7x13,font\\,with\\,commas
will make Vim try to use the font "Screen15" first, and if it fails it
will try to use "7x13" and then "font,with,commas" instead.
So, I would like to do the following:
if has("gui_running")
if has("gui_gtk2")
set guifont=Droid\ Sans\ Mono,Inconsolata,Monospace
elseif has("gui_win32")
set guifont=Droid\ Sans\ Mono:h10,Consolas:h11:cANSI
endif
endif
Trouble is that it does not work for me... I have been trying for a couple of hours on CentOS6.3 and Debian Wheey, but when ever I write this command like this, VIM will just start with Sans font.
Am I doing something wrong? How do you smartly detect which fonts are on the system ?
OK, I know this is probably not the right way, but it works. So, here is how I set a fallback font for VIM-GTK:
if has("gui_running")
if has("gui_gtk2")
let dsm=system('fc-list | grep -c Droid\ Sans\ Mono')
let cons=system('fc-list | grep -c Inconsola')
if ( dsm > 0)
set gfn=Droid\ Sans\ Mono\ 10
elseif ( cons > 0)
set gfn=Inconsolata\ 12
else
set gfn=Monospace\ 10
endif
elseif has("gui_win32")
set guifont=Droid\ Sans\ Mono:h10,Consolas:h11:cANSI
endif
endif
This snippet will check if Droid Sans Mono is installed, and also if Inconsolata is installed.
If the first one is install, the UI font will be Droid Sans Mono, if not it will be set to Inconsolata, and finally, it will be set to Monospace.
On Windows 7 the comma separated list just works.
I ran into the same issue. The problem here is that when Vim calls gui_init_font (code) it expects if gui_mch_get_font (code) fails it can move on to the next font in the comma-separated list. But in GTK gui_mch_get_font calls pango_font_description_from_string (code) which will never fail, it'll just return a default.
But pango_font_description_from_string itself takes a comma-separated list of families followed by style options, size and variations and has its own fallback logic (doc) withe the following format: [FAMILY-LIST] [STYLE-OPTIONS] [SIZE] [VARIATIONS]. Thus escape your list as follows:
if has("gui_running")
if has("gui_gtk2") || has("gui_gtk3")
set guifont=Droid\ Sans\ Mono\\,Inconsolata\\,Monospace 10
elseif has("gui_win32")
set guifont=Droid\ Sans\ Mono:h10,Consolas:h11:cANSI
endif
endif
Then Pango will do the fallback work and pick the right font for you. On GTK it seems to be best to fully escape your string and let GTK do the logic.
I either failed to get Oz123's answer properly abstracted into a function or else otherwise couldn't get this working on my system. I had additional issues due to actually using two users (a sandboxed web user and my main account); there was some problem executing fc-list).
My workaround was to reassign the alias for the Monospace font, which affects all of my apps (don't employ this technique if you only want this to work in gvim).
This change goes into ~/.config/fontconfig/fonts.conf:
<?xml version='1.0'?>
<!DOCTYPE fontconfig SYSTEM 'fonts.dtd'>
<fontconfig>
<alias>
<family>monospace</family>
<prefer><family>Panic Sans</family></prefer>
</alias>
</fontconfig>
I chose Panic Sans (unofficially hosted here), a variant of the highly popular free DejaVu Sans Mono font, because it is particularly good at rendering code (it additionally solves the underscore and dash problem in DejaVu). The font's files themselves live in my ~/.fonts/Panic_Sans directory.
Installing it in this manner allows me to share my ~/.vimrc between systems and not have to worry about whether Panic Sans is installed on them.
This means that my ~/.vimrc now merely contains:
if has("gui_running")
if has("gui_gtk2")
set guifont=Monospace\ 7
endif
" …
And this works because the fontconfig alias properly matches Monospace to Panic Sans:
$ fc-match Monospace
PanicSans.ttf: "Panic Sans" "Regular"

Vimscript: How can I get the Operating System version?

Even though it's similar to this and this question I need to know the current version of the operating system while vim is running. The previous questions don't help me since they describe a feature set of the executable; what I need is a function to return the os version either name or number (e.g. as listed in this widows version chart).
Is there one?
I don't know about Windows but on Mac OS X you can do:
$ sw_vers -productVersion
and on Ubuntu you can do:
$ lsb_release -rs
This quick hack seems to work, you'll have to adapt it to your needs:
function! GetSysVersion()
let os=substitute(system('uname'), '\n', '', '')
if os == 'Darwin' || os == 'Mac'
let sys_version=substitute(system('sw_vers -productVersion'), '\n', '', '')
elseif os == 'Linux'
let sys_version=substitute(system('lsb_release -rs'), '\n', '', '')
endif
echo sys_version
endfunction
(Just to make 30 characters)
echo exec('cat "/etc/issue"')
To invoke the Win32 function GetVersionEx(), you have to write a DLL that exposes the function, and invoke it from Vim via libcall(). For all the implementation details, see
:help libcall()
Alternatively, you could write an executable and use system() to parse its output.

Vimscript: how do I get the OS that is running Vim?

I've got vim plugin that runs on different machines and sometimes needs to do things differently depending on whether it's Windows, Linux, Mac.
What's easiest way to test for the operating system? I know I could parse the output of :version command. Is there something simpler that will reveal the OS?
From google:
You can use has() and the list of features under :help feature-list to
determine what type of Vim (and therefore under which OS is running).
if has('win32')
... win32 specific stuff ...
endif
Search for "version of Vim" from the feature-list help topic and that
should bring you to the different versions for which you can check.
In addition to #John's answer here is a full list of possible operating systems:
"▶2 os.fullname
for s:os.fullname in ["unix", "win16", "win32", "win64", "win32unix", "win95",
\ "mac", "macunix", "amiga", "os2", "qnx", "beos", "vms"]
if has(s:os.fullname)
break
endif
let s:os.fullname='unknown'
endfor
"▶2 os.name
if s:os.fullname[-3:] is 'nix' || s:os.fullname[:2] is 'mac' ||
\s:os.fullname is 'qnx' || s:os.fullname is 'vms'
let s:os.name='posix'
elseif s:os.fullname[:2] is 'win'
let s:os.name='nt'
elseif s:os.fullname is 'os2'
let s:os.name='os2'
else
let s:os.name='other'
endif
"▲2
This is the code used by my frawor plugin for determining current operating system.
Due to my love of Python:
python << endpython
import sys
sys.platform
endpython
Also maybe os.name if needed.

Resources