From c9ef8c76c5c25635cbc4fab991a7db5257a28648 Mon Sep 17 00:00:00 2001 From: Thomas Hunter II Date: Sat, 14 Nov 2015 17:37:54 -0800 Subject: [PATCH 01/96] replacing wildignore with more specific nerdtree/ctrlp settings also removing commented out items --- vimrc | 20 ++------------------ 1 file changed, 2 insertions(+), 18 deletions(-) diff --git a/vimrc b/vimrc index d49e8b0..ba08186 100644 --- a/vimrc +++ b/vimrc @@ -37,8 +37,6 @@ set hidden filetype indent on filetype plugin on set autoindent -"set expandtab -set wildignore=.svn,CVS,.git,*.o,*.a,*.class,*.mo,*.la,*.so,*.obj,*.swp,*.jpg,*.png,*.xpm,*.gif,node_modules/* "allow deletion of previously entered data in insert mode set backspace=indent,eol,start @@ -130,19 +128,11 @@ noremap A jcl let g:ackprg="ack -H --nocolor --nogroup --column" -" When searching for words with * and navigating with N/n, keep line centered vertically -"nnoremap n nzz -"nnoremap N Nzz -"nnoremap * *zz -"nnoremap # #zz -"nnoremap g* g*zz -"nnoremap g# g#zz - " CtrlP will load from the CWD, makes it easier with all these nested repos let g:ctrlp_working_path_mode = '' " CtrlP won't show results from node_modules -let g:ctrlp_custom_ignore = '\v[\/](node_modules|coverage|target|dist)|(\.(swp|ico|git|svn))$' +let g:ctrlp_custom_ignore = '\v[\/](node_modules|coverage|target|dist)|(\.(swp|ico|git|svn|png|jpg|gif|ttf))$' "type S, then type what you're looking for, a /, and what to replace it with nmap S :%s//g @@ -150,7 +140,7 @@ vmap S :s//g "------ NERDTree Options ------ -let NERDTreeIgnore=['CVS','\.dSYM$'] +let NERDTreeIgnore=['CVS','\.dSYM$', '.git', '.DS_Store', '*.swp', '*.swo', '*.swo'] "setting root dir in NT also sets VIM's cd let NERDTreeChDirMode=2 @@ -169,9 +159,6 @@ autocmd FileType nerdtree noremap " Open NERDTree if we're executing vim without specifying a file to open autocmd vimenter * if !argc() | NERDTree | endif -" Close if only NERDTree open -"autocmd bufenter * if (winnr("$") == 1 && exists("b:NERDTreeType") && b:NERDTreeType == "primary") | q | endif - " Hides "Press ? for help" let NERDTreeMinimalUI=1 @@ -202,9 +189,6 @@ map U :g/^$/d " R = Converts tabs to spaces in document map R :retab -" Deletes trailing space in file upon write -" autocmd BufWritePre * :%s/\s\+$//e - "------ JSON Filetype Settings ------ au BufRead,BufNewFile *.json set filetype=json From 4933c02b86c3f6a312713ef9b1dda1dc6b454699 Mon Sep 17 00:00:00 2001 From: Thomas Hunter II Date: Tue, 17 Nov 2015 15:06:46 -0800 Subject: [PATCH 02/96] Jade, Indent Guides, update Coffee Script --- bundle/coffee-script/.gitignore | 0 bundle/coffee-script/Copying.md | 2 +- bundle/coffee-script/Makefile | 0 bundle/coffee-script/News.md | 4 + bundle/coffee-script/Readme.md | 8 +- bundle/coffee-script/Thanks.md | 0 bundle/coffee-script/Todo.md | 0 bundle/coffee-script/after/indent/html.vim | 6 +- bundle/coffee-script/after/syntax/haml.vim | 0 bundle/coffee-script/after/syntax/html.vim | 2 +- bundle/coffee-script/autoload/coffee.vim | 2 +- bundle/coffee-script/compiler/cake.vim | 2 +- bundle/coffee-script/compiler/coffee.vim | 6 +- bundle/coffee-script/doc/coffee-script.txt | 0 bundle/coffee-script/ftdetect/coffee.vim | 2 +- bundle/coffee-script/ftplugin/coffee.vim | 13 +- bundle/coffee-script/indent/coffee.vim | 2 +- bundle/coffee-script/syntax/coffee.vim | 24 +- bundle/coffee-script/test/test-interp.coffee | 0 bundle/coffee-script/test/test-ops.coffee | 0 .../coffee-script/test/test-reserved.coffee | 0 bundle/coffee-script/test/test.haml | 0 bundle/coffee-script/test/test.html | 0 bundle/indent-guides/.gitignore | 1 + bundle/indent-guides/README.markdown | 71 ++ .../indent-guides/autoload/color_helper.vim | 879 ++++++++++++++++++ .../indent-guides/autoload/indent_guides.vim | 284 ++++++ bundle/indent-guides/doc/indent_guides.txt | 340 +++++++ bundle/indent-guides/plugin/indent_guides.vim | 91 ++ .../test-files/test-ts2sw0et.txt | 47 + .../test-files/test-ts2sw2et.txt | 47 + .../test-files/test-ts2sw2noet.txt | 47 + .../test-files/test-ts2sw4noet.txt | 24 + .../test-files/test-ts4sw4et.txt | 47 + .../test-files/test-ts4sw4noet.txt | 47 + .../test-files/test-ts8sw2noet.txt | 24 + .../test-files/test-ts8sw8et.txt | 47 + .../test-files/test-ts8sw8noet.txt | 47 + bundle/jade/README.markdown | 19 + bundle/jade/ftdetect/jade.vim | 2 + bundle/jade/ftplugin/jade.vim | 57 ++ bundle/jade/indent/jade.vim | 70 ++ bundle/jade/syntax/jade.vim | 102 ++ 43 files changed, 2331 insertions(+), 35 deletions(-) mode change 100644 => 100755 bundle/coffee-script/.gitignore mode change 100644 => 100755 bundle/coffee-script/Copying.md mode change 100644 => 100755 bundle/coffee-script/Makefile mode change 100644 => 100755 bundle/coffee-script/News.md mode change 100644 => 100755 bundle/coffee-script/Readme.md mode change 100644 => 100755 bundle/coffee-script/Thanks.md mode change 100644 => 100755 bundle/coffee-script/Todo.md mode change 100644 => 100755 bundle/coffee-script/after/indent/html.vim mode change 100644 => 100755 bundle/coffee-script/after/syntax/haml.vim mode change 100644 => 100755 bundle/coffee-script/after/syntax/html.vim mode change 100644 => 100755 bundle/coffee-script/autoload/coffee.vim mode change 100644 => 100755 bundle/coffee-script/compiler/cake.vim mode change 100644 => 100755 bundle/coffee-script/compiler/coffee.vim mode change 100644 => 100755 bundle/coffee-script/doc/coffee-script.txt mode change 100644 => 100755 bundle/coffee-script/ftdetect/coffee.vim mode change 100644 => 100755 bundle/coffee-script/ftplugin/coffee.vim mode change 100644 => 100755 bundle/coffee-script/indent/coffee.vim mode change 100644 => 100755 bundle/coffee-script/test/test-interp.coffee mode change 100644 => 100755 bundle/coffee-script/test/test-ops.coffee mode change 100644 => 100755 bundle/coffee-script/test/test-reserved.coffee mode change 100644 => 100755 bundle/coffee-script/test/test.haml mode change 100644 => 100755 bundle/coffee-script/test/test.html create mode 100755 bundle/indent-guides/.gitignore create mode 100755 bundle/indent-guides/README.markdown create mode 100755 bundle/indent-guides/autoload/color_helper.vim create mode 100755 bundle/indent-guides/autoload/indent_guides.vim create mode 100755 bundle/indent-guides/doc/indent_guides.txt create mode 100755 bundle/indent-guides/plugin/indent_guides.vim create mode 100755 bundle/indent-guides/test-files/test-ts2sw0et.txt create mode 100755 bundle/indent-guides/test-files/test-ts2sw2et.txt create mode 100755 bundle/indent-guides/test-files/test-ts2sw2noet.txt create mode 100755 bundle/indent-guides/test-files/test-ts2sw4noet.txt create mode 100755 bundle/indent-guides/test-files/test-ts4sw4et.txt create mode 100755 bundle/indent-guides/test-files/test-ts4sw4noet.txt create mode 100755 bundle/indent-guides/test-files/test-ts8sw2noet.txt create mode 100755 bundle/indent-guides/test-files/test-ts8sw8et.txt create mode 100755 bundle/indent-guides/test-files/test-ts8sw8noet.txt create mode 100755 bundle/jade/README.markdown create mode 100755 bundle/jade/ftdetect/jade.vim create mode 100755 bundle/jade/ftplugin/jade.vim create mode 100755 bundle/jade/indent/jade.vim create mode 100755 bundle/jade/syntax/jade.vim diff --git a/bundle/coffee-script/.gitignore b/bundle/coffee-script/.gitignore old mode 100644 new mode 100755 diff --git a/bundle/coffee-script/Copying.md b/bundle/coffee-script/Copying.md old mode 100644 new mode 100755 index 51cf8d1..a31ad2f --- a/bundle/coffee-script/Copying.md +++ b/bundle/coffee-script/Copying.md @@ -1,7 +1,7 @@ DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE Version 2, December 2004 - Copyright (C) 2010 to 2012 Mick Koch + Copyright (C) 2010 to 2014 Mick Koch Everyone is permitted to copy and distribute verbatim or modified copies of this license document, and changing it is allowed as long diff --git a/bundle/coffee-script/Makefile b/bundle/coffee-script/Makefile old mode 100644 new mode 100755 diff --git a/bundle/coffee-script/News.md b/bundle/coffee-script/News.md old mode 100644 new mode 100755 index 9706796..9f3f139 --- a/bundle/coffee-script/News.md +++ b/bundle/coffee-script/News.md @@ -1,3 +1,7 @@ +### Version 003 (October 10, 2014) + +Almost 3 years' worth of fixes and (hopefully) improvements. + ### Version 002 (December 5, 2011) Added binary numbers (0b0101) and fixed some bugs (#9, #62, #63, #65). diff --git a/bundle/coffee-script/Readme.md b/bundle/coffee-script/Readme.md old mode 100644 new mode 100755 index d557848..08d61f1 --- a/bundle/coffee-script/Readme.md +++ b/bundle/coffee-script/Readme.md @@ -91,7 +91,7 @@ Updating takes two steps: set rtp+=~/.vim/bundle/vundle/ call vundle#rc() - Bundle 'kchmck/vim-coffee-script' + Plugin 'kchmck/vim-coffee-script' syntax enable filetype plugin indent on @@ -100,9 +100,9 @@ Updating takes two steps: If you're adding Vundle to a built-up vimrc, just make sure all these calls are in there and that they occur in this order. -3. Open vim and run `:BundleInstall`. +3. Open vim and run `:PluginInstall`. -To update, open vim and run `:BundleInstall!` (notice the bang!) +To update, open vim and run `:PluginInstall!` (notice the bang!) ## Install from a Zip File @@ -313,7 +313,7 @@ the given `RANGE` and any extra `COFFEE-OPTIONS` are passed to `coffee`. ## CoffeeLint: Lint your CoffeeScript -CoffeeLint runs [coffeelint](http://www.coffeelint.org/) (version 0.5.7 or later +CoffeeLint runs [coffeelint](http://www.coffeelint.org/) (version 1.4.0 or later required) on the current file and adds any issues to the [quickfix] list. ![CoffeeLint](http://i.imgur.com/UN8Nr5N.png) diff --git a/bundle/coffee-script/Thanks.md b/bundle/coffee-script/Thanks.md old mode 100644 new mode 100755 diff --git a/bundle/coffee-script/Todo.md b/bundle/coffee-script/Todo.md old mode 100644 new mode 100755 diff --git a/bundle/coffee-script/after/indent/html.vim b/bundle/coffee-script/after/indent/html.vim old mode 100644 new mode 100755 index 10ca6ce..2fa8637 --- a/bundle/coffee-script/after/indent/html.vim +++ b/bundle/coffee-script/after/indent/html.vim @@ -1,15 +1,15 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL " Load the coffee and html indent functions. -unlet b:did_indent +silent! unlet b:did_indent runtime indent/coffee.vim let s:coffeeIndentExpr = &l:indentexpr " Load html last so it can overwrite coffee settings. -unlet b:did_indent +silent! unlet b:did_indent runtime indent/html.vim let s:htmlIndentExpr = &l:indentexpr diff --git a/bundle/coffee-script/after/syntax/haml.vim b/bundle/coffee-script/after/syntax/haml.vim old mode 100644 new mode 100755 diff --git a/bundle/coffee-script/after/syntax/html.vim b/bundle/coffee-script/after/syntax/html.vim old mode 100644 new mode 100755 index 9e2eb3a..82b44f1 --- a/bundle/coffee-script/after/syntax/html.vim +++ b/bundle/coffee-script/after/syntax/html.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL diff --git a/bundle/coffee-script/autoload/coffee.vim b/bundle/coffee-script/autoload/coffee.vim old mode 100644 new mode 100755 index 04d5efb..8d72795 --- a/bundle/coffee-script/autoload/coffee.vim +++ b/bundle/coffee-script/autoload/coffee.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL diff --git a/bundle/coffee-script/compiler/cake.vim b/bundle/coffee-script/compiler/cake.vim old mode 100644 new mode 100755 index 0a3c703..b49638e --- a/bundle/coffee-script/compiler/cake.vim +++ b/bundle/coffee-script/compiler/cake.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL diff --git a/bundle/coffee-script/compiler/coffee.vim b/bundle/coffee-script/compiler/coffee.vim old mode 100644 new mode 100755 index a70fa64..5a91457 --- a/bundle/coffee-script/compiler/coffee.vim +++ b/bundle/coffee-script/compiler/coffee.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL @@ -75,8 +75,8 @@ augroup CoffeeUpdateMakePrg " Set autocmd locally if compiler was set locally. if &l:makeprg =~ s:pat - autocmd BufFilePost,BufWritePost call s:UpdateMakePrg() + autocmd BufWritePre,BufFilePost call s:UpdateMakePrg() else - autocmd BufFilePost,BufWritePost call s:UpdateMakePrg() + autocmd BufWritePre,BufFilePost call s:UpdateMakePrg() endif augroup END diff --git a/bundle/coffee-script/doc/coffee-script.txt b/bundle/coffee-script/doc/coffee-script.txt old mode 100644 new mode 100755 diff --git a/bundle/coffee-script/ftdetect/coffee.vim b/bundle/coffee-script/ftdetect/coffee.vim old mode 100644 new mode 100755 index 5056929..e6c4d69 --- a/bundle/coffee-script/ftdetect/coffee.vim +++ b/bundle/coffee-script/ftdetect/coffee.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL diff --git a/bundle/coffee-script/ftplugin/coffee.vim b/bundle/coffee-script/ftplugin/coffee.vim old mode 100644 new mode 100755 index c44fe97..347155a --- a/bundle/coffee-script/ftplugin/coffee.vim +++ b/bundle/coffee-script/ftplugin/coffee.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL @@ -13,6 +13,7 @@ call coffee#CoffeeSetUpVariables() setlocal formatoptions-=t formatoptions+=croql setlocal comments=:# commentstring=#\ %s setlocal omnifunc=javascriptcomplete#CompleteJS +setlocal suffixesadd+=coffee " Create custom augroups. augroup CoffeeBufUpdate | augroup END @@ -330,7 +331,7 @@ function! s:CoffeeLint(startline, endline, bang, args) endif let output = system(g:coffee_linter . - \ ' -s --csv' . + \ ' -s --reporter csv' . \ ' ' . b:coffee_litcoffee . \ ' ' . g:coffee_lint_options . \ ' ' . a:args . @@ -394,11 +395,11 @@ if !exists('b:coffee_run_buf') call s:CoffeeRunResetVars() endif -command! -range=% -bar -nargs=* -complete=customlist,s:CoffeeComplete +command! -buffer -range=% -bar -nargs=* -complete=customlist,s:CoffeeComplete \ CoffeeCompile call s:CoffeeCompile(, , ) -command! -bar -nargs=* -complete=customlist,s:CoffeeComplete +command! -buffer -bar -nargs=* -complete=customlist,s:CoffeeComplete \ CoffeeWatch call s:CoffeeWatch() -command! -range=% -bar -nargs=* CoffeeRun +command! -buffer -range=% -bar -nargs=* CoffeeRun \ call s:CoffeeRun(, , ) -command! -range=% -bang -bar -nargs=* CoffeeLint +command! -buffer -range=% -bang -bar -nargs=* CoffeeLint \ call s:CoffeeLint(, , , ) diff --git a/bundle/coffee-script/indent/coffee.vim b/bundle/coffee-script/indent/coffee.vim old mode 100644 new mode 100755 index 7bd82e3..4f4570a --- a/bundle/coffee-script/indent/coffee.vim +++ b/bundle/coffee-script/indent/coffee.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL diff --git a/bundle/coffee-script/syntax/coffee.vim b/bundle/coffee-script/syntax/coffee.vim index eea5084..bfb252f 100755 --- a/bundle/coffee-script/syntax/coffee.vim +++ b/bundle/coffee-script/syntax/coffee.vim @@ -1,5 +1,5 @@ " Language: CoffeeScript -" Maintainer: Mick Koch +" Maintainer: Mick Koch " URL: http://github.com/kchmck/vim-coffee-script " License: WTFPL @@ -15,9 +15,6 @@ silent! unlet b:current_syntax " Highlight long strings. syntax sync fromstart -" CoffeeScript identifiers can have dollar signs. -setlocal isident+=$ - " These are `matches` instead of `keywords` because vim's highlighting " priority for keywords is higher than matches. This causes keywords to be " highlighted inside matches, even if a match says it shouldn't contain them -- @@ -35,7 +32,7 @@ hi def link coffeeConditional Conditional syn match coffeeException /\<\%(try\|catch\|finally\)\>/ display hi def link coffeeException Exception -syn match coffeeKeyword /\<\%(new\|in\|of\|by\|and\|or\|not\|is\|isnt\|class\|extends\|super\|do\)\>/ +syn match coffeeKeyword /\<\%(new\|in\|of\|by\|and\|or\|not\|is\|isnt\|class\|extends\|super\|do\|yield\)\>/ \ display " The `own` keyword is only a keyword after `for`. syn match coffeeKeyword /\/ contained containedin=coffeeRepeat @@ -67,7 +64,7 @@ syn match coffeeSpecialVar /\<\%(this\|prototype\|arguments\)\>/ display hi def link coffeeSpecialVar Special " An @-variable -syn match coffeeSpecialIdent /@\%(\I\i*\)\?/ display +syn match coffeeSpecialIdent /@\%(\%(\I\|\$\)\%(\i\|\$\)*\)\?/ display hi def link coffeeSpecialIdent Identifier " A class-like name that starts with a capital letter @@ -95,26 +92,27 @@ syn region coffeeString start=/'/ skip=/\\\\\|\\'/ end=/'/ hi def link coffeeString String " A integer, including a leading plus or minus -syn match coffeeNumber /\i\@/ display syn match coffeeNumber /\<0[bB][01]\+\>/ display syn match coffeeNumber /\<0[oO][0-7]\+\>/ display +syn match coffeeNumber /\<\%(Infinity\|NaN\)\>/ display hi def link coffeeNumber Number " A floating-point number, including a leading plus or minus -syn match coffeeFloat /\i\@/ +syn match coffeeReservedError /\<\%(case\|default\|function\|var\|void\|with\|const\|let\|enum\|export\|import\|native\|__hasProp\|__extends\|__slice\|__bind\|__indexOf\|implements\|interface\|package\|private\|protected\|public\|static\)\>/ \ display hi def link coffeeReservedError Error " A normal object assignment -syn match coffeeObjAssign /@\?\I\i*\s*\ze::\@!/ contains=@coffeeIdentifier display +syn match coffeeObjAssign /@\?\%(\I\|\$\)\%(\i\|\$\)*\s*\ze::\@!/ contains=@coffeeIdentifier display hi def link coffeeObjAssign Identifier syn keyword coffeeTodo TODO FIXME XXX contained @@ -148,7 +146,7 @@ hi def link coffeeEscape SpecialChar " A regex -- must not follow a parenthesis, number, or identifier, and must not " be followed by a number -syn region coffeeRegex start=#\%(\%()\|\i\@ + +## Features: +* Can detect both tab and space indent styles. +* Automatically inspects your colorscheme and picks appropriate colors (gVim only). +* Will highlight indent levels with alternating colors. +* Full support for gVim and basic support for Terminal Vim. +* Seems to work on Windows gVim 7.3 (haven't done any extensive tests though). +* Customizable size for indent guides, eg. skinny guides (soft-tabs only). +* Customizable start indent level. +* **NEW:** Highlight support for files with a mixture of tab and space indent styles. + +## Requirements +* Vim 7.2+ + +## Installation +To install the plugin just copy `autoload`, `plugin`, `doc` directories into your `.vim` directory. + +Alternatively if you have [Pathogen](http://www.vim.org/scripts/script.php?script_id=2332) installed, just clone this repo into a subdirectory of your `.vim/bundle` directory like so: + + cd ~/.vim/bundle + git clone git://github.com/nathanaelkane/vim-indent-guides.git + +## Usage +The default mapping to toggle the plugin is `ig` + +### gVim +**This plugin should work with gVim out of the box, no configuration needed.** It will automatically inspect your colorscheme and pick appropriate colors. + +### Setting custom indent colors +Here's an example of how to define custom colors instead of using the ones the plugin automatically generates for you. Add this to your `.vimrc` file: + + let g:indent_guides_auto_colors = 0 + autocmd VimEnter,Colorscheme * :hi IndentGuidesOdd guibg=red ctermbg=3 + autocmd VimEnter,Colorscheme * :hi IndentGuidesEven guibg=green ctermbg=4 + +Alternatively you can add the following lines to your colorscheme file. + + hi IndentGuidesOdd guibg=red ctermbg=3 + hi IndentGuidesEven guibg=green ctermbg=4 + +### Terminal Vim +At the moment Terminal Vim only has basic support. This means is that colors won't be automatically calculated based on your colorscheme. Instead, some preset colors are used depending on whether `background` is set to `dark` or `light`. + +When `set background=dark` is used, the following highlight colors will be defined: + + hi IndentGuidesOdd ctermbg=black + hi IndentGuidesEven ctermbg=darkgrey + +Alternatively, when `set background=light` is used, the following highlight colors will be defined: + + hi IndentGuidesOdd ctermbg=white + hi IndentGuidesEven ctermbg=lightgrey + +If for some reason it's incorrectly defining light highlight colors instead of dark ones or vice versa, the first thing you should check is that the `background` value is being set correctly for your colorscheme. Sometimes it's best to manually set the `background` value in your `.vimrc`, for example: + + colorscheme desert256 + set background=dark + +Alternatively you can manually setup the highlight colors yourself, see `:help indent_guides_auto_colors` for an example. + +## Help +`:help indent-guides` + +## Screenshots + + + diff --git a/bundle/indent-guides/autoload/color_helper.vim b/bundle/indent-guides/autoload/color_helper.vim new file mode 100755 index 0000000..54d18c0 --- /dev/null +++ b/bundle/indent-guides/autoload/color_helper.vim @@ -0,0 +1,879 @@ +" Author: Nate Kane +" Homepage: http://github.com/nathanaelkane/vim-indent-guides + +" +" Return hex string equivalent to given decimal string or number. +" +" Example: color_helper#dec_to_hex(255, 2) +" Returns: 'FF' +" +" Example: color_helper#dec_to_hex(255, 5) +" Returns: '000FF' +" +function! color_helper#dec_to_hex(arg, padding) + return toupper(printf('%0' . a:padding . 'x', a:arg + 0)) +endfunction + +" +" Return number equivalent to given hex string ('0x' is optional). +" +" Example: color_helper#hex_to_dec('FF') +" Returns: 255 +" +" Example: color_helper#hex_to_dec('88') +" Returns: 136 +" +" Example: color_helper#hex_to_dec('00') +" Returns: 0 +" +function! color_helper#hex_to_dec(arg) + return (a:arg =~? '^0x') ? a:arg + 0 : ('0x'.a:arg) + 0 +endfunction + +" +" Converts a given hex color string into an rgb list (eg. [red, green, blue]). +" +" Example: color_helper#hex_color_to_rgb('#0088FF') +" Returns: [0, 136, 255] +" +function! color_helper#hex_color_to_rgb(hex_color) + let l:rgb = [] + + if a:hex_color =~ g:indent_guides_color_hex_pattern + let l:red = color_helper#hex_to_dec(strpart(a:hex_color, 1, 2)) + let l:green = color_helper#hex_to_dec(strpart(a:hex_color, 3, 2)) + let l:blue = color_helper#hex_to_dec(strpart(a:hex_color, 5, 2)) + let l:rgb = [l:red, l:green, l:blue] + end + + return l:rgb +endfunction + +" +" Converts a given rgb list (eg. [red, green, blue]) into a hex color string. +" +" Example: color_helper#rgb_color_to_hex([0, 136, 255]) +" Returns: '#0088FF' +" +function! color_helper#rgb_color_to_hex(rgb_color) + let l:hex_color = '#' + let l:hex_color .= color_helper#dec_to_hex(a:rgb_color[0], 2) " red + let l:hex_color .= color_helper#dec_to_hex(a:rgb_color[1], 2) " green + let l:hex_color .= color_helper#dec_to_hex(a:rgb_color[2], 2) " blue + + return l:hex_color +endfunction + +" +" Returns a ligtened color using the given color and the percent to lighten it +" by. +" +" Example: color_helper#hex_color_lighten('#000000', 0.10) +" Returns: '#191919' +" +function! color_helper#hex_color_lighten(color, percent) + let l:rgb = color_helper#hex_color_to_rgb(a:color) + let l:rgb_lightened = [] + + for i in l:rgb + call add(l:rgb_lightened, float2nr(i + ((255 - i) * a:percent))) + endfor + + return color_helper#rgb_color_to_hex(l:rgb_lightened) +endfunction + +" +" Returns a darkened color using the given color and the percent to darken it +" by. +" +" Example: color_helper#hex_color_darken('#FFFFFF', 0.10) +" Returns: '#E5E5E5' +" +function! color_helper#hex_color_darken(color, percent) + let l:rgb = color_helper#hex_color_to_rgb(a:color) + let l:rgb_darkened = [] + + for i in l:rgb + call add(l:rgb_darkened, float2nr(i * (1 - a:percent))) + endfor + + return color_helper#rgb_color_to_hex(l:rgb_darkened) +endfunction + +" +" Returns a hex color code for the given color name. +" +" Example: color_helper#color_name_to_hex('darkslategray') +" Returns: '#2F4F4F' +" +function! color_helper#color_name_to_hex(color_name) + let l:hex_code = '' + let l:color_name = tolower(a:color_name) + + let l:color_list = { + \ 'alice blue' : '#F0F8FF', + \ 'aliceblue' : '#F0F8FF', + \ 'antique white' : '#FAEBD7', + \ 'antiquewhite' : '#FAEBD7', + \ 'antiquewhite1' : '#FFEFDB', + \ 'antiquewhite2' : '#EEDFCC', + \ 'antiquewhite3' : '#CDC0B0', + \ 'antiquewhite4' : '#8B8378', + \ 'aquamarine' : '#7FFFD4', + \ 'aquamarine1' : '#7FFFD4', + \ 'aquamarine2' : '#76EEC6', + \ 'aquamarine3' : '#66CDAA', + \ 'aquamarine4' : '#458B74', + \ 'azure' : '#F0FFFF', + \ 'azure1' : '#F0FFFF', + \ 'azure2' : '#E0EEEE', + \ 'azure3' : '#C1CDCD', + \ 'azure4' : '#838B8B', + \ 'beige' : '#F5F5DC', + \ 'bisque' : '#FFE4C4', + \ 'bisque1' : '#FFE4C4', + \ 'bisque2' : '#EED5B7', + \ 'bisque3' : '#CDB79E', + \ 'bisque4' : '#8B7D6B', + \ 'black' : '#000000', + \ 'blanched almond' : '#FFEBCD', + \ 'blanchedalmond' : '#FFEBCD', + \ 'blue violet' : '#8A2BE2', + \ 'blue' : '#0000FF', + \ 'blue1' : '#0000FF', + \ 'blue2' : '#0000EE', + \ 'blue3' : '#0000CD', + \ 'blue4' : '#00008B', + \ 'blueviolet' : '#8A2BE2', + \ 'brown' : '#A52A2A', + \ 'brown1' : '#FF4040', + \ 'brown2' : '#EE3B3B', + \ 'brown3' : '#CD3333', + \ 'brown4' : '#8B2323', + \ 'burlywood' : '#DEB887', + \ 'burlywood1' : '#FFD39B', + \ 'burlywood2' : '#EEC591', + \ 'burlywood3' : '#CDAA7D', + \ 'burlywood4' : '#8B7355', + \ 'cadet blue' : '#5F9EA0', + \ 'cadetblue' : '#5F9EA0', + \ 'cadetblue1' : '#98F5FF', + \ 'cadetblue2' : '#8EE5EE', + \ 'cadetblue3' : '#7AC5CD', + \ 'cadetblue4' : '#53868B', + \ 'chartreuse' : '#7FFF00', + \ 'chartreuse1' : '#7FFF00', + \ 'chartreuse2' : '#76EE00', + \ 'chartreuse3' : '#66CD00', + \ 'chartreuse4' : '#458B00', + \ 'chocolate' : '#D2691E', + \ 'chocolate1' : '#FF7F24', + \ 'chocolate2' : '#EE7621', + \ 'chocolate3' : '#CD661D', + \ 'chocolate4' : '#8B4513', + \ 'coral' : '#FF7F50', + \ 'coral1' : '#FF7256', + \ 'coral2' : '#EE6A50', + \ 'coral3' : '#CD5B45', + \ 'coral4' : '#8B3E2F', + \ 'cornflower blue' : '#6495ED', + \ 'cornflowerblue' : '#6495ED', + \ 'cornsilk' : '#FFF8DC', + \ 'cornsilk1' : '#FFF8DC', + \ 'cornsilk2' : '#EEE8CD', + \ 'cornsilk3' : '#CDC8B1', + \ 'cornsilk4' : '#8B8878', + \ 'cyan' : '#00FFFF', + \ 'cyan1' : '#00FFFF', + \ 'cyan2' : '#00EEEE', + \ 'cyan3' : '#00CDCD', + \ 'cyan4' : '#008B8B', + \ 'dark blue' : '#00008B', + \ 'dark cyan' : '#008B8B', + \ 'dark goldenrod' : '#B8860B', + \ 'dark gray' : '#A9A9A9', + \ 'dark green' : '#006400', + \ 'dark grey' : '#A9A9A9', + \ 'dark khaki' : '#BDB76B', + \ 'dark magenta' : '#8B008B', + \ 'dark olive green' : '#556B2F', + \ 'dark orange' : '#FF8C00', + \ 'dark orchid' : '#9932CC', + \ 'dark red' : '#8B0000', + \ 'dark salmon' : '#E9967A', + \ 'dark sea green' : '#8FBC8F', + \ 'dark slate blue' : '#483D8B', + \ 'dark slate gray' : '#2F4F4F', + \ 'dark slate grey' : '#2F4F4F', + \ 'dark turquoise' : '#00CED1', + \ 'dark violet' : '#9400D3', + \ 'dark yellow' : '#BBBB00', + \ 'darkblue' : '#00008B', + \ 'darkcyan' : '#008B8B', + \ 'darkgoldenrod' : '#B8860B', + \ 'darkgoldenrod1' : '#FFB90F', + \ 'darkgoldenrod2' : '#EEAD0E', + \ 'darkgoldenrod3' : '#CD950C', + \ 'darkgoldenrod4' : '#8B6508', + \ 'darkgray' : '#A9A9A9', + \ 'darkgreen' : '#006400', + \ 'darkgrey' : '#A9A9A9', + \ 'darkkhaki' : '#BDB76B', + \ 'darkmagenta' : '#8B008B', + \ 'darkolivegreen' : '#556B2F', + \ 'darkolivegreen1' : '#CAFF70', + \ 'darkolivegreen2' : '#BCEE68', + \ 'darkolivegreen3' : '#A2CD5A', + \ 'darkolivegreen4' : '#6E8B3D', + \ 'darkorange' : '#FF8C00', + \ 'darkorange1' : '#FF7F00', + \ 'darkorange2' : '#EE7600', + \ 'darkorange3' : '#CD6600', + \ 'darkorange4' : '#8B4500', + \ 'darkorchid' : '#9932CC', + \ 'darkorchid1' : '#BF3EFF', + \ 'darkorchid2' : '#B23AEE', + \ 'darkorchid3' : '#9A32CD', + \ 'darkorchid4' : '#68228B', + \ 'darkred' : '#8B0000', + \ 'darksalmon' : '#E9967A', + \ 'darkseagreen' : '#8FBC8F', + \ 'darkseagreen1' : '#C1FFC1', + \ 'darkseagreen2' : '#B4EEB4', + \ 'darkseagreen3' : '#9BCD9B', + \ 'darkseagreen4' : '#698B69', + \ 'darkslateblue' : '#483D8B', + \ 'darkslategray' : '#2F4F4F', + \ 'darkslategray1' : '#97FFFF', + \ 'darkslategray2' : '#8DEEEE', + \ 'darkslategray3' : '#79CDCD', + \ 'darkslategray4' : '#528B8B', + \ 'darkslategrey' : '#2F4F4F', + \ 'darkturquoise' : '#00CED1', + \ 'darkviolet' : '#9400D3', + \ 'darkyellow' : '#BBBB00', + \ 'deep pink' : '#FF1493', + \ 'deep sky blue' : '#00BFFF', + \ 'deeppink' : '#FF1493', + \ 'deeppink1' : '#FF1493', + \ 'deeppink2' : '#EE1289', + \ 'deeppink3' : '#CD1076', + \ 'deeppink4' : '#8B0A50', + \ 'deepskyblue' : '#00BFFF', + \ 'deepskyblue1' : '#00BFFF', + \ 'deepskyblue2' : '#00B2EE', + \ 'deepskyblue3' : '#009ACD', + \ 'deepskyblue4' : '#00688B', + \ 'dim gray' : '#696969', + \ 'dim grey' : '#696969', + \ 'dimgray' : '#696969', + \ 'dimgrey' : '#696969', + \ 'dodger blue' : '#1E90FF', + \ 'dodgerblue' : '#1E90FF', + \ 'dodgerblue1' : '#1E90FF', + \ 'dodgerblue2' : '#1C86EE', + \ 'dodgerblue3' : '#1874CD', + \ 'dodgerblue4' : '#104E8B', + \ 'firebrick' : '#B22222', + \ 'firebrick1' : '#FF3030', + \ 'firebrick2' : '#EE2C2C', + \ 'firebrick3' : '#CD2626', + \ 'firebrick4' : '#8B1A1A', + \ 'floral white' : '#FFFAF0', + \ 'floralwhite' : '#FFFAF0', + \ 'forest green' : '#228B22', + \ 'forestgreen' : '#228B22', + \ 'gainsboro' : '#DCDCDC', + \ 'ghost white' : '#F8F8FF', + \ 'ghostwhite' : '#F8F8FF', + \ 'gold' : '#FFD700', + \ 'gold1' : '#FFD700', + \ 'gold2' : '#EEC900', + \ 'gold3' : '#CDAD00', + \ 'gold4' : '#8B7500', + \ 'goldenrod' : '#DAA520', + \ 'goldenrod1' : '#FFC125', + \ 'goldenrod2' : '#EEB422', + \ 'goldenrod3' : '#CD9B1D', + \ 'goldenrod4' : '#8B6914', + \ 'gray' : '#BEBEBE', + \ 'gray0' : '#000000', + \ 'gray1' : '#030303', + \ 'gray10' : '#1A1A1A', + \ 'gray100' : '#FFFFFF', + \ 'gray11' : '#1C1C1C', + \ 'gray12' : '#1F1F1F', + \ 'gray13' : '#212121', + \ 'gray14' : '#242424', + \ 'gray15' : '#262626', + \ 'gray16' : '#292929', + \ 'gray17' : '#2B2B2B', + \ 'gray18' : '#2E2E2E', + \ 'gray19' : '#303030', + \ 'gray2' : '#050505', + \ 'gray20' : '#333333', + \ 'gray21' : '#363636', + \ 'gray22' : '#383838', + \ 'gray23' : '#3B3B3B', + \ 'gray24' : '#3D3D3D', + \ 'gray25' : '#404040', + \ 'gray26' : '#424242', + \ 'gray27' : '#454545', + \ 'gray28' : '#474747', + \ 'gray29' : '#4A4A4A', + \ 'gray3' : '#080808', + \ 'gray30' : '#4D4D4D', + \ 'gray31' : '#4F4F4F', + \ 'gray32' : '#525252', + \ 'gray33' : '#545454', + \ 'gray34' : '#575757', + \ 'gray35' : '#595959', + \ 'gray36' : '#5C5C5C', + \ 'gray37' : '#5E5E5E', + \ 'gray38' : '#616161', + \ 'gray39' : '#636363', + \ 'gray4' : '#0A0A0A', + \ 'gray40' : '#666666', + \ 'gray41' : '#696969', + \ 'gray42' : '#6B6B6B', + \ 'gray43' : '#6E6E6E', + \ 'gray44' : '#707070', + \ 'gray45' : '#737373', + \ 'gray46' : '#757575', + \ 'gray47' : '#787878', + \ 'gray48' : '#7A7A7A', + \ 'gray49' : '#7D7D7D', + \ 'gray5' : '#0D0D0D', + \ 'gray50' : '#7F7F7F', + \ 'gray51' : '#828282', + \ 'gray52' : '#858585', + \ 'gray53' : '#878787', + \ 'gray54' : '#8A8A8A', + \ 'gray55' : '#8C8C8C', + \ 'gray56' : '#8F8F8F', + \ 'gray57' : '#919191', + \ 'gray58' : '#949494', + \ 'gray59' : '#969696', + \ 'gray6' : '#0F0F0F', + \ 'gray60' : '#999999', + \ 'gray61' : '#9C9C9C', + \ 'gray62' : '#9E9E9E', + \ 'gray63' : '#A1A1A1', + \ 'gray64' : '#A3A3A3', + \ 'gray65' : '#A6A6A6', + \ 'gray66' : '#A8A8A8', + \ 'gray67' : '#ABABAB', + \ 'gray68' : '#ADADAD', + \ 'gray69' : '#B0B0B0', + \ 'gray7' : '#121212', + \ 'gray70' : '#B3B3B3', + \ 'gray71' : '#B5B5B5', + \ 'gray72' : '#B8B8B8', + \ 'gray73' : '#BABABA', + \ 'gray74' : '#BDBDBD', + \ 'gray75' : '#BFBFBF', + \ 'gray76' : '#C2C2C2', + \ 'gray77' : '#C4C4C4', + \ 'gray78' : '#C7C7C7', + \ 'gray79' : '#C9C9C9', + \ 'gray8' : '#141414', + \ 'gray80' : '#CCCCCC', + \ 'gray81' : '#CFCFCF', + \ 'gray82' : '#D1D1D1', + \ 'gray83' : '#D4D4D4', + \ 'gray84' : '#D6D6D6', + \ 'gray85' : '#D9D9D9', + \ 'gray86' : '#DBDBDB', + \ 'gray87' : '#DEDEDE', + \ 'gray88' : '#E0E0E0', + \ 'gray89' : '#E3E3E3', + \ 'gray9' : '#171717', + \ 'gray90' : '#E5E5E5', + \ 'gray91' : '#E8E8E8', + \ 'gray92' : '#EBEBEB', + \ 'gray93' : '#EDEDED', + \ 'gray94' : '#F0F0F0', + \ 'gray95' : '#F2F2F2', + \ 'gray96' : '#F5F5F5', + \ 'gray97' : '#F7F7F7', + \ 'gray98' : '#FAFAFA', + \ 'gray99' : '#FCFCFC', + \ 'green yellow' : '#ADFF2F', + \ 'green' : '#00FF00', + \ 'green1' : '#00FF00', + \ 'green2' : '#00EE00', + \ 'green3' : '#00CD00', + \ 'green4' : '#008B00', + \ 'greenyellow' : '#ADFF2F', + \ 'grey' : '#BEBEBE', + \ 'grey0' : '#000000', + \ 'grey1' : '#030303', + \ 'grey10' : '#1A1A1A', + \ 'grey100' : '#FFFFFF', + \ 'grey11' : '#1C1C1C', + \ 'grey12' : '#1F1F1F', + \ 'grey13' : '#212121', + \ 'grey14' : '#242424', + \ 'grey15' : '#262626', + \ 'grey16' : '#292929', + \ 'grey17' : '#2B2B2B', + \ 'grey18' : '#2E2E2E', + \ 'grey19' : '#303030', + \ 'grey2' : '#050505', + \ 'grey20' : '#333333', + \ 'grey21' : '#363636', + \ 'grey22' : '#383838', + \ 'grey23' : '#3B3B3B', + \ 'grey24' : '#3D3D3D', + \ 'grey25' : '#404040', + \ 'grey26' : '#424242', + \ 'grey27' : '#454545', + \ 'grey28' : '#474747', + \ 'grey29' : '#4A4A4A', + \ 'grey3' : '#080808', + \ 'grey30' : '#4D4D4D', + \ 'grey31' : '#4F4F4F', + \ 'grey32' : '#525252', + \ 'grey33' : '#545454', + \ 'grey34' : '#575757', + \ 'grey35' : '#595959', + \ 'grey36' : '#5C5C5C', + \ 'grey37' : '#5E5E5E', + \ 'grey38' : '#616161', + \ 'grey39' : '#636363', + \ 'grey4' : '#0A0A0A', + \ 'grey40' : '#666666', + \ 'grey41' : '#696969', + \ 'grey42' : '#6B6B6B', + \ 'grey43' : '#6E6E6E', + \ 'grey44' : '#707070', + \ 'grey45' : '#737373', + \ 'grey46' : '#757575', + \ 'grey47' : '#787878', + \ 'grey48' : '#7A7A7A', + \ 'grey49' : '#7D7D7D', + \ 'grey5' : '#0D0D0D', + \ 'grey50' : '#7F7F7F', + \ 'grey51' : '#828282', + \ 'grey52' : '#858585', + \ 'grey53' : '#878787', + \ 'grey54' : '#8A8A8A', + \ 'grey55' : '#8C8C8C', + \ 'grey56' : '#8F8F8F', + \ 'grey57' : '#919191', + \ 'grey58' : '#949494', + \ 'grey59' : '#969696', + \ 'grey6' : '#0F0F0F', + \ 'grey60' : '#999999', + \ 'grey61' : '#9C9C9C', + \ 'grey62' : '#9E9E9E', + \ 'grey63' : '#A1A1A1', + \ 'grey64' : '#A3A3A3', + \ 'grey65' : '#A6A6A6', + \ 'grey66' : '#A8A8A8', + \ 'grey67' : '#ABABAB', + \ 'grey68' : '#ADADAD', + \ 'grey69' : '#B0B0B0', + \ 'grey7' : '#121212', + \ 'grey70' : '#B3B3B3', + \ 'grey71' : '#B5B5B5', + \ 'grey72' : '#B8B8B8', + \ 'grey73' : '#BABABA', + \ 'grey74' : '#BDBDBD', + \ 'grey75' : '#BFBFBF', + \ 'grey76' : '#C2C2C2', + \ 'grey77' : '#C4C4C4', + \ 'grey78' : '#C7C7C7', + \ 'grey79' : '#C9C9C9', + \ 'grey8' : '#141414', + \ 'grey80' : '#CCCCCC', + \ 'grey81' : '#CFCFCF', + \ 'grey82' : '#D1D1D1', + \ 'grey83' : '#D4D4D4', + \ 'grey84' : '#D6D6D6', + \ 'grey85' : '#D9D9D9', + \ 'grey86' : '#DBDBDB', + \ 'grey87' : '#DEDEDE', + \ 'grey88' : '#E0E0E0', + \ 'grey89' : '#E3E3E3', + \ 'grey9' : '#171717', + \ 'grey90' : '#E5E5E5', + \ 'grey91' : '#E8E8E8', + \ 'grey92' : '#EBEBEB', + \ 'grey93' : '#EDEDED', + \ 'grey94' : '#F0F0F0', + \ 'grey95' : '#F2F2F2', + \ 'grey96' : '#F5F5F5', + \ 'grey97' : '#F7F7F7', + \ 'grey98' : '#FAFAFA', + \ 'grey99' : '#FCFCFC', + \ 'honeydew' : '#F0FFF0', + \ 'honeydew1' : '#F0FFF0', + \ 'honeydew2' : '#E0EEE0', + \ 'honeydew3' : '#C1CDC1', + \ 'honeydew4' : '#838B83', + \ 'hot pink' : '#FF69B4', + \ 'hotpink' : '#FF69B4', + \ 'hotpink1' : '#FF6EB4', + \ 'hotpink2' : '#EE6AA7', + \ 'hotpink3' : '#CD6090', + \ 'hotpink4' : '#8B3A62', + \ 'indian red' : '#CD5C5C', + \ 'indianred' : '#CD5C5C', + \ 'indianred1' : '#FF6A6A', + \ 'indianred2' : '#EE6363', + \ 'indianred3' : '#CD5555', + \ 'indianred4' : '#8B3A3A', + \ 'ivory' : '#FFFFF0', + \ 'ivory1' : '#FFFFF0', + \ 'ivory2' : '#EEEEE0', + \ 'ivory3' : '#CDCDC1', + \ 'ivory4' : '#8B8B83', + \ 'khaki' : '#F0E68C', + \ 'khaki1' : '#FFF68F', + \ 'khaki2' : '#EEE685', + \ 'khaki3' : '#CDC673', + \ 'khaki4' : '#8B864E', + \ 'lavender blush' : '#FFF0F5', + \ 'lavender' : '#E6E6FA', + \ 'lavenderblush' : '#FFF0F5', + \ 'lavenderblush1' : '#FFF0F5', + \ 'lavenderblush2' : '#EEE0E5', + \ 'lavenderblush3' : '#CDC1C5', + \ 'lavenderblush4' : '#8B8386', + \ 'lawn green' : '#7CFC00', + \ 'lawngreen' : '#7CFC00', + \ 'lemon chiffon' : '#FFFACD', + \ 'lemonchiffon' : '#FFFACD', + \ 'lemonchiffon1' : '#FFFACD', + \ 'lemonchiffon2' : '#EEE9BF', + \ 'lemonchiffon3' : '#CDC9A5', + \ 'lemonchiffon4' : '#8B8970', + \ 'light blue' : '#ADD8E6', + \ 'light coral' : '#F08080', + \ 'light cyan' : '#E0FFFF', + \ 'light goldenrod yellow' : '#FAFAD2', + \ 'light goldenrod' : '#EEDD82', + \ 'light gray' : '#D3D3D3', + \ 'light green' : '#90EE90', + \ 'light grey' : '#D3D3D3', + \ 'light magenta' : '#FFBBFF', + \ 'light pink' : '#FFB6C1', + \ 'light red' : '#FFBBBB', + \ 'light salmon' : '#FFA07A', + \ 'light sea green' : '#20B2AA', + \ 'light sky blue' : '#87CEFA', + \ 'light slate blue' : '#8470FF', + \ 'light slate gray' : '#778899', + \ 'light slate grey' : '#778899', + \ 'light steel blue' : '#B0C4DE', + \ 'light yellow' : '#FFFFE0', + \ 'lightblue' : '#ADD8E6', + \ 'lightblue1' : '#BFEFFF', + \ 'lightblue2' : '#B2DFEE', + \ 'lightblue3' : '#9AC0CD', + \ 'lightblue4' : '#68838B', + \ 'lightcoral' : '#F08080', + \ 'lightcyan' : '#E0FFFF', + \ 'lightcyan1' : '#E0FFFF', + \ 'lightcyan2' : '#D1EEEE', + \ 'lightcyan3' : '#B4CDCD', + \ 'lightcyan4' : '#7A8B8B', + \ 'lightgoldenrod' : '#EEDD82', + \ 'lightgoldenrod1' : '#FFEC8B', + \ 'lightgoldenrod2' : '#EEDC82', + \ 'lightgoldenrod3' : '#CDBE70', + \ 'lightgoldenrod4' : '#8B814C', + \ 'lightgoldenrodyellow' : '#FAFAD2', + \ 'lightgray' : '#D3D3D3', + \ 'lightgreen' : '#90EE90', + \ 'lightgrey' : '#D3D3D3', + \ 'lightmagenta' : '#FFBBFF', + \ 'lightpink' : '#FFB6C1', + \ 'lightpink1' : '#FFAEB9', + \ 'lightpink2' : '#EEA2AD', + \ 'lightpink3' : '#CD8C95', + \ 'lightpink4' : '#8B5F65', + \ 'lightred' : '#FFBBBB', + \ 'lightsalmon' : '#FFA07A', + \ 'lightsalmon1' : '#FFA07A', + \ 'lightsalmon2' : '#EE9572', + \ 'lightsalmon3' : '#CD8162', + \ 'lightsalmon4' : '#8B5742', + \ 'lightseagreen' : '#20B2AA', + \ 'lightskyblue' : '#87CEFA', + \ 'lightskyblue1' : '#B0E2FF', + \ 'lightskyblue2' : '#A4D3EE', + \ 'lightskyblue3' : '#8DB6CD', + \ 'lightskyblue4' : '#607B8B', + \ 'lightslateblue' : '#8470FF', + \ 'lightslategray' : '#778899', + \ 'lightslategrey' : '#778899', + \ 'lightsteelblue' : '#B0C4DE', + \ 'lightsteelblue1' : '#CAE1FF', + \ 'lightsteelblue2' : '#BCD2EE', + \ 'lightsteelblue3' : '#A2B5CD', + \ 'lightsteelblue4' : '#6E7B8B', + \ 'lightyellow' : '#FFFFE0', + \ 'lightyellow1' : '#FFFFE0', + \ 'lightyellow2' : '#EEEED1', + \ 'lightyellow3' : '#CDCDB4', + \ 'lightyellow4' : '#8B8B7A', + \ 'lime green' : '#32CD32', + \ 'limegreen' : '#32CD32', + \ 'linen' : '#FAF0E6', + \ 'magenta' : '#FF00FF', + \ 'magenta1' : '#FF00FF', + \ 'magenta2' : '#EE00EE', + \ 'magenta3' : '#CD00CD', + \ 'magenta4' : '#8B008B', + \ 'maroon' : '#B03060', + \ 'maroon1' : '#FF34B3', + \ 'maroon2' : '#EE30A7', + \ 'maroon3' : '#CD2990', + \ 'maroon4' : '#8B1C62', + \ 'medium aquamarine' : '#66CDAA', + \ 'medium blue' : '#0000CD', + \ 'medium orchid' : '#BA55D3', + \ 'medium purple' : '#9370DB', + \ 'medium sea green' : '#3CB371', + \ 'medium slate blue' : '#7B68EE', + \ 'medium spring green' : '#00FA9A', + \ 'medium turquoise' : '#48D1CC', + \ 'medium violet red' : '#C71585', + \ 'mediumaquamarine' : '#66CDAA', + \ 'mediumblue' : '#0000CD', + \ 'mediumorchid' : '#BA55D3', + \ 'mediumorchid1' : '#E066FF', + \ 'mediumorchid2' : '#D15FEE', + \ 'mediumorchid3' : '#B452CD', + \ 'mediumorchid4' : '#7A378B', + \ 'mediumpurple' : '#9370DB', + \ 'mediumpurple1' : '#AB82FF', + \ 'mediumpurple2' : '#9F79EE', + \ 'mediumpurple3' : '#8968CD', + \ 'mediumpurple4' : '#5D478B', + \ 'mediumseagreen' : '#3CB371', + \ 'mediumslateblue' : '#7B68EE', + \ 'mediumspringgreen' : '#00FA9A', + \ 'mediumturquoise' : '#48D1CC', + \ 'mediumvioletred' : '#C71585', + \ 'midnight blue' : '#191970', + \ 'midnightblue' : '#191970', + \ 'mint cream' : '#F5FFFA', + \ 'mintcream' : '#F5FFFA', + \ 'misty rose' : '#FFE4E1', + \ 'mistyrose' : '#FFE4E1', + \ 'mistyrose1' : '#FFE4E1', + \ 'mistyrose2' : '#EED5D2', + \ 'mistyrose3' : '#CDB7B5', + \ 'mistyrose4' : '#8B7D7B', + \ 'moccasin' : '#FFE4B5', + \ 'navajo white' : '#FFDEAD', + \ 'navajowhite' : '#FFDEAD', + \ 'navajowhite1' : '#FFDEAD', + \ 'navajowhite2' : '#EECFA1', + \ 'navajowhite3' : '#CDB38B', + \ 'navajowhite4' : '#8B795E', + \ 'navy blue' : '#000080', + \ 'navy' : '#000080', + \ 'navyblue' : '#000080', + \ 'old lace' : '#FDF5E6', + \ 'oldlace' : '#FDF5E6', + \ 'olive drab' : '#6B8E23', + \ 'olivedrab' : '#6B8E23', + \ 'olivedrab1' : '#C0FF3E', + \ 'olivedrab2' : '#B3EE3A', + \ 'olivedrab3' : '#9ACD32', + \ 'olivedrab4' : '#698B22', + \ 'orange red' : '#FF4500', + \ 'orange' : '#FFA500', + \ 'orange1' : '#FFA500', + \ 'orange2' : '#EE9A00', + \ 'orange3' : '#CD8500', + \ 'orange4' : '#8B5A00', + \ 'orangered' : '#FF4500', + \ 'orangered1' : '#FF4500', + \ 'orangered2' : '#EE4000', + \ 'orangered3' : '#CD3700', + \ 'orangered4' : '#8B2500', + \ 'orchid' : '#DA70D6', + \ 'orchid1' : '#FF83FA', + \ 'orchid2' : '#EE7AE9', + \ 'orchid3' : '#CD69C9', + \ 'orchid4' : '#8B4789', + \ 'pale goldenrod' : '#EEE8AA', + \ 'pale green' : '#98FB98', + \ 'pale turquoise' : '#AFEEEE', + \ 'pale violet red' : '#DB7093', + \ 'palegoldenrod' : '#EEE8AA', + \ 'palegreen' : '#98FB98', + \ 'palegreen1' : '#9AFF9A', + \ 'palegreen2' : '#90EE90', + \ 'palegreen3' : '#7CCD7C', + \ 'palegreen4' : '#548B54', + \ 'paleturquoise' : '#AFEEEE', + \ 'paleturquoise1' : '#BBFFFF', + \ 'paleturquoise2' : '#AEEEEE', + \ 'paleturquoise3' : '#96CDCD', + \ 'paleturquoise4' : '#668B8B', + \ 'palevioletred' : '#DB7093', + \ 'palevioletred1' : '#FF82AB', + \ 'palevioletred2' : '#EE799F', + \ 'palevioletred3' : '#CD6889', + \ 'palevioletred4' : '#8B475D', + \ 'papaya whip' : '#FFEFD5', + \ 'papayawhip' : '#FFEFD5', + \ 'peach puff' : '#FFDAB9', + \ 'peachpuff' : '#FFDAB9', + \ 'peachpuff1' : '#FFDAB9', + \ 'peachpuff2' : '#EECBAD', + \ 'peachpuff3' : '#CDAF95', + \ 'peachpuff4' : '#8B7765', + \ 'peru' : '#CD853F', + \ 'pink' : '#FFC0CB', + \ 'pink1' : '#FFB5C5', + \ 'pink2' : '#EEA9B8', + \ 'pink3' : '#CD919E', + \ 'pink4' : '#8B636C', + \ 'plum' : '#DDA0DD', + \ 'plum1' : '#FFBBFF', + \ 'plum2' : '#EEAEEE', + \ 'plum3' : '#CD96CD', + \ 'plum4' : '#8B668B', + \ 'powder blue' : '#B0E0E6', + \ 'powderblue' : '#B0E0E6', + \ 'purple' : '#A020F0', + \ 'purple1' : '#9B30FF', + \ 'purple2' : '#912CEE', + \ 'purple3' : '#7D26CD', + \ 'purple4' : '#551A8B', + \ 'red' : '#FF0000', + \ 'red1' : '#FF0000', + \ 'red2' : '#EE0000', + \ 'red3' : '#CD0000', + \ 'red4' : '#8B0000', + \ 'rosy brown' : '#BC8F8F', + \ 'rosybrown' : '#BC8F8F', + \ 'rosybrown1' : '#FFC1C1', + \ 'rosybrown2' : '#EEB4B4', + \ 'rosybrown3' : '#CD9B9B', + \ 'rosybrown4' : '#8B6969', + \ 'royal blue' : '#4169E1', + \ 'royalblue' : '#4169E1', + \ 'royalblue1' : '#4876FF', + \ 'royalblue2' : '#436EEE', + \ 'royalblue3' : '#3A5FCD', + \ 'royalblue4' : '#27408B', + \ 'saddle brown' : '#8B4513', + \ 'saddlebrown' : '#8B4513', + \ 'salmon' : '#FA8072', + \ 'salmon1' : '#FF8C69', + \ 'salmon2' : '#EE8262', + \ 'salmon3' : '#CD7054', + \ 'salmon4' : '#8B4C39', + \ 'sandy brown' : '#F4A460', + \ 'sandybrown' : '#F4A460', + \ 'sea green' : '#2E8B57', + \ 'seagreen' : '#2E8B57', + \ 'seagreen1' : '#54FF9F', + \ 'seagreen2' : '#4EEE94', + \ 'seagreen3' : '#43CD80', + \ 'seagreen4' : '#2E8B57', + \ 'seashell' : '#FFF5EE', + \ 'seashell1' : '#FFF5EE', + \ 'seashell2' : '#EEE5DE', + \ 'seashell3' : '#CDC5BF', + \ 'seashell4' : '#8B8682', + \ 'sienna' : '#A0522D', + \ 'sienna1' : '#FF8247', + \ 'sienna2' : '#EE7942', + \ 'sienna3' : '#CD6839', + \ 'sienna4' : '#8B4726', + \ 'sky blue' : '#87CEEB', + \ 'skyblue' : '#87CEEB', + \ 'skyblue1' : '#87CEFF', + \ 'skyblue2' : '#7EC0EE', + \ 'skyblue3' : '#6CA6CD', + \ 'skyblue4' : '#4A708B', + \ 'slate blue' : '#6A5ACD', + \ 'slate gray' : '#708090', + \ 'slate grey' : '#708090', + \ 'slateblue' : '#6A5ACD', + \ 'slateblue1' : '#836FFF', + \ 'slateblue2' : '#7A67EE', + \ 'slateblue3' : '#6959CD', + \ 'slateblue4' : '#473C8B', + \ 'slategray' : '#708090', + \ 'slategray1' : '#C6E2FF', + \ 'slategray2' : '#B9D3EE', + \ 'slategray3' : '#9FB6CD', + \ 'slategray4' : '#6C7B8B', + \ 'slategrey' : '#708090', + \ 'snow' : '#FFFAFA', + \ 'snow1' : '#FFFAFA', + \ 'snow2' : '#EEE9E9', + \ 'snow3' : '#CDC9C9', + \ 'snow4' : '#8B8989', + \ 'spring green' : '#00FF7F', + \ 'springgreen' : '#00FF7F', + \ 'springgreen1' : '#00FF7F', + \ 'springgreen2' : '#00EE76', + \ 'springgreen3' : '#00CD66', + \ 'springgreen4' : '#008B45', + \ 'steel blue' : '#4682B4', + \ 'steelblue' : '#4682B4', + \ 'steelblue1' : '#63B8FF', + \ 'steelblue2' : '#5CACEE', + \ 'steelblue3' : '#4F94CD', + \ 'steelblue4' : '#36648B', + \ 'tan' : '#D2B48C', + \ 'tan1' : '#FFA54F', + \ 'tan2' : '#EE9A49', + \ 'tan3' : '#CD853F', + \ 'tan4' : '#8B5A2B', + \ 'thistle' : '#D8BFD8', + \ 'thistle1' : '#FFE1FF', + \ 'thistle2' : '#EED2EE', + \ 'thistle3' : '#CDB5CD', + \ 'thistle4' : '#8B7B8B', + \ 'tomato' : '#FF6347', + \ 'tomato1' : '#FF6347', + \ 'tomato2' : '#EE5C42', + \ 'tomato3' : '#CD4F39', + \ 'tomato4' : '#8B3626', + \ 'turquoise' : '#40E0D0', + \ 'turquoise1' : '#00F5FF', + \ 'turquoise2' : '#00E5EE', + \ 'turquoise3' : '#00C5CD', + \ 'turquoise4' : '#00868B', + \ 'violet red' : '#D02090', + \ 'violet' : '#EE82EE', + \ 'violetred' : '#D02090', + \ 'violetred1' : '#FF3E96', + \ 'violetred2' : '#EE3A8C', + \ 'violetred3' : '#CD3278', + \ 'violetred4' : '#8B2252', + \ 'wheat' : '#F5DEB3', + \ 'wheat1' : '#FFE7BA', + \ 'wheat2' : '#EED8AE', + \ 'wheat3' : '#CDBA96', + \ 'wheat4' : '#8B7E66', + \ 'white smoke' : '#F5F5F5', + \ 'white' : '#FFFFFF', + \ 'whitesmoke' : '#F5F5F5', + \ 'yellow green' : '#9ACD32', + \ 'yellow' : '#FFFF00', + \ 'yellow1' : '#FFFF00', + \ 'yellow2' : '#EEEE00', + \ 'yellow3' : '#CDCD00', + \ 'yellow4' : '#8B8B00', + \ 'yellowgreen' : '#9ACD32', + \} + + if has_key(l:color_list, l:color_name) + let l:hex_code = l:color_list[l:color_name] + endif + + return l:hex_code +endfunction diff --git a/bundle/indent-guides/autoload/indent_guides.vim b/bundle/indent-guides/autoload/indent_guides.vim new file mode 100755 index 0000000..53d4ff9 --- /dev/null +++ b/bundle/indent-guides/autoload/indent_guides.vim @@ -0,0 +1,284 @@ +" Author: Nate Kane +" Homepage: http://github.com/nathanaelkane/vim-indent-guides + +" +" Toggles the indent guides on and off. +" +function! indent_guides#toggle() + call indent_guides#init_matches() + + if empty(w:indent_guides_matches) + call indent_guides#enable() + else + call indent_guides#disable() + endif +endfunction + +" +" Called from autocmds, keeps indent guides enabled or disabled when entering +" other buffers and windows. +" +function! indent_guides#process_autocmds() + if g:indent_guides_autocmds_enabled + call indent_guides#enable() + else + call indent_guides#disable() + end +endfunction + +" +" Enables the indent guides for the current buffer and any other buffer upon +" entering it. +" +function! indent_guides#enable() + let g:indent_guides_autocmds_enabled = 1 + + if &diff || indent_guides#exclude_filetype() + call indent_guides#clear_matches() + return + end + + call indent_guides#init_script_vars() + call indent_guides#highlight_colors() + call indent_guides#clear_matches() + + " loop through each indent level and define a highlight pattern + " will automagically figure out whether to use tabs or spaces + for l:level in range(s:start_level, s:indent_levels) + let l:group = 'IndentGuides' . ((l:level % 2 == 0) ? 'Even' : 'Odd') + let l:column_start = (l:level - 1) * s:indent_size + 1 + let l:soft_pattern = indent_guides#indent_highlight_pattern(g:indent_guides_soft_pattern, l:column_start, s:guide_size) + let l:hard_pattern = indent_guides#indent_highlight_pattern('\t', l:column_start, s:indent_size) + + " define the higlight patterns and add to matches list + if g:indent_guides_space_guides + call add(w:indent_guides_matches, matchadd(l:group, l:soft_pattern)) + end + call add(w:indent_guides_matches, matchadd(l:group, l:hard_pattern)) + endfor +endfunction + +" +" Disables the indent guides for the current buffer and any other buffer upon +" entering it. +" +function! indent_guides#disable() + let g:indent_guides_autocmds_enabled = 0 + call indent_guides#clear_matches() +endfunction + +" +" Clear all highlight matches for the current window. +" +function! indent_guides#clear_matches() + call indent_guides#init_matches() + if !empty(w:indent_guides_matches) + let l:index = 0 + for l:match_id in w:indent_guides_matches + try + call matchdelete(l:match_id) + catch /E803:/ + " Do nothing + endtry + call remove(w:indent_guides_matches, l:index) + let l:index += l:index + endfor + endif +endfunction + +" +" Automagically calculates and defines the indent highlight colors. +" +function! indent_guides#highlight_colors() + if s:auto_colors + if has('gui_running') + call indent_guides#gui_highlight_colors() + else + call indent_guides#basic_highlight_colors() + endif + endif +endfunction + +" +" Defines some basic indent highlight colors that work for Terminal Vim and +" gVim when colors can't be automatically calculated. +" +function! indent_guides#basic_highlight_colors() + let l:cterm_colors = (&g:background == 'dark') ? ['darkgrey', 'black'] : ['lightgrey', 'white'] + let l:gui_colors = (&g:background == 'dark') ? ['grey15', 'grey30'] : ['grey70', 'grey85'] + + exe 'hi IndentGuidesEven guibg=' . l:gui_colors[0] . ' guifg=' . l:gui_colors[1] . ' ctermbg=' . l:cterm_colors[0] . ' ctermfg=' . l:cterm_colors[1] + exe 'hi IndentGuidesOdd guibg=' . l:gui_colors[1] . ' guifg=' . l:gui_colors[0] . ' ctermbg=' . l:cterm_colors[1] . ' ctermfg=' . l:cterm_colors[0] +endfunction + +" +" Automagically calculates and defines the indent highlight colors for gui +" vim. +" +function! indent_guides#gui_highlight_colors() + let l:hi_normal_guibg = '' + + " capture the backgroud color from the normal highlight + if s:hi_normal =~ s:color_hex_bg_pat + " hex color code is being used, eg. '#FFFFFF' + let l:hi_normal_guibg = matchstr(s:hi_normal, s:color_hex_bg_pat) + + elseif s:hi_normal =~ s:color_name_bg_pat + " color name is being used, eg. 'white' + let l:color_name = matchstr(s:hi_normal, s:color_name_bg_pat) + let l:hi_normal_guibg = color_helper#color_name_to_hex(l:color_name) + + else + " background color could not be detected, default to basic colors + call indent_guides#basic_highlight_colors() + endif + + if l:hi_normal_guibg =~ s:color_hex_pat + " calculate the highlight background colors + let l:hi_odd_bg = indent_guides#lighten_or_darken_color(l:hi_normal_guibg) + let l:hi_even_bg = indent_guides#lighten_or_darken_color(l:hi_odd_bg) + + " define the new highlights + exe 'hi IndentGuidesOdd guibg=' . l:hi_odd_bg . ' guifg=' . l:hi_even_bg + exe 'hi IndentGuidesEven guibg=' . l:hi_even_bg . ' guifg=' . l:hi_odd_bg + end +endfunction + +" +" Takes a color and darkens or lightens it depending on whether a dark or light +" colorscheme is being used. +" +function! indent_guides#lighten_or_darken_color(color) + let l:new_color = '' + + if (&g:background == 'dark') + let l:new_color = color_helper#hex_color_lighten(a:color, s:change_percent) + else + let l:new_color = color_helper#hex_color_darken (a:color, s:change_percent) + endif + + return l:new_color +endfunction + +" +" Define default highlights. +" +function! indent_guides#define_default_highlights() + hi default clear IndentGuidesOdd + hi default clear IndentGuidesEven +endfunction + +" +" Init the w:indent_guides_matches variable. +" +function! indent_guides#init_matches() + let w:indent_guides_matches = exists('w:indent_guides_matches') ? w:indent_guides_matches : [] +endfunction + +" +" We need to initialize these vars every time a buffer is entered while the +" plugin is enabled. +" +function! indent_guides#init_script_vars() + if &l:shiftwidth > 0 && &l:expandtab + let s:indent_size = &l:shiftwidth + else + let s:indent_size = &l:tabstop + endif + let s:guide_size = indent_guides#calculate_guide_size() + let s:hi_normal = indent_guides#capture_highlight('Normal') + + " remove 'font=' from the s:hi_normal string (only seems to happen on Vim startup in Windows) + let s:hi_normal = substitute(s:hi_normal, ' font=[A-Za-z0-9:]\+', "", "") + + " shortcuts to the global variables - this makes the code easier to read + let s:debug = g:indent_guides_debug + let s:indent_levels = g:indent_guides_indent_levels + let s:auto_colors = g:indent_guides_auto_colors + let s:color_hex_pat = g:indent_guides_color_hex_pattern + let s:color_hex_bg_pat = g:indent_guides_color_hex_guibg_pattern + let s:color_name_bg_pat = g:indent_guides_color_name_guibg_pattern + let s:start_level = g:indent_guides_start_level + + " str2float not available in vim versions <= 7.1 + if has('float') + let s:change_percent = g:indent_guides_color_change_percent / str2float('100.0') + else + let s:change_percent = g:indent_guides_color_change_percent / 100.0 + endif + + if s:debug + echo 's:indent_size = ' . s:indent_size + echo 's:guide_size = ' . s:guide_size + echo 's:hi_normal = ' . s:hi_normal + echo 's:indent_levels = ' . s:indent_levels + echo 's:auto_colors = ' . s:auto_colors + echo 's:change_percent = ' . string(s:change_percent) + echo 's:color_hex_pat = ' . s:color_hex_pat + echo 's:color_hex_bg_pat = ' . s:color_hex_bg_pat + echo 's:color_name_bg_pat = ' . s:color_name_bg_pat + echo 's:start_level = ' . s:start_level + endif +endfunction + +" +" Calculate the indent guide size. Ensures the guide size is less than or +" equal to the actual indent size, otherwise some weird things can occur. +" +" NOTE: Currently, this only works when soft-tabs are being used. +" +function! indent_guides#calculate_guide_size() + let l:guide_size = g:indent_guides_guide_size + + if l:guide_size == 0 || l:guide_size > s:indent_size + let l:guide_size = s:indent_size + endif + + return l:guide_size +endfunction + +" +" Captures and returns the output of highlight group definitions. +" +" Example: indent_guides#capture_highlight('normal') +" Returns: 'Normal xxx guifg=#323232 guibg=#ffffff' +" +function! indent_guides#capture_highlight(group_name) + redir => l:output + exe "silent hi " . a:group_name + redir END + + let l:output = substitute(l:output, "\n", "", "") + return l:output +endfunction + +" +" Returns a regex pattern for highlighting an indent level. +" +" Example: indent_guides#indent_highlight_pattern(' ', 1, 4) +" Returns: /^ *\%1v\zs *\%5v\ze/ +" +" Example: indent_guides#indent_highlight_pattern('\s', 5, 2) +" Returns: /^\s*\%5v\zs\s*\%7v\ze/ +" +" Example: indent_guides#indent_highlight_pattern('\t', 9, 2) +" Returns: /^\t*\%9v\zs\t*\%11v\ze/ +" +function! indent_guides#indent_highlight_pattern(indent_pattern, column_start, indent_size) + let l:pattern = '^' . a:indent_pattern . '*\%' . a:column_start . 'v\zs' + let l:pattern .= a:indent_pattern . '*\%' . (a:column_start + a:indent_size) . 'v' + let l:pattern .= '\ze' + return l:pattern +endfunction + +" +" Detect if any of the buffer filetypes should be excluded. +" +function! indent_guides#exclude_filetype() + for ft in split(&ft, '\.') + if index(g:indent_guides_exclude_filetypes, ft) > -1 + return 1 + end + endfor + return 0 +endfunction diff --git a/bundle/indent-guides/doc/indent_guides.txt b/bundle/indent-guides/doc/indent_guides.txt new file mode 100755 index 0000000..fe50cb8 --- /dev/null +++ b/bundle/indent-guides/doc/indent_guides.txt @@ -0,0 +1,340 @@ +*indent_guides.txt* A plugin for visually displaying indent levels in Vim. + + *indent-guides* + ____ __ __ ______ _ __ + / _/____ ____/ /___ ____ / /_ / ____/__ __(_)____/ /___ _____ + / / / __ \/ __ // _ \/ __ \/ __/ / / __ / / / / // __ // _ \/ ___/ + _/ / / / / / /_/ // __/ / / / /_ / /_/ // /_/ / // /_/ // __(__ ) + /___//_/ /_/\__,_/ \___/_/ /_/\__/ \____/ \__,_/_/ \__,_/ \___/____/ + + +Author: Nate Kane +Version: 1.7 +Last Change: 07 Mar 2013 + +============================================================================== +CONTENTS *indent-guides-contents* + + 1. Introduction.......................... |indent-guides-introduction| + 2. Commands.............................. |indent-guides-commands| + 3. Options............................... |indent-guides-options| + 4. Mappings.............................. |indent-guides-mappings| + 5. Terminal Vim.......................... |indent-guides-terminal-vim| + 6. About................................. |indent-guides-about| + 7. Changelog............................. |indent-guides-changelog| + 8. License............................... |indent-guides-license| + +============================================================================== +1. INTRODUCTION *indent-guides-introduction* + +Indent Guides is a plugin for visually displaying indent levels in Vim. + +This plugin should work with gVim out of the box, no configuration needed. + +Features:~ + * Can detect both tab and space indent styles. + * Automatically inspects your colorscheme and picks appropriate colors (gVim + only). + * Will highlight indent levels with alternating colors. + * Full support for gVim and basic support for Terminal Vim. + * Seems to work on Windows gVim 7.3 (haven't done any extensive tests + though). + * Customizable size for indent guides, eg. skinny guides (soft-tabs only). + * Customizable start indent level. + * Highlight support for files with a mixture of tab and space indent styles. + +============================================================================== +2. COMMANDS *indent-guides-commands* + +------------------------------------------------------------------------------ +:IndentGuidesToggle *:IndentGuidesToggle* + Toggles the indent guides on and off. + +------------------------------------------------------------------------------ +:IndentGuidesEnable *:IndentGuidesEnable* + Enables the indent guides for the current buffer and any other buffer upon + entering it. + +------------------------------------------------------------------------------ +:IndentGuidesDisable *:IndentGuidesDisable* + Disables the indent guides for the current buffer and any other buffer upon + entering it. + +============================================================================== +3. OPTIONS *indent-guides-options* + +------------------------------------------------------------------------------ + *'indent_guides_indent_levels'* +Use this option to control how many indent levels to display guides for. + +Default: 30. Values: integer. +> + let g:indent_guides_indent_levels = 30 +< + +------------------------------------------------------------------------------ + *'indent_guides_auto_colors'* +Use this option to control whether or not the plugin automatically calculates +the highlight colors. Will use the current colorscheme's background color as a +base color. + +Default: 1. Values: 0 or 1. +> + let g:indent_guides_auto_colors = 1 +< + +If you set this option to 0, be sure to manually define some highlight colors +in an autocmd. +> + let g:indent_guides_auto_colors = 0 + autocmd VimEnter,Colorscheme * :hi IndentGuidesOdd guibg=red ctermbg=3 + autocmd VimEnter,Colorscheme * :hi IndentGuidesEven guibg=green ctermbg=4 +< + +Alternatively you can add the following lines to your colorscheme file. +> + hi IndentGuidesOdd guibg=red ctermbg=3 + hi IndentGuidesEven guibg=green ctermbg=4 +< + +------------------------------------------------------------------------------ + *'indent_guides_color_change_percent'* +Use this option to control the percent at which the highlight colors will be +lightened or darkened. + +Default: 10 (10%). Values: between 0 and 100. +> + let g:indent_guides_color_change_percent = 10 +< + +------------------------------------------------------------------------------ + *'indent_guides_guide_size'* +Use this option to customize the size of the indent guide. By default the +value is set to 0, which will set the guide size to be the same as the +|shiftwidth|. Setting this value to be larger than the |shiftwidth| is essentially +the same as setting it to 0. + +A common use of this setting is to create skinny indent guides, which look +great with a |shiftwidth| of 4 or more. + +NOTE: This option only works for soft-tabs (spaces) and not hard-tabs. + +Default: 0. Values: between 0 and |shiftwidth|. +> + let g:indent_guides_guide_size = 1 +< + +------------------------------------------------------------------------------ + *'indent_guides_start_level'* +Use this option to control which indent level to start showing guides from. + +Default: 1. Values: between 1 and g:|indent_guides_indent_levels|. +> + let g:indent_guides_start_level = 2 +< + +------------------------------------------------------------------------------ + *'indent_guides_space_guides'* +Use this option to control whether the plugin considers spaces as indention. + +Default: 1. Values: 0 or 1. +> + let g:indent_guides_space_guides = 0 +< + +------------------------------------------------------------------------------ + *'indent_guides_soft_pattern'* +Use this option to explicitly specify a pattern for soft indentation. For +example to match spaces only in the beginning of line use ' ' pattern. + +Default: '\s'. Values: Vim regexp. +> + let g:indent_guides_soft_pattern = ' ' +< + +------------------------------------------------------------------------------ + *'indent_guides_enable_on_vim_startup'* +Use this option to control whether the plugin is enabled on Vim startup. + +Default: 0. Values: 0 or 1. +> + let g:indent_guides_enable_on_vim_startup = 0 +< + +------------------------------------------------------------------------------ + *'indent_guides_exclude_filetypes'* +Use this option to specify a list of filetypes to disable the plugin for. + +Default: ['help']. Values: list of strings. +> + let g:indent_guides_exclude_filetypes = ['help', 'nerdtree'] +< + +------------------------------------------------------------------------------ + *'indent_guides_default_mapping'* +Use this option to control whether the default mapping (ig) gets set. + +Default: 1. Values: 0 or 1. +> + let g:indent_guides_default_mapping = 0 +< + +============================================================================== +4. MAPPINGS *indent-guides-mappings* + +The default mapping for toggling indent guides is ig. You can easily +map it to other keys. For example: +> + :nmap ig IndentGuidesToggle +< + +You can also map some other commands that are not mapped by default. For +example: +> + :nmap ie IndentGuidesEnable + :nmap id IndentGuidesDisable +< + +============================================================================== +5. TERMINAL VIM *indent-guides-terminal-vim* + +At the moment Terminal Vim only has basic support. This means is that colors +won't be automatically calculated based on your colorscheme. Instead, some +preset colors are used depending on whether `background` is set to `dark` or +`light`. + +When `set background=dark` is used, the following highlight colors will be +defined: +> + hi IndentGuidesOdd ctermbg=black + hi IndentGuidesEven ctermbg=darkgrey +< + +Alternatively, when `set background=light` is used, the following highlight +colors will be defined: +> + hi IndentGuidesOdd ctermbg=white + hi IndentGuidesEven ctermbg=lightgrey +< + +If for some reason it's incorrectly defining light highlight colors instead of +dark ones or vice versa, the first thing you should check is that the +`background` value is being set correctly for your colorscheme. Sometimes it's +best to manually set the `background` value in your `.vimrc`, for example: +> + colorscheme desert256 + set background=dark +< + +Alternatively you can manually setup the highlight colors yourself, see +|indent_guides_auto_colors| for an example. + +============================================================================== +6. ABOUT *indent-guides-about* + +Why did I build this plugin?~ + * I believe indent guides make nested code easier to read and understand. + * Other editors have them and it's high time Vim did. + * None of the existing indent guide plugins on the market suited my needs. + * I wanted to learn me some VimL. + +Links:~ + * Github: https://github.com/nathanaelkane/vim-indent-guides + * Bugs & Issues: https://github.com/nathanaelkane/vim-indent-guides/issues + +Credits:~ + * Matt Wozniski (godlygeek) for letting me use the list of color names and + hex codes from his CSApprox plugin. + +Contact:~ + * Twitter: @nathanaelkane + * Email: + +Bug reports, feedback, suggestions etc are welcomed. + +============================================================================== +7. CHANGELOG *indent-guides-changelog* + +1.8 (pending release)~ + * Added option g:|indent_guides_soft_pattern| to control the pattern for + soft indentation (thanks @sergey-vlasov). + * Added option g:|indent_guides_default_mapping| to control whether the + default mapping (ig) gets set (thanks @suy). + * Set size of indent guide to `tabstop` value when `shiftwidth=0` or + `noexpandtab` is used (thanks @darkfeline and @wilywampa). + * Don't load plugin in unsupported versions of Vim (thanks @dersaidin). + +1.7~ + * Added way to override the default mapping (thanks @xuhdev). + * Added option g:|indent_guides_exclude_filetypes| to specify a list of + filetypes to disable the plugin for. + * Disable the plugin when in a diff. + * Various bug fixes. + +1.6~ + * Added option g:|indent_guides_space_guides| to control whether spaces are + considered as indention (thanks @scoz). + * Added 'doc/tags' to gitignore (thanks @lenniboy). + * Fixed E803 ID not found spam (thanks @mutewinter). + * Fixed str2float issue with Vim 7.1 (thanks @acx0). + +1.5~ + * Added highlight support for files with a mixture of tab and space indent + styles (thanks @graywh). + * Added -bar to all the :commands so they can chain with other :commands + (thanks @graywh). + * No longer overriding pre-defined custom highlight colors (thanks @graywh). + * Using str2float to work around a float bug in some versions of Vim 7.2 + (thanks @voidus). + +1.4~ + * Added the new plugin option g:|indent_guides_enable_on_vim_startup|. + * Improved Windows support. + +1.3~ + * Changed the default value of g:|indent_guides_color_change_percent| to 10. + * Added support for gVim themes that don't specify a `hi Normal guibg` + color. + +1.2~ + * Customizable size for indent guides, eg. skinny guides (soft-tabs only). + * Customizable start indent level. + * Refactored some internal logic. + +1.1~ + * Added basic support for Terminal Vim. See |indent-guides-terminal-vim| for + more information. + * Cut down on rgb to hex color conversions by adding a big dictionary of + color names and hex codes. + * Various bug fixes. + +1.0~ + * First public version. + +============================================================================== +8. LICENSE *indent-guides-license* + +The MIT Licence +http://www.opensource.org/licenses/mit-license.php + +Copyright (c) 2010-2013 Nate Kane + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. + +vim:tw=78:ts=2:ft=help:norl: diff --git a/bundle/indent-guides/plugin/indent_guides.vim b/bundle/indent-guides/plugin/indent_guides.vim new file mode 100755 index 0000000..8a6dee3 --- /dev/null +++ b/bundle/indent-guides/plugin/indent_guides.vim @@ -0,0 +1,91 @@ +" Author: Nate Kane +" Homepage: http://github.com/nathanaelkane/vim-indent-guides + +" Do not load if vim is too old +if (v:version == 701 && !exists('*matchadd')) || (v:version < 701) + finish +endif + +if exists('g:loaded_indent_guides') || &cp + finish +endif +let g:loaded_indent_guides = 1 +call indent_guides#define_default_highlights() + +function! s:IndentGuidesToggle() + call indent_guides#toggle() +endfunction + +function! s:IndentGuidesEnable() + call indent_guides#enable() +endfunction + +function! s:IndentGuidesDisable() + call indent_guides#disable() +endfunction + +" Commands +command! -bar IndentGuidesToggle call s:IndentGuidesToggle() +command! -bar IndentGuidesEnable call s:IndentGuidesEnable() +command! -bar IndentGuidesDisable call s:IndentGuidesDisable() + +" +" Initializes a given variable to a given value. The variable is only +" initialized if it does not exist prior. +" +function s:InitVariable(var, value) + if !exists(a:var) + if type(a:value) == type("") + exec 'let ' . a:var . ' = ' . "'" . a:value . "'" + else + exec 'let ' . a:var . ' = ' . a:value + endif + endif +endfunction + +" Fixed global variables +let g:indent_guides_autocmds_enabled = 0 +let g:indent_guides_color_hex_pattern = '#[0-9A-Fa-f]\{6\}' +let g:indent_guides_color_hex_guibg_pattern = 'guibg=\zs' . g:indent_guides_color_hex_pattern . '\ze' +let g:indent_guides_color_name_guibg_pattern = "guibg='\\?\\zs[0-9A-Za-z ]\\+\\ze'\\?" + +" Configurable global variables +call s:InitVariable('g:indent_guides_indent_levels', 30) +call s:InitVariable('g:indent_guides_auto_colors', 1) +call s:InitVariable('g:indent_guides_color_change_percent', 10) " ie. 10% +call s:InitVariable('g:indent_guides_guide_size', 0) +call s:InitVariable('g:indent_guides_start_level', 1) +call s:InitVariable('g:indent_guides_enable_on_vim_startup', 0) +call s:InitVariable('g:indent_guides_debug', 0) +call s:InitVariable('g:indent_guides_space_guides', 1) +call s:InitVariable('g:indent_guides_soft_pattern', '\s') +call s:InitVariable('g:indent_guides_default_mapping', 1) + +if !exists('g:indent_guides_exclude_filetypes') + let g:indent_guides_exclude_filetypes = ['help'] +endif + +" Default mapping +if !hasmapto('IndentGuidesToggle', 'n') && maparg('ig', 'n') == '' + \ && g:indent_guides_default_mapping != 0 + nmap ig IndentGuidesToggle +endif + +" Plug mappings +nnoremap +me=s-1 keepend +\ contains=mustacheInside,@htmlMustacheContainer,htmlTag,htmlEndTag,htmlTagName,htmlSpecialChar + +let b:current_syntax = "mustache" +delcommand HtmlHiLink From 28cf88434f83a8263d1fed68ef7a3156fefa8f7d Mon Sep 17 00:00:00 2001 From: Thomas Hunter II Date: Tue, 27 Dec 2016 14:53:33 -0800 Subject: [PATCH 25/96] Jenkinsfile, Dockerfile support --- bundle/Dockerfile/LICENSE | 20 + bundle/Dockerfile/Makefile | 15 + bundle/Dockerfile/README.md | 47 ++ bundle/Dockerfile/ftdetect/Dockerfile.vim | 5 + bundle/Dockerfile/ftdetect/docker-compose.vim | 4 + bundle/Dockerfile/ftplugin/Dockerfile.vim | 27 ++ bundle/Dockerfile/indent/Dockerfile.vim | 23 + .../Dockerfile/snippets/Dockerfile.snippets | 66 +++ .../snippets/docker-compose.snippets | 163 +++++++ bundle/Dockerfile/syntax/Dockerfile.vim | 64 +++ bundle/Dockerfile/syntax/docker-compose.vim | 74 +++ bundle/Dockerfile/vim-dockerfile-example.png | Bin 0 -> 57722 bytes bundle/groovy/syntax/groovy.vim | 450 ++++++++++++++++++ vimrc | 9 + 14 files changed, 967 insertions(+) create mode 100644 bundle/Dockerfile/LICENSE create mode 100644 bundle/Dockerfile/Makefile create mode 100644 bundle/Dockerfile/README.md create mode 100644 bundle/Dockerfile/ftdetect/Dockerfile.vim create mode 100644 bundle/Dockerfile/ftdetect/docker-compose.vim create mode 100644 bundle/Dockerfile/ftplugin/Dockerfile.vim create mode 100644 bundle/Dockerfile/indent/Dockerfile.vim create mode 100644 bundle/Dockerfile/snippets/Dockerfile.snippets create mode 100644 bundle/Dockerfile/snippets/docker-compose.snippets create mode 100644 bundle/Dockerfile/syntax/Dockerfile.vim create mode 100644 bundle/Dockerfile/syntax/docker-compose.vim create mode 100644 bundle/Dockerfile/vim-dockerfile-example.png create mode 100644 bundle/groovy/syntax/groovy.vim diff --git a/bundle/Dockerfile/LICENSE b/bundle/Dockerfile/LICENSE new file mode 100644 index 0000000..27856ca --- /dev/null +++ b/bundle/Dockerfile/LICENSE @@ -0,0 +1,20 @@ +The MIT License (MIT) + +Copyright (c) 2013 Eugene Kalinin + +Permission is hereby granted, free of charge, to any person obtaining a copy of +this software and associated documentation files (the "Software"), to deal in +the Software without restriction, including without limitation the rights to +use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of +the Software, and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS +FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR +COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER +IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/bundle/Dockerfile/Makefile b/bundle/Dockerfile/Makefile new file mode 100644 index 0000000..a7c1fdf --- /dev/null +++ b/bundle/Dockerfile/Makefile @@ -0,0 +1,15 @@ +install: + @echo "Installation:" + @mkdir -p ~/.vim/syntax + @mkdir -p ~/.vim/ftdetect + @mkdir -p ~/.vim/snippets + @echo " * Dirs ... success." + @cp ./syntax/Dockerfile.vim ~/.vim/syntax/ + @cp ./syntax/docker-compose.vim ~/.vim/syntax/ + @echo " * Syntax ... success." + @cp ./ftdetect/Dockerfile.vim ~/.vim/ftdetect/ + @cp ./ftdetect/docker-compose.vim ~/.vim/ftdetect/ + @echo " * Filetype ... success." + @cp ./snippets/Dockerfile.snippets ~/.vim/snippets/ + @cp ./snippets/docker-compose.snippets ~/.vim/snippets/ + @echo " * Snippets ... success." diff --git a/bundle/Dockerfile/README.md b/bundle/Dockerfile/README.md new file mode 100644 index 0000000..d97461a --- /dev/null +++ b/bundle/Dockerfile/README.md @@ -0,0 +1,47 @@ +Dockerfile.vim +============== + +Vim syntax file for [Docker](http://docker.io/)'s [Dockerfile](http://docs.docker.com/reference/builder/) +and snippets for [snipMate](http://www.vim.org/scripts/script.php?script_id=2540). + +Screenshot +========== + +Here is an example in gnome-terminal with [vim-monokai](https://github.com/sickill/vim-monokai) color scheme: + + +![Vim & Dockerfile.vim ](https://raw.github.com/ekalinin/Dockerfile.vim/master/vim-dockerfile-example.png) + + + +Installation +============ + +```bash +$ git clone https://github.com/ekalinin/Dockerfile.vim.git +$ cd Dockerfile.vim +$ make install +``` + +####Or using Pathogen: +```bash +# Clone directly into the bundle folder. +git clone https://github.com/ekalinin/Dockerfile.vim.git bundle/Dockerfile +``` + +####Or using Vundle: +```bash +# near the top of your .vimrc +Plugin 'ekalinin/Dockerfile.vim' +``` + +####Or using NeoBundle: + +```bash +NeoBundle 'ekalinin/Dockerfile.vim' +``` + +License +======= + +See [LICENSE](https://github.com/ekalinin/Dockerfile.vim/blob/master/LICENSE) file. diff --git a/bundle/Dockerfile/ftdetect/Dockerfile.vim b/bundle/Dockerfile/ftdetect/Dockerfile.vim new file mode 100644 index 0000000..7293a26 --- /dev/null +++ b/bundle/Dockerfile/ftdetect/Dockerfile.vim @@ -0,0 +1,5 @@ +" Dockerfile +autocmd BufRead,BufNewFile Dockerfile set ft=Dockerfile +autocmd BufRead,BufNewFile Dockerfile* setf Dockerfile +autocmd BufRead,BufNewFile *.dock setf Dockerfile +autocmd BufRead,BufNewFile *.[Dd]ockerfile setf Dockerfile diff --git a/bundle/Dockerfile/ftdetect/docker-compose.vim b/bundle/Dockerfile/ftdetect/docker-compose.vim new file mode 100644 index 0000000..0214497 --- /dev/null +++ b/bundle/Dockerfile/ftdetect/docker-compose.vim @@ -0,0 +1,4 @@ +" docker-compose.yml +autocmd BufRead,BufNewFile docker-compose.yml set ft=docker-compose +autocmd BufRead,BufNewFile docker-compose.yml* setf docker-compose +autocmd BufRead,BufNewFile docker-compose* setf docker-compose diff --git a/bundle/Dockerfile/ftplugin/Dockerfile.vim b/bundle/Dockerfile/ftplugin/Dockerfile.vim new file mode 100644 index 0000000..ff6ab7b --- /dev/null +++ b/bundle/Dockerfile/ftplugin/Dockerfile.vim @@ -0,0 +1,27 @@ +function! DockerfileReplaceInstruction(original, replacement) + let syn = synIDtrans(synID(line("."), col(".") - 1, 0)) + if syn != hlID("Comment") && syn != hlID("Constant") && strlen(getline(".")) == 0 + let word = a:replacement + else + let word = a:original + endif + let g:UnduBuffer = a:original + return word +endfunction + +inoreabbr from =DockerfileReplaceInstruction("from", "FROM") +inoreabbr maintainer =DockerfileReplaceInstruction("maintainer", "MAINTAINER") +inoreabbr run =DockerfileReplaceInstruction("run", "RUN") +inoreabbr cmd =DockerfileReplaceInstruction("cmd", "CMD") +inoreabbr label =DockerfileReplaceInstruction("label", "LABEL") +inoreabbr expose =DockerfileReplaceInstruction("expose", "EXPOSE") +inoreabbr env =DockerfileReplaceInstruction("env", "ENV") +inoreabbr add =DockerfileReplaceInstruction("add", "ADD") +inoreabbr copy =DockerfileReplaceInstruction("copy", "COPY") +inoreabbr entrypoint =DockerfileReplaceInstruction("entrypoint", "ENTRYPOINT") +inoreabbr volume =DockerfileReplaceInstruction("volume", "VOLUME") +inoreabbr user =DockerfileReplaceInstruction("user", "USER") +inoreabbr workdir =DockerfileReplaceInstruction("workdir", "WORKDIR") +inoreabbr arg =DockerfileReplaceInstruction("arg", "ARG") +inoreabbr onbuild =DockerfileReplaceInstruction("onbuild", "ONBUILD") +inoreabbr stopsignal =DockerfileReplaceInstruction("stopsignal", "STOPSIGNAL") diff --git a/bundle/Dockerfile/indent/Dockerfile.vim b/bundle/Dockerfile/indent/Dockerfile.vim new file mode 100644 index 0000000..e7b5058 --- /dev/null +++ b/bundle/Dockerfile/indent/Dockerfile.vim @@ -0,0 +1,23 @@ +if exists('b:did_indent') | finish | endif +let b:did_indent = 1 + + +function! DockerfileIndent(line) + let prev_line = getline(a:line - 1) + if a:line > 1 && prev_line =~ '\\\s*$' + let i = indent(a:line - 1) + if i == 0 + let i += &l:shiftwidth + if &l:expandtab && prev_line =~# '^RUN\s' + " Overindent past RUN + let i = 4 + &l:shiftwidth + endif + endif + return i + endif + + return -1 +endfunction + + +set indentexpr=DockerfileIndent(v:lnum) diff --git a/bundle/Dockerfile/snippets/Dockerfile.snippets b/bundle/Dockerfile/snippets/Dockerfile.snippets new file mode 100644 index 0000000..5f97a51 --- /dev/null +++ b/bundle/Dockerfile/snippets/Dockerfile.snippets @@ -0,0 +1,66 @@ +snippet F + FROM ${1:ubuntu} +snippet f + FROM ${1:ubuntu} +snippet M + MAINTAINER ${1:name} +snippet m + MAINTAINER ${1:name} +snippet R + RUN ${1:command} +snippet r + RUN ${1:command} +snippet C + CMD ${1:command} +snippet c + CMD ${1:command} +snippet CP + COPY ${1:src} ${2:dest} +snippet cp + COPY ${1:src} ${2:dest} +snippet EXP + EXPOSE ${1:port} +snippet exp + EXPOSE ${1:port} +snippet E + ENV ${1:key} ${2:value} +snippet e + ENV ${1:key} ${2:value} +snippet A + ADD ${1:src} ${2:dst} +snippet a + ADD ${1:src} ${2:dst} +snippet ENT + ENTRYPOINT ${1:command} +snippet ent + ENTRYPOINT ${1:command} +snippet V + VOLUME ["${1:path}"] +snippet v + VOLUME ["${1:path}"] +snippet U + USER ${1:name} +snippet u + USER ${1:name} +snippet W + WORKDIR ${1:path} +snippet w + WORKDIR ${1:path} +snippet upd + # update packages + RUN echo "deb http://archive.ubuntu.com/ubuntu ${1:precise} main universe" > /etc/apt/sources.list; \ + apt-get update && apt-get -y upgrade; \ + ${2} +snippet head + # ${1:Description} + # + # VERSION ${2:0.1.0} + ${3} +snippet O + ONBUILD ${1} +snippet o + ONBUILD ${1} +snippet L + LABEL ${1:label}="${2:value}" +snippet l + LABEL ${1:label}="${2:value}" diff --git a/bundle/Dockerfile/snippets/docker-compose.snippets b/bundle/Dockerfile/snippets/docker-compose.snippets new file mode 100644 index 0000000..8cab91d --- /dev/null +++ b/bundle/Dockerfile/snippets/docker-compose.snippets @@ -0,0 +1,163 @@ +snippet ve + version: ${1:2} +snippet volumes + volumes: + - ${1:value} +snippet volume_ + volume_driver: ${1:driver} +snippet volumes_ + volumes_from: + - ${1:name} +snippet exter + external: ${1:boolean} +snippet ser + services: + ${1:name} +snippet bu + build: + ${1:value} +snippet conte + context: ${1:dir} +snippet com + command: ${1:command} +snippet dep + depends_on: + ${1:value} +snippet env + environment: + ${1:name}: ${2:value} +snippet doc + dockerfile: ${1:file} +snippet ar + args: + ${1:name}: ${2:value} +snippet cap_a + cap_add: + - ${1:value} +snippet cap_d + cap_drop: + - ${1:value} +snippet cgr + cgroup_parent: ${1:cgroup} +snippet conta + container_name: ${1:name} +snippet dev + devices: + - ${1:value} +snippet dn + dns: + - ${1:ip} +snippet dns_ + dns_search: + - ${1:ip} +snippet tm + tmpfs: + - ${1:dir} +snippet ent + entrypoint: ${1:command} +snippet env_ + env_file: + - ${1:file} +snippet exp + expose: + - ${1:port} +snippet exten + extends: + file: ${1:file} + service: ${2:name} +snippet exter + extra_hosts: + - ${1:host}:${2:ip} +snippet gr + group_add: + - ${1:name} +snippet im + image: ${1:image} +snippet la + labels: + ${1:dns}: ${2:label} +snippet links + links: + - ${1:name} +snippet logg + logging: + driver: ${1:driver} + options: + ${2:value} +snippet log_d + log_driver: ${1:driver} +snippet log_o + log_opt: + ${1:value} +snippet net + net: ${1:value} +snippet network_ + network_mode: ${1:value} +snippet networks + networks: + - ${1:value} +snippet al + networks: + - ${1:name} +snippet ipv4 + ipv4_address: ${1:ip} +snippet ipv6 + ipv6_address: ${1:ip} +snippet link_ + link_local_ips: + - ${1:ip} +snippet pi + pid: ${1:host} +snippet po + ports: + - ${1:value} +snippet sec + security_opt: + - ${1:value} +snippet sto + stop_signal: ${1:signal} +snippet ul + ulimits: + ${1:value} +snippet cpu_s + cpu_shares: ${1:value} +snippet cpu_q + cpu_quota: ${1:value} +snippet cpus + cpuset: ${1:value} +snippet dom + domainname: ${1:name} +snippet ho + hostname: ${1:name} +snippet ipc + ipc: ${1:host} +snippet mem_ + mem_limit: ${1:value} +snippet mems + memswap_limit: ${1:value} +snippet pr + privileged: ${1:boolean} +snippet oom + oom_score_adj: ${1:value} +snippet res + restart: ${1:value} +snippet us + user: ${1:value} +snippet wo + working_dir: ${1:dir} +snippet rea + read_only: ${1:boolean} +snippet sh + shm_size: ${1:value} +snippet std + stdin_open: ${1:boolean} +snippet tt + tty: ${1:boolean} +snippet driver + driver: ${1:value} +snippet driver_ + driver_opts: + ${1:key}: ${2:value} +snippet ipa + ipam: + ${1:value} diff --git a/bundle/Dockerfile/syntax/Dockerfile.vim b/bundle/Dockerfile/syntax/Dockerfile.vim new file mode 100644 index 0000000..f94e6a2 --- /dev/null +++ b/bundle/Dockerfile/syntax/Dockerfile.vim @@ -0,0 +1,64 @@ +" Vim syntax file +" Language: Dockerfile +" Maintainer: Eugene Kalinin +" Latest Revision: 11 September 2013 +" Source: http://docs.docker.io/en/latest/use/builder/ + +if exists("b:current_syntax") + finish +endif + +" case sensitivity (fix #17) +" syn case ignore + +" Keywords +syn keyword dockerfileKeywords FROM MAINTAINER RUN CMD COPY +syn keyword dockerfileKeywords EXPOSE ADD ENTRYPOINT +syn keyword dockerfileKeywords VOLUME USER WORKDIR ONBUILD +syn keyword dockerfileKeywords LABEL ARG HEALTHCHECK SHELL + +" Bash statements +setlocal iskeyword+=- +syn keyword bashStatement add-apt-repository adduser apk apt-get aptitude apt-key autoconf bundle +syn keyword bashStatement cd chgrp chmod chown clear complete composer cp curl du echo egrep +syn keyword bashStatement expr fgrep find gem gnufind gnugrep gpg grep groupadd head less ln +syn keyword bashStatement ls make mkdir mv node npm pacman pip pip3 php python rails rm rmdir rpm ruby +syn keyword bashStatement sed sleep sort strip tar tail tailf touch useradd virtualenv yum +syn keyword bashStatement usermod bash cat a2ensite a2dissite a2enmod a2dismod apache2ctl +syn keyword bashStatement wget gzip + +" Strings +syn region dockerfileString start=/"/ skip=/\\"/ end=/"/ +syn region dockerfileString1 start=/'/ skip=/\\'/ end=/'/ + +" Emails +syn region dockerfileEmail start=// contains=@ oneline + +" Urls +syn match dockerfileUrl /\(http\|https\|ssh\|hg\|git\)\:\/\/[a-zA-Z0-9\/\-\.]\+/ + +" Task tags +syn keyword dockerfileTodo contained TODO FIXME XXX + +" Comments +syn region dockerfileComment start="#" end="\n" contains=dockerfileTodo +syn region dockerfileEnvWithComment start="^\s*ENV\>" end="\n" contains=dockerfileEnv +syn match dockerfileEnv contained /\/ + +" Highlighting +hi link dockerfileKeywords Keyword +hi link dockerfileEnv Keyword +hi link dockerfileString String +hi link dockerfileString1 String +hi link dockerfileComment Comment +hi link dockerfileEmail Identifier +hi link dockerfileUrl Identifier +hi link dockerfileTodo Todo +hi link bashStatement Function + +let b:current_syntax = "dockerfile" + +set commentstring=#\ %s + +" Enable automatic comment insertion +setlocal fo+=cro diff --git a/bundle/Dockerfile/syntax/docker-compose.vim b/bundle/Dockerfile/syntax/docker-compose.vim new file mode 100644 index 0000000..cdfb84f --- /dev/null +++ b/bundle/Dockerfile/syntax/docker-compose.vim @@ -0,0 +1,74 @@ +" Vim syntax file +" Language: Dockerfile +" Maintainer: Eugene Kalinin +" Latest Revision: 11 September 2013 +" Source: http://docs.docker.io/en/latest/use/builder/ + +if exists("b:current_syntax") + finish +endif + +" case sensitivity (fix #17) +" syn case ignore + +" Keywords +syn keyword dockercomposeKeywords build context dockerfile args cap_add cap_drop +syn keyword dockercomposeKeywords command cgroup_parent container_name devices depends_on +syn keyword dockercomposeKeywords dns dns_search tmpfs entrypoint env_file environment +syn keyword dockercomposeKeywords expose extends extends external_links extra_hosts +syn keyword dockercomposeKeywords group_add image isolation labels links logging log_driver +syn keyword dockercomposeKeywords log_opt net network_mode networks aliases +syn keyword dockercomposeKeywords ipv4_address ipv6_address link_local_ips pid ports +syn keyword dockercomposeKeywords security_opt stop_signal ulimits volumes volume_driver +syn keyword dockercomposeKeywords volumes_from cpu_shares cpu_quota cpuset domainname hostname +syn keyword dockercomposeKeywords ipc mac_address mem_limit memswap_limit oom_score_adj privileged +syn keyword dockercomposeKeywords read_only restart shm_size stdin_open tty user working_dir +"" Volume configuration reference +syn keyword dockercomposeKeywords driver driver_opts external labels +"" Network configuration reference +syn keyword dockercomposeKeywords driver driver_opts enable_ipv6 ipam internal labels external +"" Versioning +syn keyword dockercomposeKeywords version services + +" Bash statements +setlocal iskeyword+=- +syn keyword bashStatement add-apt-repository adduser apk apt-get aptitude apt-key autoconf bundle +syn keyword bashStatement cd chgrp chmod chown clear complete composer cp curl du echo egrep +syn keyword bashStatement expr fgrep find gem gnufind gnugrep gpg grep groupadd head less ln +syn keyword bashStatement ls make mkdir mv node npm pacman pip pip3 php python rails rm rmdir rpm ruby +syn keyword bashStatement sed sleep sort strip tar tail tailf touch useradd virtualenv yum +syn keyword bashStatement usermod bash cat a2ensite a2dissite a2enmod a2dismod apache2ctl +syn keyword bashStatement wget gzip + +" Strings +syn region dockercomposeString start=/"/ skip=/\\"/ end=/"/ +syn region dockercomposeString1 start=/'/ skip=/\\'/ end=/'/ + +" Emails +syn region dockercomposeEmail start=// contains=@ oneline + +" Urls +syn match dockercomposeUrl /\(http\|https\|ssh\|hg\|git\)\:\/\/[a-zA-Z0-9\/\-\.]\+/ + +" Task tags +syn keyword dockercomposeTodo contained TODO FIXME XXX + +" Comments +syn region dockercomposeComment start="#" end="\n" contains=dockercomposeTodo + +" Highlighting +hi link dockercomposeKeywords Keyword +hi link dockercomposeString String +hi link dockercomposeString1 String +hi link dockercomposeComment Comment +hi link dockercomposeEmail Identifier +hi link dockercomposeUrl Identifier +hi link dockercomposeTodo Todo +hi link bashStatement Function + +let b:current_syntax = "dockercompose" + +set commentstring=#\ %s + +" Enable automatic comment insertion +setlocal fo+=cro diff --git a/bundle/Dockerfile/vim-dockerfile-example.png b/bundle/Dockerfile/vim-dockerfile-example.png new file mode 100644 index 0000000000000000000000000000000000000000..c82f871f84f7a27ee90783ac65a997708e0f033f GIT binary patch literal 57722 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 literal 0 HcmV?d00001 diff --git a/bundle/groovy/syntax/groovy.vim b/bundle/groovy/syntax/groovy.vim new file mode 100644 index 0000000..5f96dfb --- /dev/null +++ b/bundle/groovy/syntax/groovy.vim @@ -0,0 +1,450 @@ +" Vim syntax file +" Language: Groovy +" Maintainer: Alessio Pace +" Version: 0.1.9b +" URL: http://www.vim.org/scripts/script.php?script_id=945 +" Last Change: 6/4/2004 + +" This is my very first vim script, I hope to have +" done it the right way. +" +" I must directly or indirectly thank the author of java.vim and ruby.vim: +" I copied from them most of the stuff :-) +" +" Relies on html.vim + +" For version 5.x: Clear all syntax items +" For version 6.x: Quit when a syntax file was already loaded +" +" HOWTO USE IT (INSTALL): +" [groovy is still not recognized by vim! :-( ] +" +" 1) copy the file in the (global or user's $HOME/.vim/syntax/) syntax folder +" +" 2) add this line to recognize groovy files by filename extension: +" +" au BufNewFile,BufRead *.groovy setf groovy +" in the global vim filetype.vim file or inside $HOME/.vim/filetype.vim +" +" 3) add this part to recognize by content groovy script (no extension needed :-) +" +" if did_filetype() +" finish +" endif +" if getline(1) =~ '^#!.*[/\\]groovy\>' +" setf groovy +" endif +" +" in the global scripts.vim file or in $HOME/.vim/scripts.vim +" +" 4) open/write a .groovy file or a groovy script :-) +" +" Let me know if you like it or send me patches, so that I can improve it +" when I have time + +" Quit when a syntax file was already loaded +if !exists("main_syntax") + if version < 600 + syntax clear + elseif exists("b:current_syntax") + finish + endif + " we define it here so that included files can test for it + let main_syntax='groovy' +endif + +" don't use standard HiLink, it will not work with included syntax files +if version < 508 + command! -nargs=+ GroovyHiLink hi link +else + command! -nargs=+ GroovyHiLink hi def link +endif + +" ########################## +" Java stuff taken from java.vim +" some characters that cannot be in a groovy program (outside a string) +" syn match groovyError "[\\@`]" +"syn match groovyError "<<<\|\.\.\|=>\|<>\|||=\|&&=\|[^-]->\|\*\/" +"syn match groovyOK "\.\.\." + +" keyword definitions +syn keyword groovyExternal native package +syn match groovyExternal "\\)\?" +syn keyword groovyError goto const +syn keyword groovyConditional if else switch +syn keyword groovyRepeat while for do +syn keyword groovyBoolean true false +syn keyword groovyConstant null +syn keyword groovyTypedef this super +syn keyword groovyOperator new instanceof +syn keyword groovyType boolean char byte short int long float double +syn keyword groovyType void +syn keyword groovyType Integer Double Date Boolean Float String Array Vector List +syn keyword groovyStatement return +syn keyword groovyStorageClass static synchronized transient volatile final strictfp serializable +syn keyword groovyExceptions throw try catch finally +syn keyword groovyAssert assert +syn keyword groovyMethodDecl synchronized throws +syn keyword groovyClassDecl extends implements interface +" to differentiate the keyword class from MyClass.class we use a match here +syn match groovyTypedef "\.\s*\"ms=s+1 +syn keyword groovyClassDecl enum +syn match groovyClassDecl "^class\>" +syn match groovyClassDecl "[^.]\s*\"ms=s+1 +syn keyword groovyBranch break continue nextgroup=groovyUserLabelRef skipwhite +syn match groovyUserLabelRef "\k\+" contained +syn keyword groovyScopeDecl public protected private abstract + + +if exists("groovy_highlight_groovy_lang_ids") || exists("groovy_highlight_groovy_lang") || exists("groovy_highlight_all") + " groovy.lang.* + syn keyword groovyLangClass Closure MetaMethod GroovyObject + + syn match groovyJavaLangClass "\" + syn keyword groovyJavaLangClass Cloneable Comparable Runnable Serializable Boolean Byte Class Object + syn keyword groovyJavaLangClass Character CharSequence ClassLoader Compiler + " syn keyword groovyJavaLangClass Integer Double Float Long + syn keyword groovyJavaLangClass InheritableThreadLocal Math Number Object Package Process + syn keyword groovyJavaLangClass Runtime RuntimePermission InheritableThreadLocal + syn keyword groovyJavaLangClass SecurityManager Short StrictMath StackTraceElement + syn keyword groovyJavaLangClass StringBuffer Thread ThreadGroup + syn keyword groovyJavaLangClass ThreadLocal Throwable Void ArithmeticException + syn keyword groovyJavaLangClass ArrayIndexOutOfBoundsException AssertionError + syn keyword groovyJavaLangClass ArrayStoreException ClassCastException + syn keyword groovyJavaLangClass ClassNotFoundException + syn keyword groovyJavaLangClass CloneNotSupportedException Exception + syn keyword groovyJavaLangClass IllegalAccessException + syn keyword groovyJavaLangClass IllegalArgumentException + syn keyword groovyJavaLangClass IllegalMonitorStateException + syn keyword groovyJavaLangClass IllegalStateException + syn keyword groovyJavaLangClass IllegalThreadStateException + syn keyword groovyJavaLangClass IndexOutOfBoundsException + syn keyword groovyJavaLangClass InstantiationException InterruptedException + syn keyword groovyJavaLangClass NegativeArraySizeException NoSuchFieldException + syn keyword groovyJavaLangClass NoSuchMethodException NullPointerException + syn keyword groovyJavaLangClass NumberFormatException RuntimeException + syn keyword groovyJavaLangClass SecurityException StringIndexOutOfBoundsException + syn keyword groovyJavaLangClass UnsupportedOperationException + syn keyword groovyJavaLangClass AbstractMethodError ClassCircularityError + syn keyword groovyJavaLangClass ClassFormatError Error ExceptionInInitializerError + syn keyword groovyJavaLangClass IllegalAccessError InstantiationError + syn keyword groovyJavaLangClass IncompatibleClassChangeError InternalError + syn keyword groovyJavaLangClass LinkageError NoClassDefFoundError + syn keyword groovyJavaLangClass NoSuchFieldError NoSuchMethodError + syn keyword groovyJavaLangClass OutOfMemoryError StackOverflowError + syn keyword groovyJavaLangClass ThreadDeath UnknownError UnsatisfiedLinkError + syn keyword groovyJavaLangClass UnsupportedClassVersionError VerifyError + syn keyword groovyJavaLangClass VirtualMachineError + + syn keyword groovyJavaLangObject clone equals finalize getClass hashCode + syn keyword groovyJavaLangObject notify notifyAll toString wait + + GroovyHiLink groovyLangClass groovyConstant + GroovyHiLink groovyJavaLangClass groovyExternal + GroovyHiLink groovyJavaLangObject groovyConstant + syn cluster groovyTop add=groovyJavaLangObject,groovyJavaLangClass,groovyLangClass + syn cluster groovyClasses add=groovyJavaLangClass,groovyLangClass +endif + + +" Groovy stuff +syn match groovyOperator "\.\." +syn match groovyOperator "<\{2,3}" +syn match groovyOperator ">\{2,3}" +syn match groovyOperator "->" +syn match groovyExternal '^#!.*[/\\]groovy\>' +syn match groovyExceptions "\\|\<[A-Z]\{1,}[a-zA-Z0-9]*Exception\>" + +" Groovy JDK stuff +syn keyword groovyJDKBuiltin as def in +syn keyword groovyJDKOperOverl div minus plus abs round power multiply +syn keyword groovyJDKMethods each call inject sort print println +syn keyword groovyJDKMethods getAt putAt size push pop toList getText writeLine eachLine readLines +syn keyword groovyJDKMethods withReader withStream withWriter withPrintWriter write read leftShift +syn keyword groovyJDKMethods withWriterAppend readBytes splitEachLine +syn keyword groovyJDKMethods newInputStream newOutputStream newPrintWriter newReader newWriter +syn keyword groovyJDKMethods compareTo next previous isCase +syn keyword groovyJDKMethods times step toInteger upto any collect dump every find findAll grep +syn keyword groovyJDKMethods inspect invokeMethods join +syn keyword groovyJDKMethods getErr getIn getOut waitForOrKill +syn keyword groovyJDKMethods count tokenize asList flatten immutable intersect reverse reverseEach +syn keyword groovyJDKMethods subMap append asWritable eachByte eachLine eachFile +syn cluster groovyTop add=groovyJDKBuiltin,groovyJDKOperOverl,groovyJDKMethods + +" no useful I think, so I comment it.. +"if filereadable(expand(":p:h")."/groovyid.vim") + " source :p:h/groovyid.vim +"endif + +if exists("groovy_space_errors") + if !exists("groovy_no_trail_space_error") + syn match groovySpaceError "\s\+$" + endif + if !exists("groovy_no_tab_space_error") + syn match groovySpaceError " \+\t"me=e-1 + endif +endif + +" it is a better case construct than java.vim to match groovy syntax +syn region groovyLabelRegion transparent matchgroup=groovyLabel start="\" matchgroup=NONE end=":\|$" contains=groovyNumber,groovyString,groovyLangClass,groovyJavaLangClass +syn match groovyUserLabel "^\s*[_$a-zA-Z][_$a-zA-Z0-9_]*\s*:"he=e-1 contains=groovyLabel +syn keyword groovyLabel default + +if !exists("groovy_allow_cpp_keywords") + syn keyword groovyError auto delete extern friend inline redeclared + syn keyword groovyError register signed sizeof struct template typedef union + syn keyword groovyError unsigned operator +endif + +" The following cluster contains all groovy groups except the contained ones +syn cluster groovyTop add=groovyExternal,groovyError,groovyError,groovyBranch,groovyLabelRegion,groovyLabel,groovyConditional,groovyRepeat,groovyBoolean,groovyConstant,groovyTypedef,groovyOperator,groovyType,groovyType,groovyStatement,groovyStorageClass,groovyAssert,groovyExceptions,groovyMethodDecl,groovyClassDecl,groovyClassDecl,groovyClassDecl,groovyScopeDecl,groovyError,groovyError2,groovyUserLabel,groovyLangObject + + +" Comments +syn keyword groovyTodo contained TODO FIXME XXX +if exists("groovy_comment_strings") + syn region groovyCommentString contained start=+"+ end=+"+ end=+$+ end=+\*/+me=s-1,he=s-1 contains=groovySpecial,groovyCommentStar,groovySpecialChar,@Spell + syn region groovyComment2String contained start=+"+ end=+$\|"+ contains=groovySpecial,groovySpecialChar,@Spell + syn match groovyCommentCharacter contained "'\\[^']\{1,6\}'" contains=groovySpecialChar + syn match groovyCommentCharacter contained "'\\''" contains=groovySpecialChar + syn match groovyCommentCharacter contained "'[^\\]'" + syn cluster groovyCommentSpecial add=groovyCommentString,groovyCommentCharacter,groovyNumber + syn cluster groovyCommentSpecial2 add=groovyComment2String,groovyCommentCharacter,groovyNumber +endif +syn region groovyComment start="/\*" end="\*/" contains=@groovyCommentSpecial,groovyTodo,@Spell +syn match groovyCommentStar contained "^\s*\*[^/]"me=e-1 +syn match groovyCommentStar contained "^\s*\*$" +syn match groovyLineComment "//.*" contains=@groovyCommentSpecial2,groovyTodo,@Spell +syn match groovyLineComment "#.*" contains=@groovyCommentSpecial2,groovyTodo,@Spell +GroovyHiLink groovyCommentString groovyString +GroovyHiLink groovyComment2String groovyString +GroovyHiLink groovyCommentCharacter groovyCharacter + +syn cluster groovyTop add=groovyComment,groovyLineComment + +if !exists("groovy_ignore_groovydoc") && main_syntax != 'jsp' + syntax case ignore + " syntax coloring for groovydoc comments (HTML) + " syntax include @groovyHtml :p:h/html.vim + syntax include @groovyHtml runtime! syntax/html.vim + unlet b:current_syntax + syn region groovyDocComment start="/\*\*" end="\*/" keepend contains=groovyCommentTitle,@groovyHtml,groovyDocTags,groovyTodo,@Spell + syn region groovyCommentTitle contained matchgroup=groovyDocComment start="/\*\*" matchgroup=groovyCommentTitle keepend end="\.$" end="\.[ \t\r<&]"me=e-1 end="[^{]@"me=s-2,he=s-1 end="\*/"me=s-1,he=s-1 contains=@groovyHtml,groovyCommentStar,groovyTodo,@Spell,groovyDocTags + + syn region groovyDocTags contained start="{@\(link\|linkplain\|inherit[Dd]oc\|doc[rR]oot\|value\)" end="}" + syn match groovyDocTags contained "@\(see\|param\|exception\|throws\|since\)\s\+\S\+" contains=groovyDocParam + syn match groovyDocParam contained "\s\S\+" + syn match groovyDocTags contained "@\(version\|author\|return\|deprecated\|serial\|serialField\|serialData\)\>" + syntax case match +endif + +" match the special comment /**/ +syn match groovyComment "/\*\*/" + +" Strings and constants +syn match groovySpecialError contained "\\." +syn match groovySpecialCharError contained "[^']" +syn match groovySpecialChar contained "\\\([4-9]\d\|[0-3]\d\d\|[\"\\'ntbrf]\|u\x\{4\}\)" +syn region groovyString start=+"+ end=+"+ end=+$+ contains=groovySpecialChar,groovySpecialError,@Spell,groovyELExpr +syn region groovyString start=+'+ end=+'+ end=+$+ contains=groovySpecialChar,groovySpecialError,@Spell,groovyELExpr +" syn region groovyELExpr start=+${+ end=+}+ keepend contained + syn match groovyELExpr /\${.\{-}}/ contained +GroovyHiLink groovyELExpr Identifier + +" TODO: better matching. I am waiting to understand how it really works in groovy +" syn region groovyClosureParamsBraces start=+|+ end=+|+ contains=groovyClosureParams +" syn match groovyClosureParams "[ a-zA-Z0-9_*]\+" contained +" GroovyHiLink groovyClosureParams Identifier + +" next line disabled, it can cause a crash for a long line +"syn match groovyStringError +"\([^"\\]\|\\.\)*$+ + +" disabled: in groovy strings or characters are written the same +" syn match groovyCharacter "'[^']*'" contains=groovySpecialChar,groovySpecialCharError +" syn match groovyCharacter "'\\''" contains=groovySpecialChar +" syn match groovyCharacter "'[^\\]'" +syn match groovyNumber "\<\(0[0-7]*\|0[xX]\x\+\|\d\+\)[lL]\=\>" +syn match groovyNumber "\(\<\d\+\.\d*\|\.\d\+\)\([eE][-+]\=\d\+\)\=[fFdD]\=" +syn match groovyNumber "\<\d\+[eE][-+]\=\d\+[fFdD]\=\>" +syn match groovyNumber "\<\d\+\([eE][-+]\=\d\+\)\=[fFdD]\>" + +" unicode characters +syn match groovySpecial "\\u\d\{4\}" + +syn cluster groovyTop add=groovyString,groovyCharacter,groovyNumber,groovySpecial,groovyStringError + +if exists("groovy_highlight_functions") + if groovy_highlight_functions == "indent" + syn match groovyFuncDef "^\(\t\| \{8\}\)[_$a-zA-Z][_$a-zA-Z0-9_. \[\]]*([^-+*/()]*)" contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses + syn region groovyFuncDef start=+^\(\t\| \{8\}\)[$_a-zA-Z][$_a-zA-Z0-9_. \[\]]*([^-+*/()]*,\s*+ end=+)+ contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses + syn match groovyFuncDef "^ [$_a-zA-Z][$_a-zA-Z0-9_. \[\]]*([^-+*/()]*)" contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses + syn region groovyFuncDef start=+^ [$_a-zA-Z][$_a-zA-Z0-9_. \[\]]*([^-+*/()]*,\s*+ end=+)+ contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses + else + " This line catches method declarations at any indentation>0, but it assumes + " two things: + " 1. class names are always capitalized (ie: Button) + " 2. method names are never capitalized (except constructors, of course) + syn region groovyFuncDef start=+^\s\+\(\(public\|protected\|private\|static\|abstract\|final\|native\|synchronized\)\s\+\)*\(\(void\|boolean\|char\|byte\|short\|int\|long\|float\|double\|\([A-Za-z_][A-Za-z0-9_$]*\.\)*[A-Z][A-Za-z0-9_$]*\)\(<[^>]*>\)\=\(\[\]\)*\s\+[a-z][A-Za-z0-9_$]*\|[A-Z][A-Za-z0-9_$]*\)\s*([^0-9]+ end=+)+ contains=groovyScopeDecl,groovyType,groovyStorageClass,groovyComment,groovyLineComment,@groovyClasses + endif + syn match groovyBraces "[{}]" + syn cluster groovyTop add=groovyFuncDef,groovyBraces +endif + +if exists("groovy_highlight_debug") + + " Strings and constants + syn match groovyDebugSpecial contained "\\\d\d\d\|\\." + syn region groovyDebugString contained start=+"+ end=+"+ contains=groovyDebugSpecial + syn match groovyDebugStringError +"\([^"\\]\|\\.\)*$+ + syn match groovyDebugCharacter contained "'[^\\]'" + syn match groovyDebugSpecialCharacter contained "'\\.'" + syn match groovyDebugSpecialCharacter contained "'\\''" + syn match groovyDebugNumber contained "\<\(0[0-7]*\|0[xX]\x\+\|\d\+\)[lL]\=\>" + syn match groovyDebugNumber contained "\(\<\d\+\.\d*\|\.\d\+\)\([eE][-+]\=\d\+\)\=[fFdD]\=" + syn match groovyDebugNumber contained "\<\d\+[eE][-+]\=\d\+[fFdD]\=\>" + syn match groovyDebugNumber contained "\<\d\+\([eE][-+]\=\d\+\)\=[fFdD]\>" + syn keyword groovyDebugBoolean contained true false + syn keyword groovyDebugType contained null this super + syn region groovyDebugParen start=+(+ end=+)+ contained contains=groovyDebug.*,groovyDebugParen + + " to make this work you must define the highlighting for these groups + syn match groovyDebug "\= 508 || !exists("did_c_syn_inits") + GroovyHiLink groovyDebug Debug + GroovyHiLink groovyDebugString DebugString + GroovyHiLink groovyDebugStringError groovyError + GroovyHiLink groovyDebugType DebugType + GroovyHiLink groovyDebugBoolean DebugBoolean + GroovyHiLink groovyDebugNumber Debug + GroovyHiLink groovyDebugSpecial DebugSpecial + GroovyHiLink groovyDebugSpecialCharacter DebugSpecial + GroovyHiLink groovyDebugCharacter DebugString + GroovyHiLink groovyDebugParen Debug + + GroovyHiLink DebugString String + GroovyHiLink DebugSpecial Special + GroovyHiLink DebugBoolean Boolean + GroovyHiLink DebugType Type + endif +endif + +" Match all Exception classes +syn match groovyExceptions "\\|\<[A-Z]\{1,}[a-zA-Z0-9]*Exception\>" + + +if !exists("groovy_minlines") + let groovy_minlines = 10 +endif +exec "syn sync ccomment groovyComment minlines=" . groovy_minlines + + +" ################### +" Groovy stuff +" syn match groovyOperator "|[ ,a-zA-Z0-9_*]\+|" + +" All groovy valid tokens +" syn match groovyTokens ";\|,\|<=>\|<>\|:\|:=\|>\|>=\|=\|==\|<\|<=\|!=\|/\|/=\|\.\.|\.\.\.\|\~=\|\~==" +" syn match groovyTokens "\*=\|&\|&=\|\*\|->\|\~\|+\|-\|/\|?\|<<<\|>>>\|<<\|>>" + +" Must put explicit these ones because groovy.vim mark them as errors otherwise +" syn match groovyTokens "<=>\|<>\|==\~" +"syn cluster groovyTop add=groovyTokens + +" Mark these as operators + +" Hightlight brackets +" syn match groovyBraces "[{}]" +" syn match groovyBraces "[\[\]]" +" syn match groovyBraces "[\|]" + +if exists("groovy_mark_braces_in_parens_as_errors") + syn match groovyInParen contained "[{}]" + GroovyHiLink groovyInParen groovyError + syn cluster groovyTop add=groovyInParen +endif + +" catch errors caused by wrong parenthesis +syn region groovyParenT transparent matchgroup=groovyParen start="(" end=")" contains=@groovyTop,groovyParenT1 +syn region groovyParenT1 transparent matchgroup=groovyParen1 start="(" end=")" contains=@groovyTop,groovyParenT2 contained +syn region groovyParenT2 transparent matchgroup=groovyParen2 start="(" end=")" contains=@groovyTop,groovyParenT contained +syn match groovyParenError ")" +GroovyHiLink groovyParenError groovyError + +" catch errors caused by wrong square parenthesis +syn region groovyParenT transparent matchgroup=groovyParen start="\[" end="\]" contains=@groovyTop,groovyParenT1 +syn region groovyParenT1 transparent matchgroup=groovyParen1 start="\[" end="\]" contains=@groovyTop,groovyParenT2 contained +syn region groovyParenT2 transparent matchgroup=groovyParen2 start="\[" end="\]" contains=@groovyTop,groovyParenT contained +syn match groovyParenError "\]" + +" ############################### +" java.vim default highlighting +if version >= 508 || !exists("did_groovy_syn_inits") + if version < 508 + let did_groovy_syn_inits = 1 + endif + GroovyHiLink groovyFuncDef Function + GroovyHiLink groovyBraces Function + GroovyHiLink groovyBranch Conditional + GroovyHiLink groovyUserLabelRef groovyUserLabel + GroovyHiLink groovyLabel Label + GroovyHiLink groovyUserLabel Label + GroovyHiLink groovyConditional Conditional + GroovyHiLink groovyRepeat Repeat + GroovyHiLink groovyExceptions Exception + GroovyHiLink groovyAssert Statement + GroovyHiLink groovyStorageClass StorageClass + GroovyHiLink groovyMethodDecl groovyStorageClass + GroovyHiLink groovyClassDecl groovyStorageClass + GroovyHiLink groovyScopeDecl groovyStorageClass + GroovyHiLink groovyBoolean Boolean + GroovyHiLink groovySpecial Special + GroovyHiLink groovySpecialError Error + GroovyHiLink groovySpecialCharError Error + GroovyHiLink groovyString String + GroovyHiLink groovyCharacter Character + GroovyHiLink groovySpecialChar SpecialChar + GroovyHiLink groovyNumber Number + GroovyHiLink groovyError Error + GroovyHiLink groovyStringError Error + GroovyHiLink groovyStatement Statement + GroovyHiLink groovyOperator Operator + GroovyHiLink groovyComment Comment + GroovyHiLink groovyDocComment Comment + GroovyHiLink groovyLineComment Comment + GroovyHiLink groovyConstant Constant + GroovyHiLink groovyTypedef Typedef + GroovyHiLink groovyTodo Todo + + GroovyHiLink groovyCommentTitle SpecialComment + GroovyHiLink groovyDocTags Special + GroovyHiLink groovyDocParam Function + GroovyHiLink groovyCommentStar groovyComment + + GroovyHiLink groovyType Type + GroovyHiLink groovyExternal Include + + GroovyHiLink htmlComment Special + GroovyHiLink htmlCommentPart Special + GroovyHiLink groovySpaceError Error + GroovyHiLink groovyJDKBuiltin Special + GroovyHiLink groovyJDKOperOverl Operator + GroovyHiLink groovyJDKMethods Function +endif + +delcommand GroovyHiLink + + +let b:current_syntax = "groovy" +if main_syntax == 'groovy' + unlet main_syntax +endif + +let b:spell_options="contained" + +" vim: ts=8 diff --git a/vimrc b/vimrc index 561751b..40e8e57 100644 --- a/vimrc +++ b/vimrc @@ -240,6 +240,15 @@ let g:airline#extensions#tabline#left_sep = ' ' let g:airline#extensions#tabline#left_alt_sep = ' ' +"------ Text File Settings ------ +:autocmd! BufNewFile,BufRead *.txt,*.md,*.tex set wrap + + +"------ Jenkins Settings ------ +au BufReadPost Jenkinsfile set syntax=groovy +au BufReadPost Jenkinsfile set filetype=groovy + + "------ GUI Options ------ if has("gui_running") " Hides toolbar and scrollbars and File menu From 02a002ef898d42085d879ba5f44fdd1bf17fa93d Mon Sep 17 00:00:00 2001 From: Thomas Hunter II Date: Wed, 8 Feb 2017 14:08:22 -0800 Subject: [PATCH 26/96] gitgutter and nerdtree-git-plugin --- bundle/gitgutter/.gitignore | 5 + bundle/gitgutter/LICENCE | 22 + bundle/gitgutter/README.mkd | 499 ++++++++++++++++++ bundle/gitgutter/autoload/gitgutter.vim | 259 +++++++++ bundle/gitgutter/autoload/gitgutter/async.vim | 207 ++++++++ bundle/gitgutter/autoload/gitgutter/debug.vim | 119 +++++ bundle/gitgutter/autoload/gitgutter/diff.vim | 342 ++++++++++++ .../autoload/gitgutter/highlight.vim | 115 ++++ bundle/gitgutter/autoload/gitgutter/hunk.vim | 137 +++++ bundle/gitgutter/autoload/gitgutter/sign.vim | 179 +++++++ .../gitgutter/autoload/gitgutter/utility.vim | 208 ++++++++ bundle/gitgutter/doc/gitgutter.txt | 341 ++++++++++++ bundle/gitgutter/plugin/gitgutter.vim | 241 +++++++++ bundle/gitgutter/screenshot.png | Bin 0 -> 16191 bytes bundle/gitgutter/test/fixture.txt | 11 + bundle/gitgutter/test/runner.vim | 162 ++++++ bundle/gitgutter/test/test | 19 + bundle/gitgutter/test/test_gitgutter.vim | 400 ++++++++++++++ bundle/nerdtree-git-plugin/README.md | 65 +++ .../nerdtree_plugin/git_status.vim | 340 ++++++++++++ vimrc | 6 +- 21 files changed, 3676 insertions(+), 1 deletion(-) create mode 100644 bundle/gitgutter/.gitignore create mode 100644 bundle/gitgutter/LICENCE create mode 100644 bundle/gitgutter/README.mkd create mode 100644 bundle/gitgutter/autoload/gitgutter.vim create mode 100644 bundle/gitgutter/autoload/gitgutter/async.vim create mode 100644 bundle/gitgutter/autoload/gitgutter/debug.vim create mode 100644 bundle/gitgutter/autoload/gitgutter/diff.vim create mode 100644 bundle/gitgutter/autoload/gitgutter/highlight.vim create mode 100644 bundle/gitgutter/autoload/gitgutter/hunk.vim create mode 100644 bundle/gitgutter/autoload/gitgutter/sign.vim create mode 100644 bundle/gitgutter/autoload/gitgutter/utility.vim create mode 100644 bundle/gitgutter/doc/gitgutter.txt create mode 100644 bundle/gitgutter/plugin/gitgutter.vim create mode 100644 bundle/gitgutter/screenshot.png create mode 100644 bundle/gitgutter/test/fixture.txt create mode 100644 bundle/gitgutter/test/runner.vim create mode 100755 bundle/gitgutter/test/test create mode 100644 bundle/gitgutter/test/test_gitgutter.vim create mode 100644 bundle/nerdtree-git-plugin/README.md create mode 100644 bundle/nerdtree-git-plugin/nerdtree_plugin/git_status.vim diff --git a/bundle/gitgutter/.gitignore b/bundle/gitgutter/.gitignore new file mode 100644 index 0000000..82fb253 --- /dev/null +++ b/bundle/gitgutter/.gitignore @@ -0,0 +1,5 @@ +/doc/tags +/misc +/test/*.actual +*.log + diff --git a/bundle/gitgutter/LICENCE b/bundle/gitgutter/LICENCE new file mode 100644 index 0000000..38e2dc2 --- /dev/null +++ b/bundle/gitgutter/LICENCE @@ -0,0 +1,22 @@ +MIT License + +Copyright (c) Andrew Stewart + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/bundle/gitgutter/README.mkd b/bundle/gitgutter/README.mkd new file mode 100644 index 0000000..19ed387 --- /dev/null +++ b/bundle/gitgutter/README.mkd @@ -0,0 +1,499 @@ +## vim-gitgutter + +A Vim plugin which shows a git diff in the 'gutter' (sign column). It shows whether each line has been added, modified, and where lines have been removed. You can also stage and undo individual hunks. + +Features: + +* Shows signs for added, modified, and removed lines. +* Runs the diffs asynchronously in terminal Vim/MacVim (7.4.1826+), gVim (7.4.1850+), MacVim GUI (7.4.1832+), and NeoVim. +* Ensures signs are always as up to date as possible (but without running more than necessary). +* Quick jumping between blocks of changed lines ("hunks"). +* Stage/undo/preview individual hunks. +* Provides a hunk text object. +* Diffs against index (default) or any commit. +* Handles line endings correctly, even with repos that do CRLF conversion. +* Optional line highlighting. +* Fully customisable (signs, sign column, line highlights, mappings, extra git-diff arguments, etc). +* Can be toggled on/off. +* Preserves signs from other plugins. +* Easy to integrate diff stats into status line; built-in integration with [vim-airline](https://github.com/bling/vim-airline/). +* Works with fish shell (in addition to the usual shells). + +Constraints: + +* Supports git only. + +If you work with other version control systems, I recommend [vim-signify](https://github.com/mhinz/vim-signify). + + +### Screenshot + +![screenshot](https://raw.github.com/airblade/vim-gitgutter/master/screenshot.png) + +In the screenshot above you can see: + +* Line 15 has been modified. +* Lines 21-24 are new. +* A line or lines were removed between lines 25 and 26. + + +### Installation + +Before installation, please check your Vim supports signs by running `:echo has('signs')`. `1` means you're all set; `0` means you need to install a Vim with signs support. If you're compiling Vim yourself you need the 'big' or 'huge' feature set. [MacVim][] supports signs. + +You install vim-gitgutter like any other vim plugin. + +##### Pathogen + +``` +cd ~/.vim/bundle +git clone git://github.com/airblade/vim-gitgutter.git +``` + +##### Voom + +Edit your plugin manifest (`voom edit`) and add: + +``` +airblade/vim-gitgutter +``` + +##### VimPlug + +Place this in your .vimrc: + +```viml +Plug 'airblade/vim-gitgutter' +``` + +Then run the following in Vim: + +``` +:source % +:PlugInstall +``` + +##### NeoBundle + +Place this in your .vimrc: + +```viml +NeoBundle 'airblade/vim-gitgutter' +``` + +Then run the following in Vim: + +``` +:source % +:NeoBundleInstall +``` + +##### No plugin manager + +Copy vim-gitgutter's subdirectories into your vim configuration directory: + +``` +cd /tmp && git clone git://github.com/airblade/vim-gitgutter.git +cp -r vim-gitgutter/* ~/.vim/ +``` + +See `:help add-global-plugin`. + + +If you are on Windows you may find the command prompt pops up briefly every time vim-gitgutter runs. You can avoid this by installing both [vim-misc](https://github.com/xolox/vim-misc) and [vim-shell](https://github.com/xolox/vim-shell). If you have those two plugins but don't want vim-gitgutter to use them, you can opt out with `let g:gitgutter_avoid_cmd_prompt_on_windows = 0` in your `~/.vimrc`. + + +### Getting started + +When you make a change to a file tracked by git, the diff markers should appear automatically. The delay is governed by vim's `updatetime` option; the default value is 4 seconds but I suggest reducing it to around 250ms (add `set updatetime=250` to your vimrc). + +You can jump between hunks with `[c` and `]c`. You can preview, stage, and undo hunks with `hp`, `hs`, and `hu` respectively. + +You cannot currently unstage a staged hunk. + + +#### Activation + +You can explicitly turn vim-gitgutter off and on (defaults to on): + +* turn off with `:GitGutterDisable` +* turn on with `:GitGutterEnable` +* toggle with `:GitGutterToggle`. + +You can turn the signs on and off (defaults to on): + +* turn on with `:GitGutterSignsEnable` +* turn off with `:GitGutterSignsDisable` +* toggle with `:GitGutterSignsToggle`. + +And you can turn line highlighting on and off (defaults to off): + +* turn on with `:GitGutterLineHighlightsEnable` +* turn off with `:GitGutterLineHighlightsDisable` +* toggle with `:GitGutterLineHighlightsToggle`. + +Note that if you have line highlighting on and signs off, you will have an empty sign column – more accurately, a sign column with invisible signs. This is because line highlighting requires signs and Vim always shows the sign column even if the signs are invisible. + +If you switch off both line highlighting and signs, you won't see the sign column. That is unless you have set `let g:gitgutter_sign_column_always = 1` so it's always there. + +To keep your Vim snappy, vim-gitgutter will suppress itself when a file has more than 500 changes. As soon as the number of changes falls below the limit vim-gitgutter will show the signs again. You can configure the threshold with: + +```viml +let g:gitgutter_max_signs = 500 " default value +``` + +#### Hunks + +You can jump between hunks: + +* jump to next hunk (change): `]c` +* jump to previous hunk (change): `[c`. + +Both of those take a preceding count. + +To set your own mappings for these, for example `]h` and `[h`: + +```viml +nmap ]h GitGutterNextHunk +nmap [h GitGutterPrevHunk +``` + +You can stage or undo an individual hunk when your cursor is in it: + +* stage the hunk with `hs` or +* undo it with `hu`. + +See the FAQ if you want to unstage staged changes. + +The `.` command will work with both these if you install [repeat.vim](https://github.com/tpope/vim-repeat). + +To set your own mappings for these, for example if you prefer the mnemonics hunk-add and hunk-revert: + +```viml +nmap ha GitGutterStageHunk +nmap hr GitGutterUndoHunk +``` + +And you can preview a hunk's changes with `hp`. You can of course change this mapping, e.g: + +```viml +nmap hv GitGutterPreviewHunk +``` + +A hunk text object is provided which works in visual and operator-pending modes. + +- `ic` operates on all lines in the current hunk. +- `ac` operates on all lines in the current hunk and any trailing empty lines. + +To re-map these, for example to `ih` and `ah`: + +```viml +omap ih GitGutterTextObjectInnerPending +omap ah GitGutterTextObjectOuterPending +xmap ih GitGutterTextObjectInnerVisual +xmap ah GitGutterTextObjectOuterVisual +``` + +If you don't want vim-gitgutter to set up any mappings at all, use this: + +```viml +let g:gitgutter_map_keys = 0 +``` + +Finally, you can force vim-gitgutter to update its signs across all visible buffers with `:GitGutterAll`. + +See the customisation section below for how to change the defaults. + + +### When are the signs updated? + +By default the signs are updated as follows: + +| Event | Reason for update | Configuration | +|---------------------------|--------------------------------------|------------------------| +| Stop typing | So the signs are real time | `g:gitgutter_realtime` | +| Switch buffer | To notice change to git index | `g:gitgutter_eager` | +| Switch tab | To notice change to git index | `g:gitgutter_eager` | +| Focus the GUI | To notice change to git index | `g:gitgutter_eager` (not gVim on Windows) | +| Read a file into a buffer | To display initial signs | [always] | +| Save a buffer | So non-realtime signs are up to date | [always] | +| Change a file outside Vim | To notice `git stash` | [always] | + +The length of time Vim waits after you stop typing before it triggers the plugin is governed by the setting `updatetime`. This defaults to `4000` milliseconds which is rather too long. I recommend around `250` milliseconds but it depends on your system and your preferences. Note that in terminal Vim pre-7.4.427 an `updatetime` of less than approximately `1000` milliseconds can lead to random highlighting glitches; the lower the `updatetime`, the more glitches. + +If you experience a lag, you can trade speed for accuracy: + +```viml +let g:gitgutter_realtime = 0 +let g:gitgutter_eager = 0 +``` + +Note the realtime updating requires Vim 7.3.105 or higher. + + +### Customisation + +You can customise: + +* The sign column's colours +* Whether or not the sign column is shown when there aren't any signs (defaults to no) +* The signs' colours and symbols +* Line highlights +* The base of the diff +* Extra arguments for `git diff` +* Key mappings +* Whether or not vim-gitgutter is on initially (defaults to on) +* Whether or not signs are shown (defaults to yes) +* Whether or not line highlighting is on initially (defaults to off) +* Whether or not vim-gitgutter runs in "realtime" (defaults to yes) +* Whether or not vim-gitgutter runs eagerly (defaults to yes) +* Whether or not vim-gitgutter runs asynchronously (defaults to yes) + +Please note that vim-gitgutter won't override any colours or highlights you've set in your colorscheme. + + +#### Sign column + +By default vim-gitgutter will make the sign column look like the line number column. + +To customise your sign column's background color, first tell vim-gitgutter to leave it alone: + +```viml +let g:gitgutter_override_sign_column_highlight = 0 +``` + +And then either update your colorscheme's `SignColumn` highlight group or set it in your vimrc: + +```viml +highlight SignColumn ctermbg=whatever " terminal Vim +highlight SignColumn guibg=whatever " gVim/MacVim +``` + +By default the sign column will appear when there are signs to show and disappear when there aren't. If you would always like the sign column to be there, add `let g:gitgutter_sign_column_always = 1` to your `~/.vimrc`. + + +#### Signs' colours and symbols + +To customise the colours, set up the following highlight groups in your colorscheme or `~/.vimrc`: + +```viml +GitGutterAdd " an added line +GitGutterChange " a changed line +GitGutterDelete " at least one removed line +GitGutterChangeDelete " a changed line followed by at least one removed line +``` + +You can either set these with `highlight GitGutterAdd {key}={arg}...` or link them to existing highlight groups with, say, `highlight link GitGutterAdd DiffAdd`. + +To customise the symbols, add the following to your `~/.vimrc`: + +```viml +let g:gitgutter_sign_added = 'xx' +let g:gitgutter_sign_modified = 'yy' +let g:gitgutter_sign_removed = 'zz' +let g:gitgutter_sign_removed_first_line = '^^' +let g:gitgutter_sign_modified_removed = 'ww' +``` + + +#### Line highlights + +Similarly to the signs' colours, set up the following highlight groups in your colorscheme or `~/.vimrc`: + +```viml +GitGutterAddLine " default: links to DiffAdd +GitGutterChangeLine " default: links to DiffChange +GitGutterDeleteLine " default: links to DiffDelete +GitGutterChangeDeleteLine " default: links to GitGutterChangeLineDefault, i.e. DiffChange +``` + + +#### The base of the diff + +By default buffers are diffed against the index. However you can diff against any commit by setting: + +```viml +let g:gitgutter_diff_base = '' +``` + + +#### Extra arguments for `git diff` + +If you want to pass extra arguments to `git diff`, for example to ignore whitespace, do so like this: + +```viml +let g:gitgutter_diff_args = '-w' +``` + +#### Key mappings + +To disable all key mappings: + +```viml +let g:gitgutter_map_keys = 0 +``` + +See above for configuring maps for hunk-jumping and staging/undoing. + + +#### Use a custom `grep` command + +If you use an alternative to grep, or your grep does not support the `color` flag, you can tell vim-gitgutter to use it here. It only needs to support extended POSIX regex. + +```viml +" Default: +let g:gitgutter_grep_command = 'grep --color=never -e' +``` + +#### To turn off vim-gitgutter by default + +Add `let g:gitgutter_enabled = 0` to your `~/.vimrc`. + + +#### To turn off signs by default + +Add `let g:gitgutter_signs = 0` to your `~/.vimrc`. + + +#### To turn on line highlighting by default + +Add `let g:gitgutter_highlight_lines = 1` to your `~/.vimrc`. + + +#### To turn off asynchronous updates + +By default diffs are run asynchronously. To run diffs synchronously instead: + +```viml +let g:gitgutter_async = 0 +``` + + +### Extensions + +#### Operate on every line in a hunk + +You can map an operator to do whatever you want to every line in a hunk. + +Let's say, for example, you want to remove trailing whitespace. + +```viml +function! CleanUp(...) + if a:0 " opfunc + let [first, last] = [line("'["), line("']")] + else + let [first, last] = [line("'<"), line("'>")] + endif + for lnum in range(first, last) + let line = getline(lnum) + + " clean up the text, e.g.: + let line = substitute(line, '\s\+$', '', '') + + call setline(lnum, line) + endfor +endfunction + +nmap x :set opfunc=CleanUpg@ +``` + +Then place your cursor in a hunk and type `\xic` (assuming a leader of `\`). + +Alternatively you could place your cursor in a hunk, type `vic` to select it, then `:call CleanUp()`. + + +#### Operate on every changed line in a file + +You can write a command to do whatever you want to every changed line in a file. + +```viml +function! GlobalChangedLines(ex_cmd) + for hunk in GitGutterGetHunks() + for lnum in range(hunk[2], hunk[2]+hunk[3]-1) + let cursor = getcurpos() + silent! execute lnum.a:ex_cmd + call setpos('.', cursor) + endfor + endfor +endfunction + +command -nargs=1 Glines call GlobalChangedLines() +``` + +Let's say, for example, you want to remove trailing whitespace from all changed lines: + +```viml +:Glines s/\s\+$// +``` + + +### FAQ + +> Why can't I unstage staged changes? + +Unstaging staged hunks is feasible but not quite as easy as it sounds. There are three relevant versions of a file at any one time: + +1. The version at HEAD in the repo. +2. The version staged in the index. +3. The version in the working tree, in your vim buffer. + +`git-diff` without arguments shows you how 3 and 2 differ; this is what vim-gitgutter shows too. + +`git-diff --staged` shows you how 2 and 1 differ. + +Let's say you are looking at a file in vim which has some unstaged changes. Now you stage a hunk, either via vim-gitgutter or another means. The hunk is no longer marked in vim-gitgutter because it is the same in 3 and 2. + +Now you want to unstage that hunk. To see it, you need the difference between 2 and 1. For vim-gitgutter to show those differences, it would need to show you 2 instead of 3 in your vim buffer. But 2 is virtual so vim-gitgutter would need to handle it without touching 3. + +I intend to implement this but I can't commit to any deadline. + +> Why are the colours in the sign column weird? + +Your colorscheme is configuring the `SignColumn` highlight group weirdly. Please see the section above on customising the sign column. + +> There's a noticeable lag when vim-gitter runs; how can I avoid it? + +By default vim-gitgutter runs often so the signs are as accurate as possible. The delay is governed by `updatetime`; see [above](#when-are-the-signs-updated) for more information. + +If you don't want realtime updates and would like to trade a little accuracy for speed, add this to your `~/.vimrc`: + +```viml +let g:gitgutter_realtime = 0 +let g:gitgutter_eager = 0 +``` + +> What happens if I also use another plugin which uses signs (e.g. Syntastic)? + +Vim only allows one sign per line. Before adding a sign to a line, vim-gitgutter checks whether a sign has already been added by somebody else. If so it doesn't do anything. In other words vim-gitgutter won't overwrite another plugin's signs. It also won't remove another plugin's signs. + +> Why aren't any signs showing at all? + +Here are some things you can check: + +* `:echo system("git --version")` succeeds. +* Your git config is compatible with the version of git returned by the command above. +* Your Vim supports signs (`:echo has('signs')` should give `1`). +* Your file is being tracked by git and has unstaged changes. +* If your grep does not support the `color` flag, add `let g:gitgutter_grep_command = 'grep -e'` to your `~/.vimrc`. + + +### Shameless Plug + +If this plugin has helped you, or you'd like to learn more about Vim, why not check out this screencast I wrote for PeepCode: + +* [Smash Into Vim][siv] + +This was one of PeepCode's all-time top three bestsellers and is now available at Pluralsight. + +You can read reviews on my [website][airblade]. + + +### Intellectual Property + +Copyright Andrew Stewart, AirBlade Software Ltd. Released under the MIT licence. + + + [pathogen]: https://github.com/tpope/vim-pathogen + [siv]: http://pluralsight.com/training/Courses/TableOfContents/smash-into-vim + [airblade]: http://airbladesoftware.com/peepcode-vim + [macvim]: http://code.google.com/p/macvim/ diff --git a/bundle/gitgutter/autoload/gitgutter.vim b/bundle/gitgutter/autoload/gitgutter.vim new file mode 100644 index 0000000..0a05a6a --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter.vim @@ -0,0 +1,259 @@ +let s:nomodeline = (v:version > 703 || (v:version == 703 && has('patch442'))) ? '' : '' + +" Primary functions {{{ + +function! gitgutter#all() abort + for buffer_id in gitgutter#utility#dedup(tabpagebuflist()) + let file = expand('#' . buffer_id . ':p') + if !empty(file) + call gitgutter#process_buffer(buffer_id, 0) + endif + endfor +endfunction + +" bufnr: (integer) the buffer to process. +" realtime: (boolean) when truthy, do a realtime diff; otherwise do a disk-based diff. +function! gitgutter#process_buffer(bufnr, realtime) abort + call gitgutter#utility#use_known_shell() + + call gitgutter#utility#set_buffer(a:bufnr) + if gitgutter#utility#is_active() + if g:gitgutter_sign_column_always + call gitgutter#sign#add_dummy_sign() + endif + try + if !a:realtime || gitgutter#utility#has_fresh_changes() + let diff = gitgutter#diff#run_diff(a:realtime || gitgutter#utility#has_unsaved_changes(), 0) + if diff != 'async' + call gitgutter#handle_diff(diff) + endif + endif + catch /diff failed/ + call gitgutter#debug#log('diff failed') + call gitgutter#hunk#reset() + endtry + execute "silent doautocmd" s:nomodeline "User GitGutter" + else + call gitgutter#hunk#reset() + endif + + call gitgutter#utility#restore_shell() +endfunction + + +function! gitgutter#handle_diff(diff) abort + call gitgutter#debug#log(a:diff) + + call setbufvar(gitgutter#utility#bufnr(), 'gitgutter_tracked', 1) + + call gitgutter#hunk#set_hunks(gitgutter#diff#parse_diff(a:diff)) + let modified_lines = gitgutter#diff#process_hunks(gitgutter#hunk#hunks()) + + if len(modified_lines) > g:gitgutter_max_signs + call gitgutter#utility#warn_once('exceeded maximum number of signs (configured by g:gitgutter_max_signs).', 'max_signs') + call gitgutter#sign#clear_signs() + return + endif + + if g:gitgutter_signs || g:gitgutter_highlight_lines + call gitgutter#sign#update_signs(modified_lines) + endif + + call gitgutter#utility#save_last_seen_change() +endfunction + +function! gitgutter#disable() abort + " get list of all buffers (across all tabs) + let buflist = [] + for i in range(tabpagenr('$')) + call extend(buflist, tabpagebuflist(i + 1)) + endfor + + for buffer_id in gitgutter#utility#dedup(buflist) + let file = expand('#' . buffer_id . ':p') + if !empty(file) + call gitgutter#utility#set_buffer(buffer_id) + call gitgutter#sign#clear_signs() + call gitgutter#sign#remove_dummy_sign(1) + call gitgutter#hunk#reset() + endif + endfor + + let g:gitgutter_enabled = 0 +endfunction + +function! gitgutter#enable() abort + let g:gitgutter_enabled = 1 + call gitgutter#all() +endfunction + +function! gitgutter#toggle() abort + if g:gitgutter_enabled + call gitgutter#disable() + else + call gitgutter#enable() + endif +endfunction + +" }}} + +" Line highlights {{{ + +function! gitgutter#line_highlights_disable() abort + let g:gitgutter_highlight_lines = 0 + call gitgutter#highlight#define_sign_line_highlights() + + if !g:gitgutter_signs + call gitgutter#sign#clear_signs() + call gitgutter#sign#remove_dummy_sign(0) + endif + + redraw! +endfunction + +function! gitgutter#line_highlights_enable() abort + let old_highlight_lines = g:gitgutter_highlight_lines + + let g:gitgutter_highlight_lines = 1 + call gitgutter#highlight#define_sign_line_highlights() + + if !old_highlight_lines && !g:gitgutter_signs + call gitgutter#all() + endif + + redraw! +endfunction + +function! gitgutter#line_highlights_toggle() abort + if g:gitgutter_highlight_lines + call gitgutter#line_highlights_disable() + else + call gitgutter#line_highlights_enable() + endif +endfunction + +" }}} + +" Signs {{{ + +function! gitgutter#signs_enable() abort + let old_signs = g:gitgutter_signs + + let g:gitgutter_signs = 1 + call gitgutter#highlight#define_sign_text_highlights() + + if !old_signs && !g:gitgutter_highlight_lines + call gitgutter#all() + endif +endfunction + +function! gitgutter#signs_disable() abort + let g:gitgutter_signs = 0 + call gitgutter#highlight#define_sign_text_highlights() + + if !g:gitgutter_highlight_lines + call gitgutter#sign#clear_signs() + call gitgutter#sign#remove_dummy_sign(0) + endif +endfunction + +function! gitgutter#signs_toggle() abort + if g:gitgutter_signs + call gitgutter#signs_disable() + else + call gitgutter#signs_enable() + endif +endfunction + +" }}} + +" Hunks {{{ + +function! gitgutter#stage_hunk() abort + call gitgutter#utility#use_known_shell() + if gitgutter#utility#is_active() + " Ensure the working copy of the file is up to date. + " It doesn't make sense to stage a hunk otherwise. + noautocmd silent write + let diff = gitgutter#diff#run_diff(0, 1) + call gitgutter#handle_diff(diff) + + if empty(gitgutter#hunk#current_hunk()) + call gitgutter#utility#warn('cursor is not in a hunk') + else + let diff_for_hunk = gitgutter#diff#generate_diff_for_hunk(diff, 'stage') + call gitgutter#utility#system(gitgutter#utility#command_in_directory_of_file(g:gitgutter_git_executable.' apply --cached --unidiff-zero - '), diff_for_hunk) + + " refresh gitgutter's view of buffer + silent execute "GitGutter" + endif + + silent! call repeat#set("\GitGutterStageHunk", -1) + endif + call gitgutter#utility#restore_shell() +endfunction + +function! gitgutter#undo_hunk() abort + call gitgutter#utility#use_known_shell() + if gitgutter#utility#is_active() + " Ensure the working copy of the file is up to date. + " It doesn't make sense to stage a hunk otherwise. + noautocmd silent write + let diff = gitgutter#diff#run_diff(0, 1) + call gitgutter#handle_diff(diff) + + if empty(gitgutter#hunk#current_hunk()) + call gitgutter#utility#warn('cursor is not in a hunk') + else + let diff_for_hunk = gitgutter#diff#generate_diff_for_hunk(diff, 'undo') + call gitgutter#utility#system(gitgutter#utility#command_in_directory_of_file(g:gitgutter_git_executable.' apply --reverse --unidiff-zero - '), diff_for_hunk) + + " reload file preserving screen line position + " CTRL-Y and CTRL-E treat negative counts as positive counts. + let x = line('w0') + silent edit + let y = line('w0') + let z = x - y + if z > 0 + execute "normal! ".z."\" + else + execute "normal! ".z."\" + endif + endif + + silent! call repeat#set("\GitGutterUndoHunk", -1) + endif + call gitgutter#utility#restore_shell() +endfunction + +function! gitgutter#preview_hunk() abort + call gitgutter#utility#use_known_shell() + if gitgutter#utility#is_active() + " Ensure the working copy of the file is up to date. + " It doesn't make sense to stage a hunk otherwise. + noautocmd silent write + let diff = gitgutter#diff#run_diff(0, 1) + call gitgutter#handle_diff(diff) + + if empty(gitgutter#hunk#current_hunk()) + call gitgutter#utility#warn('cursor is not in a hunk') + else + let diff_for_hunk = gitgutter#diff#generate_diff_for_hunk(diff, 'preview') + + silent! wincmd P + if !&previewwindow + noautocmd execute 'bo' &previewheight 'new' + set previewwindow + endif + + setlocal noro modifiable filetype=diff buftype=nofile bufhidden=delete noswapfile + execute "%delete_" + call append(0, split(diff_for_hunk, "\n")) + + noautocmd wincmd p + endif + endif + call gitgutter#utility#restore_shell() +endfunction + +" }}} diff --git a/bundle/gitgutter/autoload/gitgutter/async.vim b/bundle/gitgutter/autoload/gitgutter/async.vim new file mode 100644 index 0000000..5b2428b --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter/async.vim @@ -0,0 +1,207 @@ +let s:jobs = {} + +" Nvim has always supported async commands. +" +" Vim introduced async in 7.4.1826. +" +" gVim didn't support aync until 7.4.1850 (though I haven't been able to +" verify this myself). +" +" MacVim-GUI didn't support async until 7.4.1832 (actually commit +" 88f4fe0 but 7.4.1832 was the first subsequent patch release). +let s:available = has('nvim') || ( + \ has('job') && ( + \ (has('patch-7-4-1826') && !has('gui_running')) || + \ (has('patch-7-4-1850') && has('gui_running')) || + \ (has('patch-7-4-1832') && has('gui_macvim')) + \ ) + \ ) + +function! gitgutter#async#available() + return s:available +endfunction + +function! gitgutter#async#execute(cmd) abort + let bufnr = gitgutter#utility#bufnr() + + if has('nvim') + if has('unix') + let command = ["sh", "-c", a:cmd] + elseif has('win32') + let command = ["cmd.exe", "/c", a:cmd] + else + throw 'unknown os' + endif + " Make the job use a shell while avoiding (un)quoting problems. + let job_id = jobstart(command, { + \ 'buffer': bufnr, + \ 'on_stdout': function('gitgutter#async#handle_diff_job_nvim'), + \ 'on_stderr': function('gitgutter#async#handle_diff_job_nvim'), + \ 'on_exit': function('gitgutter#async#handle_diff_job_nvim') + \ }) + call gitgutter#debug#log('[nvim job: '.job_id.', buffer: '.bufnr.'] '.a:cmd) + if job_id < 1 + throw 'diff failed' + endif + + " Note that when `cmd` doesn't produce any output, i.e. the diff is empty, + " the `stdout` event is not fired on the job handler. Therefore we keep + " track of the jobs ourselves so we can spot empty diffs. + call s:job_started(job_id) + + else + " Make the job use a shell. + " + " Pass a handler for stdout but not for stderr so that errors are + " ignored (and thus signs are not updated; this assumes that an error + " only occurs when a file is not tracked by git). + + if has('unix') + let command = ["sh", "-c", a:cmd] + elseif has('win32') + let command = "cmd.exe /c ".a:cmd + else + throw 'unknown os' + endif + + let job = job_start(command, { + \ 'out_cb': 'gitgutter#async#handle_diff_job_vim', + \ 'close_cb': 'gitgutter#async#handle_diff_job_vim_close' + \ }) + call gitgutter#debug#log('[vim job: '.string(job_info(job)).', buffer: '.bufnr.'] '.a:cmd) + + call s:job_started(s:channel_id(job_getchannel(job)), bufnr) + endif +endfunction + + +function! gitgutter#async#handle_diff_job_nvim(job_id, data, event) dict abort + call gitgutter#debug#log('job_id: '.a:job_id.', event: '.a:event.', buffer: '.self.buffer) + + let job_bufnr = self.buffer + if bufexists(job_bufnr) + let current_buffer = gitgutter#utility#bufnr() + call gitgutter#utility#set_buffer(job_bufnr) + + if a:event == 'stdout' + " a:data is a list + call s:job_finished(a:job_id) + if gitgutter#utility#is_active() + call gitgutter#handle_diff(gitgutter#utility#stringify(a:data)) + endif + + elseif a:event == 'exit' + " If the exit event is triggered without a preceding stdout event, + " the diff was empty. + if s:is_job_started(a:job_id) + if gitgutter#utility#is_active() + call gitgutter#handle_diff("") + endif + call s:job_finished(a:job_id) + endif + + else " a:event is stderr + call gitgutter#hunk#reset() + call s:job_finished(a:job_id) + + endif + + call gitgutter#utility#set_buffer(current_buffer) + else + call s:job_finished(a:job_id) + endif +endfunction + + +" Channel is in NL mode. +function! gitgutter#async#handle_diff_job_vim(channel, line) abort + call gitgutter#debug#log('channel: '.a:channel.', line: '.a:line) + + call s:accumulate_job_output(s:channel_id(a:channel), a:line) +endfunction + +function! gitgutter#async#handle_diff_job_vim_close(channel) abort + call gitgutter#debug#log('channel: '.a:channel) + + let channel_id = s:channel_id(a:channel) + let job_bufnr = s:job_buffer(channel_id) + + if bufexists(job_bufnr) + let current_buffer = gitgutter#utility#bufnr() + call gitgutter#utility#set_buffer(job_bufnr) + + if gitgutter#utility#is_active() + call gitgutter#handle_diff(s:job_output(channel_id)) + endif + + call gitgutter#utility#set_buffer(current_buffer) + endif + call s:job_finished(channel_id) +endfunction + + +function! s:channel_id(channel) abort + return ch_info(a:channel)['id'] +endfunction + + +" +" Keep track of jobs. +" +" nvim: receives all the job's output at once so we don't need to accumulate +" it ourselves. We can pass the buffer number into the job so we don't need +" to track that either. +" +" s:jobs {} -> key: job's id, value: anything truthy +" +" vim: receives the job's output line by line so we need to accumulate it. +" We also need to keep track of the buffer the job is running for. +" Vim job's don't have an id. Instead we could use the external process's id +" or the channel's id (there seems to be 1 channel per job). Arbitrarily +" choose the channel's id. +" +" s:jobs {} -> key: channel's id, value: {} key: output, value: [] job's output +" key: buffer: value: buffer number + + +" nvim: +" id: job's id +" +" vim: +" id: channel's id +" arg: buffer number +function! s:job_started(id, ...) abort + if a:0 " vim + let s:jobs[a:id] = {'output': [], 'buffer': a:1} + else " nvim + let s:jobs[a:id] = 1 + endif +endfunction + +function! s:is_job_started(id) abort + return has_key(s:jobs, a:id) +endfunction + +function! s:accumulate_job_output(id, line) abort + call add(s:jobs[a:id].output, a:line) +endfunction + +" Returns a string +function! s:job_output(id) abort + if has_key(s:jobs, a:id) + return gitgutter#utility#stringify(s:jobs[a:id].output) + else + return "" + endif +endfunction + +function! s:job_buffer(id) abort + return s:jobs[a:id].buffer +endfunction + +function! s:job_finished(id) abort + if has_key(s:jobs, a:id) + unlet s:jobs[a:id] + endif +endfunction + diff --git a/bundle/gitgutter/autoload/gitgutter/debug.vim b/bundle/gitgutter/autoload/gitgutter/debug.vim new file mode 100644 index 0000000..594f044 --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter/debug.vim @@ -0,0 +1,119 @@ +let s:plugin_dir = expand(':p:h:h:h').'/' +let s:log_file = s:plugin_dir.'gitgutter.log' +let s:channel_log = s:plugin_dir.'channel.log' +let s:new_log_session = 1 + + +function! gitgutter#debug#debug() + " Open a scratch buffer + vsplit __GitGutter_Debug__ + normal! ggdG + setlocal buftype=nofile + setlocal bufhidden=delete + setlocal noswapfile + + call gitgutter#debug#vim_version() + call gitgutter#debug#separator() + + call gitgutter#debug#git_version() + call gitgutter#debug#separator() + + call gitgutter#debug#grep_version() + call gitgutter#debug#separator() + + call gitgutter#debug#option('updatetime') + call gitgutter#debug#option('shell') + call gitgutter#debug#option('shellcmdflag') + call gitgutter#debug#option('shellpipe') + call gitgutter#debug#option('shellquote') + call gitgutter#debug#option('shellredir') + call gitgutter#debug#option('shellslash') + call gitgutter#debug#option('shelltemp') + call gitgutter#debug#option('shelltype') + call gitgutter#debug#option('shellxescape') + call gitgutter#debug#option('shellxquote') +endfunction + + +function! gitgutter#debug#separator() + call gitgutter#debug#output('') +endfunction + +function! gitgutter#debug#vim_version() + redir => version_info + silent execute 'version' + redir END + call gitgutter#debug#output(split(version_info, '\n')[0:2]) +endfunction + +function! gitgutter#debug#git_version() + let v = system(g:gitgutter_git_executable.' --version') + call gitgutter#debug#output( substitute(v, '\n$', '', '') ) +endfunction + +function! gitgutter#debug#grep_version() + let v = system('grep --version') + call gitgutter#debug#output( substitute(v, '\n$', '', '') ) + + let v = system('grep --help') + call gitgutter#debug#output( substitute(v, '\%x00', '', 'g') ) +endfunction + +function! gitgutter#debug#option(name) + if exists('+' . a:name) + let v = eval('&' . a:name) + call gitgutter#debug#output(a:name . '=' . v) + " redir => output + " silent execute "verbose set " . a:name . "?" + " redir END + " call gitgutter#debug#output(a:name . '=' . output) + else + call gitgutter#debug#output(a:name . ' [n/a]') + end +endfunction + +function! gitgutter#debug#output(text) + call append(line('$'), a:text) +endfunction + +" assumes optional args are calling function's optional args +function! gitgutter#debug#log(message, ...) abort + if g:gitgutter_log + if s:new_log_session && gitgutter#async#available() + if exists('*ch_logfile') + call ch_logfile(s:channel_log, 'w') + endif + endif + + execute 'redir >> '.s:log_file + if s:new_log_session + let s:start = reltime() + silent echo "\n==== start log session ====" + endif + + let elapsed = reltimestr(reltime(s:start)).' ' + silent echo '' + " callers excluding this function + silent echo elapsed.expand('')[:-22].':' + silent echo elapsed.s:format_for_log(a:message) + if a:0 && !empty(a:1) + for msg in a:000 + silent echo elapsed.s:format_for_log(msg) + endfor + endif + redir END + + let s:new_log_session = 0 + endif +endfunction + +function! s:format_for_log(data) abort + if type(a:data) == 1 + return join(split(a:data,'\n'),"\n") + elseif type(a:data) == 3 + return '['.join(a:data,"\n").']' + else + return a:data + endif +endfunction + diff --git a/bundle/gitgutter/autoload/gitgutter/diff.vim b/bundle/gitgutter/autoload/gitgutter/diff.vim new file mode 100644 index 0000000..170193b --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter/diff.vim @@ -0,0 +1,342 @@ +if exists('g:gitgutter_grep_command') + let s:grep_available = 1 + let s:grep_command = g:gitgutter_grep_command +else + let s:grep_available = executable('grep') + if s:grep_available + let s:grep_command = 'grep --color=never -e' + endif +endif +let s:hunk_re = '^@@ -\(\d\+\),\?\(\d*\) +\(\d\+\),\?\(\d*\) @@' + +let s:c_flag = gitgutter#utility#git_supports_command_line_config_override() + +let s:temp_index = tempname() +let s:temp_buffer = tempname() + +" Returns a diff of the buffer. +" +" The way to get the diff depends on whether the buffer is saved or unsaved. +" +" * Saved: the buffer contents is the same as the file on disk in the working +" tree so we simply do: +" +" git diff myfile +" +" * Unsaved: the buffer contents is not the same as the file on disk so we +" need to pass two instances of the file to git-diff: +" +" git diff myfileA myfileB +" +" The first instance is the file in the index which we obtain with: +" +" git show :myfile > myfileA +" +" The second instance is the buffer contents. Ideally we would pass this to +" git-diff on stdin via the second argument to vim's system() function. +" Unfortunately git-diff does not do CRLF conversion for input received on +" stdin, and git-show never performs CRLF conversion, so repos with CRLF +" conversion report that every line is modified due to mismatching EOLs. +" +" Instead, we write the buffer contents to a temporary file - myfileB in this +" example. Note the file extension must be preserved for the CRLF +" conversion to work. +" +" Before diffing a buffer for the first time, we check whether git knows about +" the file: +" +" git ls-files --error-unmatch myfile +" +" After running the diff we pass it through grep where available to reduce +" subsequent processing by the plugin. If grep is not available the plugin +" does the filtering instead. +function! gitgutter#diff#run_diff(realtime, preserve_full_diff) abort + " Wrap compound commands in parentheses to make Windows happy. + " bash doesn't mind the parentheses. + let cmd = '(' + + let bufnr = gitgutter#utility#bufnr() + let tracked = getbufvar(bufnr, 'gitgutter_tracked') " i.e. tracked by git + if !tracked + " Don't bother trying to realtime-diff an untracked file. + " NOTE: perhaps we should pull this guard up to the caller? + if a:realtime + throw 'diff failed' + else + let cmd .= g:gitgutter_git_executable.' ls-files --error-unmatch '.gitgutter#utility#shellescape(gitgutter#utility#filename()).' && (' + endif + endif + + if a:realtime + let blob_name = g:gitgutter_diff_base.':'.gitgutter#utility#shellescape(gitgutter#utility#file_relative_to_repo_root()) + let blob_file = s:temp_index + let buff_file = s:temp_buffer + let extension = gitgutter#utility#extension() + if !empty(extension) + let blob_file .= '.'.extension + let buff_file .= '.'.extension + endif + let cmd .= g:gitgutter_git_executable.' show '.blob_name.' > '.blob_file.' && ' + + " Writing the whole buffer resets the '[ and '] marks and also the + " 'modified' flag (if &cpoptions includes '+'). These are unwanted + " side-effects so we save and restore the values ourselves. + let modified = getbufvar(bufnr, "&mod") + let op_mark_start = getpos("'[") + let op_mark_end = getpos("']") + + execute 'keepalt noautocmd silent write!' buff_file + + call setbufvar(bufnr, "&mod", modified) + call setpos("'[", op_mark_start) + call setpos("']", op_mark_end) + endif + + let cmd .= g:gitgutter_git_executable + if s:c_flag + let cmd .= ' -c "diff.autorefreshindex=0"' + endif + let cmd .= ' diff --no-ext-diff --no-color -U0 '.g:gitgutter_diff_args.' ' + + if a:realtime + let cmd .= ' -- '.blob_file.' '.buff_file + else + let cmd .= g:gitgutter_diff_base.' -- '.gitgutter#utility#shellescape(gitgutter#utility#filename()) + endif + + if !a:preserve_full_diff && s:grep_available + let cmd .= ' | '.s:grep_command.' '.gitgutter#utility#shellescape('^@@ ') + endif + + if (!a:preserve_full_diff && s:grep_available) || a:realtime + " grep exits with 1 when no matches are found; diff exits with 1 when + " differences are found. However we want to treat non-matches and + " differences as non-erroneous behaviour; so we OR the command with one + " which always exits with success (0). + let cmd .= ' || exit 0' + endif + + let cmd .= ')' + + if !tracked + let cmd .= ')' + endif + + let cmd = gitgutter#utility#command_in_directory_of_file(cmd) + + if g:gitgutter_async && gitgutter#async#available() && !a:preserve_full_diff + call gitgutter#async#execute(cmd) + return 'async' + + else + let diff = gitgutter#utility#system(cmd) + + if gitgutter#utility#shell_error() + " A shell error indicates the file is not tracked by git (unless something bizarre is going on). + throw 'diff failed' + endif + + return diff + endif +endfunction + +function! gitgutter#diff#parse_diff(diff) abort + let hunks = [] + for line in split(a:diff, '\n') + let hunk_info = gitgutter#diff#parse_hunk(line) + if len(hunk_info) == 4 + call add(hunks, hunk_info) + endif + endfor + return hunks +endfunction + +function! gitgutter#diff#parse_hunk(line) abort + let matches = matchlist(a:line, s:hunk_re) + if len(matches) > 0 + let from_line = str2nr(matches[1]) + let from_count = (matches[2] == '') ? 1 : str2nr(matches[2]) + let to_line = str2nr(matches[3]) + let to_count = (matches[4] == '') ? 1 : str2nr(matches[4]) + return [from_line, from_count, to_line, to_count] + else + return [] + end +endfunction + +function! gitgutter#diff#process_hunks(hunks) abort + call gitgutter#hunk#reset() + let modified_lines = [] + for hunk in a:hunks + call extend(modified_lines, gitgutter#diff#process_hunk(hunk)) + endfor + return modified_lines +endfunction + +" Returns [ [, ], ...] +function! gitgutter#diff#process_hunk(hunk) abort + let modifications = [] + let from_line = a:hunk[0] + let from_count = a:hunk[1] + let to_line = a:hunk[2] + let to_count = a:hunk[3] + + if gitgutter#diff#is_added(from_count, to_count) + call gitgutter#diff#process_added(modifications, from_count, to_count, to_line) + call gitgutter#hunk#increment_lines_added(to_count) + + elseif gitgutter#diff#is_removed(from_count, to_count) + call gitgutter#diff#process_removed(modifications, from_count, to_count, to_line) + call gitgutter#hunk#increment_lines_removed(from_count) + + elseif gitgutter#diff#is_modified(from_count, to_count) + call gitgutter#diff#process_modified(modifications, from_count, to_count, to_line) + call gitgutter#hunk#increment_lines_modified(to_count) + + elseif gitgutter#diff#is_modified_and_added(from_count, to_count) + call gitgutter#diff#process_modified_and_added(modifications, from_count, to_count, to_line) + call gitgutter#hunk#increment_lines_added(to_count - from_count) + call gitgutter#hunk#increment_lines_modified(from_count) + + elseif gitgutter#diff#is_modified_and_removed(from_count, to_count) + call gitgutter#diff#process_modified_and_removed(modifications, from_count, to_count, to_line) + call gitgutter#hunk#increment_lines_modified(to_count) + call gitgutter#hunk#increment_lines_removed(from_count - to_count) + + endif + return modifications +endfunction + +function! gitgutter#diff#is_added(from_count, to_count) abort + return a:from_count == 0 && a:to_count > 0 +endfunction + +function! gitgutter#diff#is_removed(from_count, to_count) abort + return a:from_count > 0 && a:to_count == 0 +endfunction + +function! gitgutter#diff#is_modified(from_count, to_count) abort + return a:from_count > 0 && a:to_count > 0 && a:from_count == a:to_count +endfunction + +function! gitgutter#diff#is_modified_and_added(from_count, to_count) abort + return a:from_count > 0 && a:to_count > 0 && a:from_count < a:to_count +endfunction + +function! gitgutter#diff#is_modified_and_removed(from_count, to_count) abort + return a:from_count > 0 && a:to_count > 0 && a:from_count > a:to_count +endfunction + +function! gitgutter#diff#process_added(modifications, from_count, to_count, to_line) abort + let offset = 0 + while offset < a:to_count + let line_number = a:to_line + offset + call add(a:modifications, [line_number, 'added']) + let offset += 1 + endwhile +endfunction + +function! gitgutter#diff#process_removed(modifications, from_count, to_count, to_line) abort + if a:to_line == 0 + call add(a:modifications, [1, 'removed_first_line']) + else + call add(a:modifications, [a:to_line, 'removed']) + endif +endfunction + +function! gitgutter#diff#process_modified(modifications, from_count, to_count, to_line) abort + let offset = 0 + while offset < a:to_count + let line_number = a:to_line + offset + call add(a:modifications, [line_number, 'modified']) + let offset += 1 + endwhile +endfunction + +function! gitgutter#diff#process_modified_and_added(modifications, from_count, to_count, to_line) abort + let offset = 0 + while offset < a:from_count + let line_number = a:to_line + offset + call add(a:modifications, [line_number, 'modified']) + let offset += 1 + endwhile + while offset < a:to_count + let line_number = a:to_line + offset + call add(a:modifications, [line_number, 'added']) + let offset += 1 + endwhile +endfunction + +function! gitgutter#diff#process_modified_and_removed(modifications, from_count, to_count, to_line) abort + let offset = 0 + while offset < a:to_count + let line_number = a:to_line + offset + call add(a:modifications, [line_number, 'modified']) + let offset += 1 + endwhile + let a:modifications[-1] = [a:to_line + offset - 1, 'modified_removed'] +endfunction + +" Generates a zero-context diff for the current hunk. +" +" diff - the full diff for the buffer +" type - stage | undo | preview +function! gitgutter#diff#generate_diff_for_hunk(diff, type) abort + let diff_for_hunk = gitgutter#diff#discard_hunks(a:diff, a:type == 'stage' || a:type == 'undo') + + if a:type == 'stage' || a:type == 'undo' + let diff_for_hunk = gitgutter#diff#adjust_hunk_summary(diff_for_hunk, a:type == 'stage') + endif + + return diff_for_hunk +endfunction + +" Returns the diff with all hunks discarded except the current. +" +" diff - the diff to process +" keep_header - truthy to keep the diff header and hunk summary, falsy to discard it +function! gitgutter#diff#discard_hunks(diff, keep_header) abort + let modified_diff = [] + let keep_line = a:keep_header + for line in split(a:diff, '\n') + let hunk_info = gitgutter#diff#parse_hunk(line) + if len(hunk_info) == 4 " start of new hunk + let keep_line = gitgutter#hunk#cursor_in_hunk(hunk_info) + endif + if keep_line + call add(modified_diff, line) + endif + endfor + + if a:keep_header + return gitgutter#utility#stringify(modified_diff) + else + " Discard hunk summary too. + return gitgutter#utility#stringify(modified_diff[1:]) + endif +endfunction + +" Adjust hunk summary (from's / to's line number) to ignore changes above/before this one. +" +" diff_for_hunk - a diff containing only the hunk of interest +" staging - truthy if the hunk is to be staged, falsy if it is to be undone +" +" TODO: push this down to #discard_hunks? +function! gitgutter#diff#adjust_hunk_summary(diff_for_hunk, staging) abort + let line_adjustment = gitgutter#hunk#line_adjustment_for_current_hunk() + let adj_diff = [] + for line in split(a:diff_for_hunk, '\n') + if match(line, s:hunk_re) != -1 + if a:staging + " increment 'to' line number + let line = substitute(line, '+\@<=\(\d\+\)', '\=submatch(1)+line_adjustment', '') + else + " decrement 'from' line number + let line = substitute(line, '-\@<=\(\d\+\)', '\=submatch(1)-line_adjustment', '') + endif + endif + call add(adj_diff, line) + endfor + return gitgutter#utility#stringify(adj_diff) +endfunction + diff --git a/bundle/gitgutter/autoload/gitgutter/highlight.vim b/bundle/gitgutter/autoload/gitgutter/highlight.vim new file mode 100644 index 0000000..e3b774b --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter/highlight.vim @@ -0,0 +1,115 @@ +function! gitgutter#highlight#define_sign_column_highlight() abort + if g:gitgutter_override_sign_column_highlight + highlight! link SignColumn LineNr + else + highlight default link SignColumn LineNr + endif +endfunction + +function! gitgutter#highlight#define_highlights() abort + let [guibg, ctermbg] = gitgutter#highlight#get_background_colors('SignColumn') + + " Highlights used by the signs. + + execute "highlight GitGutterAddDefault guifg=#009900 guibg=" . guibg . " ctermfg=2 ctermbg=" . ctermbg + execute "highlight GitGutterChangeDefault guifg=#bbbb00 guibg=" . guibg . " ctermfg=3 ctermbg=" . ctermbg + execute "highlight GitGutterDeleteDefault guifg=#ff2222 guibg=" . guibg . " ctermfg=1 ctermbg=" . ctermbg + highlight default link GitGutterChangeDeleteDefault GitGutterChangeDefault + + execute "highlight GitGutterAddInvisible guifg=bg guibg=" . guibg . " ctermfg=" . ctermbg . " ctermbg=" . ctermbg + execute "highlight GitGutterChangeInvisible guifg=bg guibg=" . guibg . " ctermfg=" . ctermbg . " ctermbg=" . ctermbg + execute "highlight GitGutterDeleteInvisible guifg=bg guibg=" . guibg . " ctermfg=" . ctermbg . " ctermbg=" . ctermbg + highlight default link GitGutterChangeDeleteInvisible GitGutterChangeInvisble + + highlight default link GitGutterAdd GitGutterAddDefault + highlight default link GitGutterChange GitGutterChangeDefault + highlight default link GitGutterDelete GitGutterDeleteDefault + highlight default link GitGutterChangeDelete GitGutterChangeDeleteDefault + + " Highlights used for the whole line. + + highlight default link GitGutterAddLine DiffAdd + highlight default link GitGutterChangeLine DiffChange + highlight default link GitGutterDeleteLine DiffDelete + highlight default link GitGutterChangeDeleteLine GitGutterChangeLine +endfunction + +function! gitgutter#highlight#define_signs() abort + sign define GitGutterLineAdded + sign define GitGutterLineModified + sign define GitGutterLineRemoved + sign define GitGutterLineRemovedFirstLine + sign define GitGutterLineModifiedRemoved + sign define GitGutterDummy + + call gitgutter#highlight#define_sign_text() + call gitgutter#highlight#define_sign_text_highlights() + call gitgutter#highlight#define_sign_line_highlights() +endfunction + +function! gitgutter#highlight#define_sign_text() abort + execute "sign define GitGutterLineAdded text=" . g:gitgutter_sign_added + execute "sign define GitGutterLineModified text=" . g:gitgutter_sign_modified + execute "sign define GitGutterLineRemoved text=" . g:gitgutter_sign_removed + execute "sign define GitGutterLineRemovedFirstLine text=" . g:gitgutter_sign_removed_first_line + execute "sign define GitGutterLineModifiedRemoved text=" . g:gitgutter_sign_modified_removed +endfunction + +function! gitgutter#highlight#define_sign_text_highlights() abort + " Once a sign's text attribute has been defined, it cannot be undefined or + " set to an empty value. So to make signs' text disappear (when toggling + " off or disabling) we make them invisible by setting their foreground colours + " to the background's. + if g:gitgutter_signs + sign define GitGutterLineAdded texthl=GitGutterAdd + sign define GitGutterLineModified texthl=GitGutterChange + sign define GitGutterLineRemoved texthl=GitGutterDelete + sign define GitGutterLineRemovedFirstLine texthl=GitGutterDelete + sign define GitGutterLineModifiedRemoved texthl=GitGutterChangeDelete + else + sign define GitGutterLineAdded texthl=GitGutterAddInvisible + sign define GitGutterLineModified texthl=GitGutterChangeInvisible + sign define GitGutterLineRemoved texthl=GitGutterDeleteInvisible + sign define GitGutterLineRemovedFirstLine texthl=GitGutterDeleteInvisible + sign define GitGutterLineModifiedRemoved texthl=GitGutterChangeDeleteInvisible + endif +endfunction + +function! gitgutter#highlight#define_sign_line_highlights() abort + if g:gitgutter_highlight_lines + sign define GitGutterLineAdded linehl=GitGutterAddLine + sign define GitGutterLineModified linehl=GitGutterChangeLine + sign define GitGutterLineRemoved linehl=GitGutterDeleteLine + sign define GitGutterLineRemovedFirstLine linehl=GitGutterDeleteLine + sign define GitGutterLineModifiedRemoved linehl=GitGutterChangeDeleteLine + else + sign define GitGutterLineAdded linehl= + sign define GitGutterLineModified linehl= + sign define GitGutterLineRemoved linehl= + sign define GitGutterLineRemovedFirstLine linehl= + sign define GitGutterLineModifiedRemoved linehl= + endif +endfunction + +function! gitgutter#highlight#get_background_colors(group) abort + redir => highlight + silent execute 'silent highlight ' . a:group + redir END + + let link_matches = matchlist(highlight, 'links to \(\S\+\)') + if len(link_matches) > 0 " follow the link + return gitgutter#highlight#get_background_colors(link_matches[1]) + endif + + let ctermbg = gitgutter#highlight#match_highlight(highlight, 'ctermbg=\([0-9A-Za-z]\+\)') + let guibg = gitgutter#highlight#match_highlight(highlight, 'guibg=\([#0-9A-Za-z]\+\)') + return [guibg, ctermbg] +endfunction + +function! gitgutter#highlight#match_highlight(highlight, pattern) abort + let matches = matchlist(a:highlight, a:pattern) + if len(matches) == 0 + return 'NONE' + endif + return matches[1] +endfunction diff --git a/bundle/gitgutter/autoload/gitgutter/hunk.vim b/bundle/gitgutter/autoload/gitgutter/hunk.vim new file mode 100644 index 0000000..0fd0246 --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter/hunk.vim @@ -0,0 +1,137 @@ +let s:hunks = [] + +function! gitgutter#hunk#set_hunks(hunks) abort + let s:hunks = a:hunks +endfunction + +function! gitgutter#hunk#hunks() abort + return s:hunks +endfunction + +function! gitgutter#hunk#summary(bufnr) abort + return get(getbufvar(a:bufnr,''), 'gitgutter_summary', [0,0,0]) +endfunction + +function! gitgutter#hunk#reset() abort + call setbufvar(gitgutter#utility#bufnr(), 'gitgutter_summary', [0,0,0]) +endfunction + +function! gitgutter#hunk#increment_lines_added(count) abort + let bufnr = gitgutter#utility#bufnr() + let summary = gitgutter#hunk#summary(bufnr) + let summary[0] += a:count + call setbufvar(bufnr, 'gitgutter_summary', summary) +endfunction + +function! gitgutter#hunk#increment_lines_modified(count) abort + let bufnr = gitgutter#utility#bufnr() + let summary = gitgutter#hunk#summary(bufnr) + let summary[1] += a:count + call setbufvar(bufnr, 'gitgutter_summary', summary) +endfunction + +function! gitgutter#hunk#increment_lines_removed(count) abort + let bufnr = gitgutter#utility#bufnr() + let summary = gitgutter#hunk#summary(bufnr) + let summary[2] += a:count + call setbufvar(bufnr, 'gitgutter_summary', summary) +endfunction + +function! gitgutter#hunk#next_hunk(count) abort + if gitgutter#utility#is_active() + let current_line = line('.') + let hunk_count = 0 + for hunk in s:hunks + if hunk[2] > current_line + let hunk_count += 1 + if hunk_count == a:count + execute 'normal!' hunk[2] . 'G' + return + endif + endif + endfor + call gitgutter#utility#warn('No more hunks') + endif +endfunction + +function! gitgutter#hunk#prev_hunk(count) abort + if gitgutter#utility#is_active() + let current_line = line('.') + let hunk_count = 0 + for hunk in reverse(copy(s:hunks)) + if hunk[2] < current_line + let hunk_count += 1 + if hunk_count == a:count + let target = hunk[2] == 0 ? 1 : hunk[2] + execute 'normal!' target . 'G' + return + endif + endif + endfor + call gitgutter#utility#warn('No previous hunks') + endif +endfunction + +" Returns the hunk the cursor is currently in or an empty list if the cursor +" isn't in a hunk. +function! gitgutter#hunk#current_hunk() abort + let current_hunk = [] + + for hunk in s:hunks + if gitgutter#hunk#cursor_in_hunk(hunk) + let current_hunk = hunk + break + endif + endfor + + return current_hunk +endfunction + +function! gitgutter#hunk#cursor_in_hunk(hunk) abort + let current_line = line('.') + + if current_line == 1 && a:hunk[2] == 0 + return 1 + endif + + if current_line >= a:hunk[2] && current_line < a:hunk[2] + (a:hunk[3] == 0 ? 1 : a:hunk[3]) + return 1 + endif + + return 0 +endfunction + +" Returns the number of lines the current hunk is offset from where it would +" be if any changes above it in the file didn't exist. +function! gitgutter#hunk#line_adjustment_for_current_hunk() abort + let adj = 0 + for hunk in s:hunks + if gitgutter#hunk#cursor_in_hunk(hunk) + break + else + let adj += hunk[1] - hunk[3] + endif + endfor + return adj +endfunction + +function! gitgutter#hunk#text_object(inner) abort + let hunk = gitgutter#hunk#current_hunk() + + if empty(hunk) + return + endif + + let [first_line, last_line] = [hunk[2], hunk[2] + hunk[3] - 1] + + if ! a:inner + let lnum = last_line + let eof = line('$') + while lnum < eof && empty(getline(lnum + 1)) + let lnum +=1 + endwhile + let last_line = lnum + endif + + execute 'normal! 'first_line.'GV'.last_line.'G' +endfunction diff --git a/bundle/gitgutter/autoload/gitgutter/sign.vim b/bundle/gitgutter/autoload/gitgutter/sign.vim new file mode 100644 index 0000000..7e1218d --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter/sign.vim @@ -0,0 +1,179 @@ +" Vim doesn't namespace sign ids so every plugin shares the same +" namespace. Sign ids are simply integers so to avoid clashes with other +" signs we guess at a clear run. +" +" Note also we currently never reset s:next_sign_id. +let s:first_sign_id = 3000 +let s:next_sign_id = s:first_sign_id +let s:dummy_sign_id = s:first_sign_id - 1 +" Remove-all-signs optimisation requires Vim 7.3.596+. +let s:supports_star = v:version > 703 || (v:version == 703 && has("patch596")) + + +" Removes gitgutter's signs (excluding dummy sign) from the buffer being processed. +function! gitgutter#sign#clear_signs() abort + let bufnr = gitgutter#utility#bufnr() + call gitgutter#sign#find_current_signs() + + let sign_ids = map(values(getbufvar(bufnr, 'gitgutter_gitgutter_signs')), 'v:val.id') + call gitgutter#sign#remove_signs(sign_ids, 1) + call setbufvar(bufnr, 'gitgutter_gitgutter_signs', {}) +endfunction + + +" Updates gitgutter's signs in the buffer being processed. +" +" modified_lines: list of [, ] +" where name = 'added|removed|modified|modified_removed' +function! gitgutter#sign#update_signs(modified_lines) abort + call gitgutter#sign#find_current_signs() + + let new_gitgutter_signs_line_numbers = map(copy(a:modified_lines), 'v:val[0]') + let obsolete_signs = gitgutter#sign#obsolete_gitgutter_signs_to_remove(new_gitgutter_signs_line_numbers) + + let flicker_possible = s:remove_all_old_signs && !empty(a:modified_lines) + if flicker_possible + call gitgutter#sign#add_dummy_sign() + endif + + call gitgutter#sign#remove_signs(obsolete_signs, s:remove_all_old_signs) + call gitgutter#sign#upsert_new_gitgutter_signs(a:modified_lines) + + if flicker_possible + call gitgutter#sign#remove_dummy_sign(0) + endif +endfunction + + +function! gitgutter#sign#add_dummy_sign() abort + let bufnr = gitgutter#utility#bufnr() + if !getbufvar(bufnr, 'gitgutter_dummy_sign') + execute "sign place" s:dummy_sign_id "line=" . 9999 "name=GitGutterDummy buffer=" . bufnr + call setbufvar(bufnr, 'gitgutter_dummy_sign', 1) + endif +endfunction + +function! gitgutter#sign#remove_dummy_sign(force) abort + let bufnr = gitgutter#utility#bufnr() + if getbufvar(bufnr, 'gitgutter_dummy_sign') && (a:force || !g:gitgutter_sign_column_always) + execute "sign unplace" s:dummy_sign_id "buffer=" . bufnr + call setbufvar(bufnr, 'gitgutter_dummy_sign', 0) + endif +endfunction + + +" +" Internal functions +" + + +function! gitgutter#sign#find_current_signs() abort + let bufnr = gitgutter#utility#bufnr() + let gitgutter_signs = {} " : {'id': , 'name': } + let other_signs = [] " [ signs + silent execute "sign place buffer=" . bufnr + redir END + + for sign_line in filter(split(signs, '\n')[2:], 'v:val =~# "="') + " Typical sign line: line=88 id=1234 name=GitGutterLineAdded + " We assume splitting is faster than a regexp. + let components = split(sign_line) + let name = split(components[2], '=')[1] + if name =~# 'GitGutterDummy' + let dummy_sign_placed = 1 + else + let line_number = str2nr(split(components[0], '=')[1]) + if name =~# 'GitGutter' + let id = str2nr(split(components[1], '=')[1]) + " Remove orphaned signs (signs placed on lines which have been deleted). + " (When a line is deleted its sign lingers. Subsequent lines' signs' + " line numbers are decremented appropriately.) + if has_key(gitgutter_signs, line_number) + execute "sign unplace" gitgutter_signs[line_number].id + endif + let gitgutter_signs[line_number] = {'id': id, 'name': name} + else + call add(other_signs, line_number) + endif + end + endfor + + call setbufvar(bufnr, 'gitgutter_dummy_sign', dummy_sign_placed) + call setbufvar(bufnr, 'gitgutter_gitgutter_signs', gitgutter_signs) + call setbufvar(bufnr, 'gitgutter_other_signs', other_signs) +endfunction + + +" Returns a list of [, ...] +" Sets `s:remove_all_old_signs` as a side-effect. +function! gitgutter#sign#obsolete_gitgutter_signs_to_remove(new_gitgutter_signs_line_numbers) abort + let bufnr = gitgutter#utility#bufnr() + let signs_to_remove = [] " list of [, ...] + let remove_all_signs = 1 + let old_gitgutter_signs = getbufvar(bufnr, 'gitgutter_gitgutter_signs') + for line_number in keys(old_gitgutter_signs) + if index(a:new_gitgutter_signs_line_numbers, str2nr(line_number)) == -1 + call add(signs_to_remove, old_gitgutter_signs[line_number].id) + else + let remove_all_signs = 0 + endif + endfor + let s:remove_all_old_signs = remove_all_signs + return signs_to_remove +endfunction + + +function! gitgutter#sign#remove_signs(sign_ids, all_signs) abort + let bufnr = gitgutter#utility#bufnr() + if a:all_signs && s:supports_star && empty(getbufvar(bufnr, 'gitgutter_other_signs')) + let dummy_sign_present = getbufvar(bufnr, 'gitgutter_dummy_sign') + execute "sign unplace * buffer=" . bufnr + if dummy_sign_present + execute "sign place" s:dummy_sign_id "line=" . 9999 "name=GitGutterDummy buffer=" . bufnr + endif + else + for id in a:sign_ids + execute "sign unplace" id + endfor + endif +endfunction + + +function! gitgutter#sign#upsert_new_gitgutter_signs(modified_lines) abort + let bufnr = gitgutter#utility#bufnr() + let other_signs = getbufvar(bufnr, 'gitgutter_other_signs') + let old_gitgutter_signs = getbufvar(bufnr, 'gitgutter_gitgutter_signs') + + for line in a:modified_lines + let line_number = line[0] " + if index(other_signs, line_number) == -1 " don't clobber others' signs + let name = gitgutter#utility#highlight_name_for_change(line[1]) + if !has_key(old_gitgutter_signs, line_number) " insert + let id = gitgutter#sign#next_sign_id() + execute "sign place" id "line=" . line_number "name=" . name "buffer=" . bufnr + else " update if sign has changed + let old_sign = old_gitgutter_signs[line_number] + if old_sign.name !=# name + execute "sign place" old_sign.id "name=" . name "buffer=" . bufnr + end + endif + endif + endfor + " At this point b:gitgutter_gitgutter_signs is out of date. +endfunction + + +function! gitgutter#sign#next_sign_id() abort + let next_id = s:next_sign_id + let s:next_sign_id += 1 + return next_id +endfunction + + +" Only for testing. +function! gitgutter#sign#reset() + let s:next_sign_id = s:first_sign_id +endfunction diff --git a/bundle/gitgutter/autoload/gitgutter/utility.vim b/bundle/gitgutter/autoload/gitgutter/utility.vim new file mode 100644 index 0000000..684f92a --- /dev/null +++ b/bundle/gitgutter/autoload/gitgutter/utility.vim @@ -0,0 +1,208 @@ +let s:file = '' +let s:using_xolox_shell = -1 +let s:exit_code = 0 + +function! gitgutter#utility#warn(message) abort + echohl WarningMsg + echo 'vim-gitgutter: ' . a:message + echohl None + let v:warningmsg = a:message +endfunction + +function! gitgutter#utility#warn_once(message, key) abort + if empty(getbufvar(s:bufnr, a:key)) + call setbufvar(s:bufnr, a:key, '1') + echohl WarningMsg + redraw | echo 'vim-gitgutter: ' . a:message + echohl None + let v:warningmsg = a:message + endif +endfunction + +" Returns truthy when the buffer's file should be processed; and falsey when it shouldn't. +" This function does not and should not make any system calls. +function! gitgutter#utility#is_active() abort + return g:gitgutter_enabled && + \ !pumvisible() && + \ gitgutter#utility#is_file_buffer() && + \ gitgutter#utility#exists_file() && + \ gitgutter#utility#not_git_dir() +endfunction + +function! gitgutter#utility#not_git_dir() abort + return gitgutter#utility#full_path_to_directory_of_file() !~ '[/\\]\.git\($\|[/\\]\)' +endfunction + +function! gitgutter#utility#is_file_buffer() abort + return empty(getbufvar(s:bufnr, '&buftype')) +endfunction + +" A replacement for the built-in `shellescape(arg)`. +" +" Recent versions of Vim handle shell escaping pretty well. However older +" versions aren't as good. This attempts to do the right thing. +" +" See: +" https://github.com/tpope/vim-fugitive/blob/8f0b8edfbd246c0026b7a2388e1d883d579ac7f6/plugin/fugitive.vim#L29-L37 +function! gitgutter#utility#shellescape(arg) abort + if a:arg =~ '^[A-Za-z0-9_/.-]\+$' + return a:arg + elseif &shell =~# 'cmd' || gitgutter#utility#using_xolox_shell() + return '"' . substitute(substitute(a:arg, '"', '""', 'g'), '%', '"%"', 'g') . '"' + else + return shellescape(a:arg) + endif +endfunction + +function! gitgutter#utility#set_buffer(bufnr) abort + let s:bufnr = a:bufnr + let s:file = resolve(bufname(a:bufnr)) +endfunction + +function! gitgutter#utility#bufnr() + return s:bufnr +endfunction + +function! gitgutter#utility#file() + return s:file +endfunction + +function! gitgutter#utility#filename() abort + return fnamemodify(s:file, ':t') +endfunction + +function! gitgutter#utility#extension() abort + return fnamemodify(s:file, ':e') +endfunction + +function! gitgutter#utility#full_path_to_directory_of_file() abort + return fnamemodify(s:file, ':p:h') +endfunction + +function! gitgutter#utility#directory_of_file() abort + return fnamemodify(s:file, ':h') +endfunction + +function! gitgutter#utility#exists_file() abort + return filereadable(s:file) +endfunction + +function! gitgutter#utility#has_unsaved_changes() abort + return getbufvar(s:bufnr, "&mod") +endfunction + +function! gitgutter#utility#has_fresh_changes() abort + return getbufvar(s:bufnr, 'changedtick') != getbufvar(s:bufnr, 'gitgutter_last_tick') +endfunction + +function! gitgutter#utility#save_last_seen_change() abort + call setbufvar(s:bufnr, 'gitgutter_last_tick', getbufvar(s:bufnr, 'changedtick')) +endfunction + +function! gitgutter#utility#shell_error() abort + return gitgutter#utility#using_xolox_shell() ? s:exit_code : v:shell_error +endfunction + +function! gitgutter#utility#using_xolox_shell() abort + if s:using_xolox_shell == -1 + if !g:gitgutter_avoid_cmd_prompt_on_windows + let s:using_xolox_shell = 0 + " Although xolox/vim-shell works on both windows and unix we only want to use + " it on windows. + elseif has('win32') || has('win64') || has('win32unix') + let s:using_xolox_shell = exists('g:xolox#misc#version') && exists('g:xolox#shell#version') + else + let s:using_xolox_shell = 0 + endif + endif + return s:using_xolox_shell +endfunction + +function! gitgutter#utility#system(cmd, ...) abort + call gitgutter#debug#log(a:cmd, a:000) + + if gitgutter#utility#using_xolox_shell() + let options = {'command': a:cmd, 'check': 0} + if a:0 > 0 + let options['stdin'] = a:1 + endif + let ret = xolox#misc#os#exec(options) + let output = join(ret.stdout, "\n") + let s:exit_code = ret.exit_code + else + silent let output = (a:0 == 0) ? system(a:cmd) : system(a:cmd, a:1) + endif + return output +endfunction + +function! gitgutter#utility#file_relative_to_repo_root() abort + let file_path_relative_to_repo_root = getbufvar(s:bufnr, 'gitgutter_repo_relative_path') + if empty(file_path_relative_to_repo_root) + let dir_path_relative_to_repo_root = gitgutter#utility#system(gitgutter#utility#command_in_directory_of_file(g:gitgutter_git_executable.' rev-parse --show-prefix')) + let dir_path_relative_to_repo_root = gitgutter#utility#strip_trailing_new_line(dir_path_relative_to_repo_root) + let file_path_relative_to_repo_root = dir_path_relative_to_repo_root . gitgutter#utility#filename() + call setbufvar(s:bufnr, 'gitgutter_repo_relative_path', file_path_relative_to_repo_root) + endif + return file_path_relative_to_repo_root +endfunction + +function! gitgutter#utility#command_in_directory_of_file(cmd) abort + return 'cd '.gitgutter#utility#shellescape(gitgutter#utility#directory_of_file()).' && '.a:cmd +endfunction + +function! gitgutter#utility#highlight_name_for_change(text) abort + if a:text ==# 'added' + return 'GitGutterLineAdded' + elseif a:text ==# 'removed' + return 'GitGutterLineRemoved' + elseif a:text ==# 'removed_first_line' + return 'GitGutterLineRemovedFirstLine' + elseif a:text ==# 'modified' + return 'GitGutterLineModified' + elseif a:text ==# 'modified_removed' + return 'GitGutterLineModifiedRemoved' + endif +endfunction + +" Dedups list in-place. +" Assumes list has no empty entries. +function! gitgutter#utility#dedup(list) + return filter(sort(a:list), 'index(a:list, v:val, v:key + 1) == -1') +endfunction + +function! gitgutter#utility#strip_trailing_new_line(line) abort + return substitute(a:line, '\n$', '', '') +endfunction + +" True for git v1.7.2+. +function! gitgutter#utility#git_supports_command_line_config_override() abort + call system(g:gitgutter_git_executable.' -c foo.bar=baz --version') + return !v:shell_error +endfunction + +function! gitgutter#utility#stringify(list) abort + return join(a:list, "\n")."\n" +endfunction + +function! gitgutter#utility#use_known_shell() abort + if has('unix') + if &shell !=# 'sh' + let s:shell = &shell + let s:shellcmdflag = &shellcmdflag + let s:shellredir = &shellredir + let &shell = 'sh' + set shellcmdflag=-c + set shellredir=>%s\ 2>&1 + endif + endif +endfunction + +function! gitgutter#utility#restore_shell() abort + if has('unix') + if exists('s:shell') + let &shell = s:shell + let &shellcmdflag = s:shellcmdflag + let &shellredir = s:shellredir + endif + endif +endfunction diff --git a/bundle/gitgutter/doc/gitgutter.txt b/bundle/gitgutter/doc/gitgutter.txt new file mode 100644 index 0000000..6524564 --- /dev/null +++ b/bundle/gitgutter/doc/gitgutter.txt @@ -0,0 +1,341 @@ +*gitgutter.txt* A Vim plugin which shows a git diff in the gutter. + + + Vim Git Gutter + + +Author: Andy Stewart +Plugin Homepage: + +=============================================================================== +CONTENTS *GitGutterContents* + + 1. Introduction ................. |GitGutterIntroduction| + 2. Installation ................. |GitGutterInstallation| + 3. Usage ........................ |GitGutterUsage| + 4. Commands ..................... |GitGutterCommands| + 5. Autocommand .................. |GitGutterAutocmd| + 6. CUSTOMISATION................. |GitGutterCustomisation| + 7. FAQ .......................... |GitGutterFAQ| + +=============================================================================== +1. INTRODUCTION *GitGutterIntroduction* + *GitGutter* + +Vim Git Gutter is a Vim plugin which shows a git diff in the 'gutter' (sign +column). It shows whether each line has been added, modified, and where lines +have been removed. + +This is a port of the Git Gutter plugin for Sublime Text 2. + +=============================================================================== +2. INSTALLATION *GitGutterInstallation* + +* Pathogen: +> + cd ~/.vim/bundle + git clone git://github.com/airblade/vim-gitgutter.git +< +* Voom: + +Edit your plugin manifest (`voom edit`) and add: +> + airblade/vim-gitgutter +< +* VimPlug: + +Place this in your .vimrc: +> + Plug 'airblade/vim-gitgutter' +< +Then run the following in Vim: +> + :source % + :PlugInstall +< +* NeoBundle: + +Place this in your .vimrc: +> + NeoBundle 'airblade/vim-gitgutter' +< +Then run the following in Vim: +> + :source % + :NeoBundleInstall +< +* No plugin manager: + +Copy vim-gitgutter's subdirectories into your vim configuration directory: +> + cd tmp && git clone git://github.com/airblade/vim-gitgutter.git + cp vim-gitgutter/* ~/.vim/ +< +See |add-global-plugin|. + +=============================================================================== +3. USAGE *GitGutterUsage* + +You don't have to do anything: it just works. + +=============================================================================== +4. COMMANDS *GitGutterCommands* + +Commands for turning Git Gutter on and off: + + :GitGutterDisable *:GitGutterDisable* + Explicitly turn Git Gutter off. + + :GitGutterEnable *:GitGutterEnable* + Explicitly turn Git Gutter on. + + :GitGutterToggle *:GitGutterToggle* + Explicitly turn Git Gutter on if it was off and vice versa. + + :GitGutter *:GitGutter* + Update signs for the current buffer. + + :GitGutterAll *:GitGutterAll* + Update signs across all buffers. + +Commands for turning signs on and off (defaults to on): + + :GitGutterSignsEnable *:GitGutterSignsEnable* + Explicitly turn line signs on. + + :GitGutterSignsDisable *:GitGutterSignsDisable* + Explicitly turn line signs off. + + :GitGutterSignsToggle *:GitGutterSignsToggle* + Explicitly turn line signs on if it was off and vice versa. + +Commands for turning line highlighting on and off (defaults to off): + + :GitGutterLineHighlightsEnable *:GitGutterLineHighlightsEnable* + Explicitly turn line highlighting on. + + :GitGutterLineHighlightsDisable *:GitGutterLineHighlightsDisable* + Explicitly turn line highlighting off. + + :GitGutterLineHighlightsToggle *:GitGutterLineHighlightsToggle* + Explicitly turn line highlighting on if it was off and vice versa. + +Commands for jumping between marked hunks: + + :GitGutterNextHunk *:GitGutterNextHunk* + Jump to the next marked hunk. Takes a count. + + :GitGutterPrevHunk *:GitGutterPrevHunk* + Jump to the previous marked hunk. Takes a count. + +Commands for staging or undoing individual hunks: + + :GitGutterStageHunk *:GitGutterStageHunk* + Stage the hunk the cursor is in. + + :GitGutterUndoHunk *:GitGutterUndoHunk* + Undo the hunk the cursor is in. + + :GitGutterPreviewHunk *:GitGutterPreviewHunk* + Preview the hunk the cursor is in. + Use |:pclose| or |CTRL-W_CTRL-Z| to close the preview window. + +=============================================================================== +5. AUTOCOMMAND *GitGutterAutocmd* + +After updating a buffer's signs vim-gitgutter fires a |User| |autocmd| with the +event GitGutter. You can listen for this event, for example: +> + autocmd User GitGutter call updateMyStatusLine() +< + +=============================================================================== +6. CUSTOMISATION *GitGutterCustomisation* + +You can customise: + +- The sign column's colours +- The signs' colours and symbols +- Line highlights +- The base of the diff +- Extra arguments for git-diff +- Key mappings +- The grep executable used +- Whether or not vim-gitgutter is on initially (defaults to on) +- Whether or not signs are shown (defaults to yes) +- Whether or not line highlighting is on initially (defaults to off) +- Whether or not vim-gitgutter runs in realtime (defaults to yes) +- Whether or not vim-gitgutter runs eagerly (defaults to yes) +- Whether or not vim-gitgutter runs asynchronously (defaults to yes) + +Please note that vim-gitgutter won't override any colours or highlights you've +set in your colorscheme. + +SIGN COLUMN + +By default vim-gitgutter will make the sign column look like the line number +column (i.e. the |hl-LineNr| highlight group). + +To customise your sign column's background color, first tell vim-gitgutter to +leave it alone: +> + let g:gitgutter_override_sign_column_highlight = 0 +< + +And then either update your colorscheme's |hlSignColumn| highlight group or set +it in your |vimrc|: + + Desired appearance Command ~ + Same as line number column highlight clear SignColumn + User-defined (terminal Vim) highlight SignColumn ctermbg={whatever} + User-defined (graphical Vim) highlight SignColumn guibg={whatever} + +SIGNS' COLOURS AND SYMBOLS + +To customise the colours, set up the following highlight groups in your +colorscheme or |vimrc|: + +> + GitGutterAdd " an added line + GitGutterChange " a changed line + GitGutterDelete " at least one removed line + GitGutterChangeDelete " a changed line followed by at least one removed line +< + +You can either set these with `highlight GitGutterAdd {key}={arg}...` or link +them to existing highlight groups with, say: +> + highlight link GitGutterAdd DiffAdd +< + +To customise the symbols, add the following to your |vimrc|: +> + let g:gitgutter_sign_added = 'xx' + let g:gitgutter_sign_modified = 'yy' + let g:gitgutter_sign_removed = 'zz' + let g:gitgutter_sign_modified_removed = 'ww' +< + +LINE HIGHLIGHTS + +Similarly to the signs' colours, set up the following highlight groups in your +colorscheme or |vimrc|: +> + GitGutterAddLine " default: links to DiffAdd + GitGutterChangeLine " default: links to DiffChange + GitGutterDeleteLine " default: links to DiffDelete + GitGutterChangeDeleteLine " default: links to GitGutterChangeLineDefault +< + +THE BASE OF THE DIFF + +By default buffers are diffed against the index. To diff against a commit +instead: +> + let g:gitgutter_diff_base = '' +< + +EXTRA ARGUMENTS FOR GIT-DIFF + +To pass extra arguments to git-diff, add this to your |vimrc|: +> + let g:gitgutter_diff_args = '-w' +< + +KEY MAPPINGS + +To disable all key maps: +> + let g:gitgutter_map_keys = 0 +< + +To change the hunk-jumping maps (defaults shown): +> + nmap [c GitGutterPrevHunk + nmap ]c GitGutterNextHunk +< + +To change the hunk-staging/undoing/previewing maps (defaults shown): +> + nmap hs GitGutterStageHunk + nmap hu GitGutterUndoHunk + nmap hp GitGutterPreviewHunk +< + +To change the hunk text object maps (defaults shown): +> + omap ic GitGutterTextObjectInnerPending + omap ac GitGutterTextObjectOuterPending + xmap ic GitGutterTextObjectInnerVisual + xmap ac GitGutterTextObjectOuterVisual +< + +TO USE A CUSTOM GREP COMMAND + +To use a custom invocation for grep, use this: +> + let g:gitgutter_grep_command = 'grep --color=never -e' +< + +TO TURN OFF VIM-GITGUTTER BY DEFAULT + +Add to your |vimrc| +> + let g:gitgutter_enabled = 0 +< + +TO TURN OFF SIGNS BY DEFAULT + +Add to your |vimrc| +> + let g:gitgutter_signs = 0 +< + +Note that the sign column will still be present if you have line highlighting +switched on. + +TO TURN ON LINE HIGHLIGHTING BY DEFAULT + +Add to your |vimrc| +> + let g:gitgutter_highlight_lines = 1 +< + +TO STOP VIM-GITGUTTER RUNNING IN REALTIME + +Add to your |vimrc| +> + let g:gitgutter_realtime = 0 +< + +TO STOP VIM-GITGUTTER RUNNING EAGERLY + +Add to your |vimrc| +> + let g:gitgutter_eager = 0 +< + +TO TURN OFF ASYNCHRONOUS UPDATES + +By default diffs are run asynchronously. To run diffs synchronously +instead: + +Add to your |vimrc| +> +let g:gitgutter_async = 0 +< + +=============================================================================== +7. FAQ *GitGutterFAQ* + +a. Why are the colours in the sign column weird? + + Your colorscheme is configuring the |hl-SignColumn| highlight group weirdly. + Please see |GitGutterCustomisation| on customising the sign column. + +b. What happens if I also use another plugin which uses signs (e.g. Syntastic)? + + Vim only allows one sign per line. Before adding a sign to a line, + vim-gitgutter checks whether a sign has already been added by somebody else. + If so it doesn't do anything. In other words vim-gitgutter won't overwrite + another plugin's signs. It also won't remove another plugin's signs. diff --git a/bundle/gitgutter/plugin/gitgutter.vim b/bundle/gitgutter/plugin/gitgutter.vim new file mode 100644 index 0000000..eeaffb1 --- /dev/null +++ b/bundle/gitgutter/plugin/gitgutter.vim @@ -0,0 +1,241 @@ +scriptencoding utf-8 + +if exists('g:loaded_gitgutter') || !has('signs') || &cp + finish +endif +let g:loaded_gitgutter = 1 + +" Initialisation {{{ + +" Realtime sign updates require Vim 7.3.105+. +if v:version < 703 || (v:version == 703 && !has("patch105")) + let g:gitgutter_realtime = 0 +endif + +" Eager updates require gettabvar()/settabvar(). +if !exists("*gettabvar") + let g:gitgutter_eager = 0 +endif + +function! s:set(var, default) abort + if !exists(a:var) + if type(a:default) + execute 'let' a:var '=' string(a:default) + else + execute 'let' a:var '=' a:default + endif + endif +endfunction + +call s:set('g:gitgutter_enabled', 1) +call s:set('g:gitgutter_max_signs', 500) +call s:set('g:gitgutter_signs', 1) +call s:set('g:gitgutter_highlight_lines', 0) +call s:set('g:gitgutter_sign_column_always', 0) +call s:set('g:gitgutter_override_sign_column_highlight', 1) +call s:set('g:gitgutter_realtime', 1) +call s:set('g:gitgutter_eager', 1) +call s:set('g:gitgutter_sign_added', '+') +call s:set('g:gitgutter_sign_modified', '~') +call s:set('g:gitgutter_sign_removed', '_') +try + call s:set('g:gitgutter_sign_removed_first_line', '‾') +catch /E239/ + let g:gitgutter_sign_removed_first_line = '_^' +endtry + +call s:set('g:gitgutter_sign_modified_removed', '~_') +call s:set('g:gitgutter_diff_args', '') +call s:set('g:gitgutter_diff_base', '') +call s:set('g:gitgutter_map_keys', 1) +call s:set('g:gitgutter_avoid_cmd_prompt_on_windows', 1) +call s:set('g:gitgutter_async', 1) +call s:set('g:gitgutter_log', 0) +call s:set('g:gitgutter_git_executable', 'git') + +if !executable(g:gitgutter_git_executable) + call gitgutter#utility#warn('cannot find git. Please set g:gitgutter_git_executable.') +endif + +call gitgutter#highlight#define_sign_column_highlight() +call gitgutter#highlight#define_highlights() +call gitgutter#highlight#define_signs() + +" }}} + +" Primary functions {{{ + +command -bar GitGutterAll call gitgutter#all() +command -bar GitGutter call gitgutter#process_buffer(bufnr(''), 0) + +command -bar GitGutterDisable call gitgutter#disable() +command -bar GitGutterEnable call gitgutter#enable() +command -bar GitGutterToggle call gitgutter#toggle() + +" }}} + +" Line highlights {{{ + +command -bar GitGutterLineHighlightsDisable call gitgutter#line_highlights_disable() +command -bar GitGutterLineHighlightsEnable call gitgutter#line_highlights_enable() +command -bar GitGutterLineHighlightsToggle call gitgutter#line_highlights_toggle() + +" }}} + +" Signs {{{ + +command -bar GitGutterSignsEnable call gitgutter#signs_enable() +command -bar GitGutterSignsDisable call gitgutter#signs_disable() +command -bar GitGutterSignsToggle call gitgutter#signs_toggle() + +" }}} + +" Hunks {{{ + +command -bar -count=1 GitGutterNextHunk call gitgutter#hunk#next_hunk() +command -bar -count=1 GitGutterPrevHunk call gitgutter#hunk#prev_hunk() + +command -bar GitGutterStageHunk call gitgutter#stage_hunk() +command -bar GitGutterUndoHunk call gitgutter#undo_hunk() +command -bar GitGutterRevertHunk echomsg 'GitGutterRevertHunk is deprecated. Use GitGutterUndoHunk'call gitgutter#undo_hunk() +command -bar GitGutterPreviewHunk call gitgutter#preview_hunk() + +" Hunk text object +onoremap GitGutterTextObjectInnerPending :call gitgutter#hunk#text_object(1) +onoremap GitGutterTextObjectOuterPending :call gitgutter#hunk#text_object(0) +xnoremap GitGutterTextObjectInnerVisual :call gitgutter#hunk#text_object(1) +xnoremap GitGutterTextObjectOuterVisual :call gitgutter#hunk#text_object(0) + + +" Returns the git-diff hunks for the file or an empty list if there +" aren't any hunks. +" +" The return value is a list of lists. There is one inner list per hunk. +" +" [ +" [from_line, from_count, to_line, to_count], +" [from_line, from_count, to_line, to_count], +" ... +" ] +" +" where: +" +" `from` - refers to the staged file +" `to` - refers to the working tree's file +" `line` - refers to the line number where the change starts +" `count` - refers to the number of lines the change covers +function! GitGutterGetHunks() + return gitgutter#utility#is_active() ? gitgutter#hunk#hunks() : [] +endfunction + +" Returns an array that contains a summary of the hunk status for the current +" window. The format is [ added, modified, removed ], where each value +" represents the number of lines added/modified/removed respectively. +function! GitGutterGetHunkSummary() + return gitgutter#hunk#summary(winbufnr(0)) +endfunction + +" }}} + +command -bar GitGutterDebug call gitgutter#debug#debug() + +" Maps {{{ + +nnoremap GitGutterNextHunk &diff ? ']c' : ":\execute v:count1 . 'GitGutterNextHunk'\" +nnoremap GitGutterPrevHunk &diff ? '[c' : ":\execute v:count1 . 'GitGutterPrevHunk'\" + +if g:gitgutter_map_keys + if !hasmapto('GitGutterPrevHunk') && maparg('[c', 'n') ==# '' + nmap [c GitGutterPrevHunk + endif + if !hasmapto('GitGutterNextHunk') && maparg(']c', 'n') ==# '' + nmap ]c GitGutterNextHunk + endif +endif + + +nnoremap GitGutterStageHunk :GitGutterStageHunk +nnoremap GitGutterUndoHunk :GitGutterUndoHunk +nnoremap GitGutterPreviewHunk :GitGutterPreviewHunk + +if g:gitgutter_map_keys + if !hasmapto('GitGutterStageHunk') && maparg('hs', 'n') ==# '' + nmap hs GitGutterStageHunk + endif + if !hasmapto('GitGutterUndoHunk') && maparg('hu', 'n') ==# '' + nmap hu GitGutterUndoHunk + nmap hr GitGutterUndoHunk:echomsg 'hr is deprecated. Use hu' + endif + if !hasmapto('GitGutterPreviewHunk') && maparg('hp', 'n') ==# '' + nmap hp GitGutterPreviewHunk + endif + + if !hasmapto('GitGutterTextObjectInnerPending') && maparg('ic', 'o') ==# '' + omap ic GitGutterTextObjectInnerPending + endif + if !hasmapto('GitGutterTextObjectOuterPending') && maparg('ac', 'o') ==# '' + omap ac GitGutterTextObjectOuterPending + endif + if !hasmapto('GitGutterTextObjectInnerVisual') && maparg('ic', 'x') ==# '' + xmap ic GitGutterTextObjectInnerVisual + endif + if !hasmapto('GitGutterTextObjectOuterVisual') && maparg('ac', 'x') ==# '' + xmap ac GitGutterTextObjectOuterVisual + endif +endif + +" }}} + +" Autocommands {{{ + +augroup gitgutter + autocmd! + + if g:gitgutter_realtime + autocmd CursorHold,CursorHoldI * call gitgutter#process_buffer(bufnr(''), 1) + endif + + if g:gitgutter_eager + autocmd BufWritePost,FileChangedShellPost * call gitgutter#process_buffer(bufnr(''), 0) + + " When you enter a new tab, BufEnter is only fired if the buffer you enter + " is not the one you came from. + " + " For example: + " + " `:tab split` fires TabEnter but not BufEnter. + " `:tab new` fires TabEnter and BufEnter. + " + " As and when both TabEnter and BufEnter are fired, we do not want to + " process the entered buffer twice. We avoid this by setting and clearing + " a flag. + + autocmd BufEnter * + \ if gettabvar(tabpagenr(), 'gitgutter_didtabenter') | + \ call settabvar(tabpagenr(), 'gitgutter_didtabenter', 0) | + \ else | + \ call gitgutter#process_buffer(bufnr(''), 0) | + \ endif + + autocmd TabEnter * + \ call settabvar(tabpagenr(), 'gitgutter_didtabenter', 1) | + \ call gitgutter#all() + + if !has('gui_win32') + autocmd FocusGained * call gitgutter#all() + endif + + else + autocmd BufRead,BufWritePost,FileChangedShellPost * call gitgutter#process_buffer(bufnr(''), 0) + endif + + autocmd ColorScheme * call gitgutter#highlight#define_sign_column_highlight() | call gitgutter#highlight#define_highlights() + + " Disable during :vimgrep + autocmd QuickFixCmdPre *vimgrep* let g:gitgutter_enabled = 0 + autocmd QuickFixCmdPost *vimgrep* let g:gitgutter_enabled = 1 +augroup END + +" }}} + +" vim:set et sw=2 fdm=marker: diff --git a/bundle/gitgutter/screenshot.png b/bundle/gitgutter/screenshot.png new file mode 100644 index 0000000000000000000000000000000000000000..6b50f839ec91fd623e1191f8ada8c823740be041 GIT binary patch literal 16191 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 P9zj7?MW#y1H01vSr(8@| literal 0 HcmV?d00001 diff --git a/bundle/gitgutter/test/fixture.txt b/bundle/gitgutter/test/fixture.txt new file mode 100644 index 0000000..f5c6aff --- /dev/null +++ b/bundle/gitgutter/test/fixture.txt @@ -0,0 +1,11 @@ +a +b +c +d +e +f +g +h +i +j + diff --git a/bundle/gitgutter/test/runner.vim b/bundle/gitgutter/test/runner.vim new file mode 100644 index 0000000..630693c --- /dev/null +++ b/bundle/gitgutter/test/runner.vim @@ -0,0 +1,162 @@ +" +" Adapted from https://github.com/vim/vim/blob/master/src/testdir/runtest.vim +" +" When debugging tests it can help to write debug output: +" call Log('oh noes') +" + +function RunTest(test) + if exists("*SetUp") + call SetUp() + endif + + try + execute 'call '.a:test + catch + call Exception() + let s:errored = 1 + endtry + + if exists("*TearDown") + call TearDown() + endif +endfunction + +function Log(msg) + if type(a:msg) == type('') + call add(s:messages, a:msg) + elseif type(a:msg) == type([]) + call extend(s:messages, a:msg) + else + call add(v:errors, 'Exception: unsupported type: '.type(a:msg)) + endif +endfunction + +function Exception() + call add(v:errors, v:throwpoint.'..'.'Exception: '.v:exception) +endfunction + +" Shuffles list in place. +function Shuffle(list) + " Fisher-Yates-Durstenfeld-Knuth + let n = len(a:list) + if n < 2 + return a:list + endif + for i in range(0, n-2) + let j = Random(0, n-i-1) + let e = a:list[i] + let a:list[i] = a:list[i+j] + let a:list[i+j] = e + endfor + return a:list +endfunction + +" Returns a pseudorandom integer i such that 0 <= i <= max +function Random(min, max) + if has('unix') + let i = system('echo $RANDOM') " 0 <= i <= 32767 + else + let i = system('echo %RANDOM%') " 0 <= i <= 32767 + endif + return i * (a:max - a:min + 1) / 32768 + a:min +endfunction + +function FriendlyName(test_name) + return substitute(a:test_name[5:-3], '_', ' ', 'g') +endfunction + +function Align(left, right) + if type(a:right) == type([]) + let result = [] + for s in a:right + if empty(result) + call add(result, printf('%-'.s:indent.'S', a:left).s) + else + call add(result, printf('%-'.s:indent.'S', '').s) + endif + endfor + return result + endif + + return printf('%-'.s:indent.'S', a:left).a:right +endfunction + +let g:testname = expand('%') +let s:errored = 0 +let s:done = 0 +let s:fail = 0 +let s:errors = 0 +let s:messages = [] +let s:indent = '' + +call Log(g:testname.':') + +" Source the test script. +try + source % +catch + let s:errors += 1 + call Exception() +endtry + +" Locate the test functions. +set nomore +redir @q +silent function /^Test_ +redir END +let s:tests = split(substitute(@q, 'function \(\k*()\)', '\1', 'g')) + +" If there is another argument, filter test-functions' names against it. +if argc() > 1 + let s:tests = filter(s:tests, 'v:val =~ argv(1)') +endif + +let s:indent = max(map(copy(s:tests), {_, val -> len(FriendlyName(val))})) + +" Run the tests in random order. +for test in Shuffle(s:tests) + call RunTest(test) + let s:done += 1 + + let friendly_name = FriendlyName(test) + if len(v:errors) == 0 + call Log(Align(friendly_name, ' - ok')) + else + if s:errored + let s:errors += 1 + let s:errored = 0 + else + let s:fail += 1 + endif + call Log(Align(friendly_name, ' - not ok')) + + let i = 0 + for error in v:errors + if i != 0 + call Log(Align('',' ! ----')) + endif + for trace in reverse(split(error, '\.\.')) + call Log(Align('', ' ! '.trace)) + endfor + let i += 1 + endfor + + let v:errors = [] + endif +endfor + +let summary = [ + \ s:done.( s:done == 1 ? ' test' : ' tests'), + \ s:errors.(s:errors == 1 ? ' error' : ' errors'), + \ s:fail.( s:fail == 1 ? ' failure' : ' failures'), + \ ] +call Log('') +call Log(join(summary, ', ')) + +split messages.log +call append(line('$'), s:messages) +write + +qall! + diff --git a/bundle/gitgutter/test/test b/bundle/gitgutter/test/test new file mode 100755 index 0000000..6247a05 --- /dev/null +++ b/bundle/gitgutter/test/test @@ -0,0 +1,19 @@ +#!/usr/bin/env bash + +VIM="/Applications/MacVim.app/Contents/MacOS/Vim -v" + +$VIM -u NONE -U NONE -N \ + --cmd 'set rtp+=../' \ + --cmd 'let g:gitgutter_async=0' \ + --cmd 'source ../plugin/gitgutter.vim' \ + -S runner.vim \ + test_*.vim \ + $* + +cat messages.log + +grep -q "0 errors, 0 failures" messages.log +status=$? +rm messages.log +exit $status + diff --git a/bundle/gitgutter/test/test_gitgutter.vim b/bundle/gitgutter/test/test_gitgutter.vim new file mode 100644 index 0000000..1a65ed8 --- /dev/null +++ b/bundle/gitgutter/test/test_gitgutter.vim @@ -0,0 +1,400 @@ +let s:current_dir = expand('%:p:h') +let s:test_repo = s:current_dir.'/test-repo' +let s:bufnr = bufnr('') + +" +" Helpers +" + +function s:signs(filename) + redir => signs + silent execute 'sign place' + redir END + + let signs = split(signs, '\n') + + " filter out signs for this test file + " assumes a:filename's signs are last set listed + let i = index(signs, 'Signs for '.a:filename.':') + let signs = (i > -1 ? signs[i+1:] : []) + + call map(signs, {_, v -> substitute(v, ' ', '', '')}) + + return signs +endfunction + +function s:git_diff() + return split(system('git diff -U0 fixture.txt'), '\n') +endfunction + +function s:git_diff_staged() + return split(system('git diff -U0 --staged fixture.txt'), '\n') +endfunction + + +" +" SetUp / TearDown +" + +function SetUp() + call system("git init ".s:test_repo. + \ " && cd ".s:test_repo. + \ " && cp ../fixture.txt .". + \ " && git add . && git commit -m 'initial'") + execute ':cd' s:test_repo + edit! fixture.txt + call gitgutter#sign#reset() +endfunction + +function TearDown() + " delete all buffers except this one + " TODO: move to runner.vim, accounting for multiple test files + if s:bufnr > 1 + silent! execute '1,'.s:bufnr-1.'bdelete!' + endif + silent! execute s:bufnr+1.',$bdelete!' + + execute ':cd' s:current_dir + call system("rm -rf ".s:test_repo) +endfunction + +" +" The tests +" + +function Test_add_lines() + normal ggo* + write + + let expected = ["line=2 id=3000 name=GitGutterLineAdded"] + call assert_equal(expected, s:signs('fixture.txt')) +endfunction + + +function Test_add_lines_fish() + let _shell = &shell + set shell=/usr/local/bin/fish + + normal ggo* + write + + let expected = ["line=2 id=3000 name=GitGutterLineAdded"] + call assert_equal(expected, s:signs('fixture.txt')) + + let &shell = _shell +endfunction + + +function Test_modify_lines() + normal ggi* + write + + let expected = ["line=1 id=3000 name=GitGutterLineModified"] + call assert_equal(expected, s:signs('fixture.txt')) +endfunction + + +function Test_remove_lines() + execute '5d' + write + + let expected = ["line=4 id=3000 name=GitGutterLineRemoved"] + call assert_equal(expected, s:signs('fixture.txt')) +endfunction + + +function Test_remove_first_lines() + execute '1d' + write + + let expected = ["line=1 id=3000 name=GitGutterLineRemovedFirstLine"] + call assert_equal(expected, s:signs('fixture.txt')) +endfunction + + +function Test_edit_file_with_same_name_as_a_branch() + normal 5Gi* + call system('git checkout -b fixture.txt') + write + + let expected = ["line=5 id=3000 name=GitGutterLineModified"] + call assert_equal(expected, s:signs('fixture.txt')) +endfunction + + +function Test_file_added_to_git() + let tmpfile = 'fileAddedToGit.tmp' + call system('touch '.tmpfile.' && git add '.tmpfile) + execute 'edit '.tmpfile + normal ihello + write + + let expected = ["line=1 id=3000 name=GitGutterLineAdded"] + call assert_equal(expected, s:signs('fileAddedToGit.tmp')) +endfunction + + +function Test_filename_with_equals() + call system('touch =fixture=.txt && git add =fixture=.txt') + edit =fixture=.txt + normal ggo* + write + + let expected = [ + \ 'line=1 id=3000 name=GitGutterLineAdded', + \ 'line=2 id=3001 name=GitGutterLineAdded' + \ ] + call assert_equal(expected, s:signs('=fixture=.txt')) +endfunction + + +function Test_filename_with_square_brackets() + call system('touch fix[tu]re.txt && git add fix[tu]re.txt') + edit fix[tu]re.txt + normal ggo* + write + + let expected = [ + \ 'line=1 id=3000 name=GitGutterLineAdded', + \ 'line=2 id=3001 name=GitGutterLineAdded' + \ ] + call assert_equal(expected, s:signs('fix[tu]re.txt')) +endfunction + + +" FIXME: this test fails when it is the first (or only) test to be run +function Test_follow_symlink() + let tmp = 'symlink' + call system('ln -nfs fixture.txt '.tmp) + execute 'edit '.tmp + 6d + write + + let expected = ['line=5 id=3000 name=GitGutterLineRemoved'] + call assert_equal(expected, s:signs('symlink')) +endfunction + + +function Test_keep_alt() + enew + execute "normal! \" + + call assert_equal('fixture.txt', bufname('')) + call assert_equal('', bufname('#')) + + normal ggx + doautocmd CursorHold + + call assert_equal('', bufname('#')) +endfunction + + +function Test_keep_modified() + normal 5Go* + call assert_equal(1, getbufvar('', '&modified')) + + doautocmd CursorHold + + call assert_equal(1, getbufvar('', '&modified')) +endfunction + + +function Test_keep_op_marks() + normal 5Go* + call assert_equal([0,6,1,0], getpos("'[")) + call assert_equal([0,6,2,0], getpos("']")) + + doautocmd CursorHold + + call assert_equal([0,6,1,0], getpos("'[")) + call assert_equal([0,6,2,0], getpos("']")) +endfunction + + +function Test_no_modifications() + call assert_equal([], s:signs('fixture.txt')) +endfunction + + +function Test_orphaned_signs() + execute "normal 5GoX\Y" + write + 6d + write + + let expected = ['line=6 id=3001 name=GitGutterLineAdded'] + call assert_equal(expected, s:signs('fixture.txt')) +endfunction + + +function Test_sign_column_always() + let g:gitgutter_sign_column_always=1 + write + + let expected = ['line=9999 id=2999 name=GitGutterDummy'] + call assert_equal(expected, s:signs('fixture.txt')) + + let g:gitgutter_sign_column_always=0 +endfunction + + +function Test_untracked_file_outside_repo() + let tmp = tempname() + call system('touch '.tmp) + execute 'edit '.tmp + + call assert_equal([], s:signs(tmp)) +endfunction + + +function Test_untracked_file_within_repo() + let tmp = 'untrackedFileWithinRepo.tmp' + call system('touch '.tmp) + execute 'edit '.tmp + normal ggo* + doautocmd CursorHold + + call assert_equal([], s:signs(tmp)) + + call system('rm '.tmp) +endfunction + + +function Test_untracked_file_square_brackets_within_repo() + let tmp = '[un]trackedFileWithinRepo.tmp' + call system('touch '.tmp) + execute 'edit '.tmp + normal ggo* + doautocmd CursorHold + + call assert_equal([], s:signs(tmp)) + + call system('rm '.tmp) +endfunction + + +function Test_hunk_outside_noop() + normal 5G + GitGutterStageHunk + + call assert_equal([], s:signs('fixture.txt')) + call assert_equal([], s:git_diff()) + call assert_equal([], s:git_diff_staged()) + + GitGutterUndoHunk + + call assert_equal([], s:signs('fixture.txt')) + call assert_equal([], s:git_diff()) + call assert_equal([], s:git_diff_staged()) +endfunction + + +function Test_hunk_stage() + let _shell = &shell + set shell=foo + + normal 5Gi* + GitGutterStageHunk + + call assert_equal('foo', &shell) + let &shell = _shell + + call assert_equal([], s:signs('fixture.txt')) + + call assert_equal([], s:git_diff()) + + let expected = [ + \ 'diff --git a/fixture.txt b/fixture.txt', + \ 'index f5c6aff..ae8e546 100644', + \ '--- a/fixture.txt', + \ '+++ b/fixture.txt', + \ '@@ -5 +5 @@ d', + \ '-e', + \ '+*e' + \ ] + call assert_equal(expected, s:git_diff_staged()) +endfunction + + +function Test_hunk_stage_nearby_hunk() + execute "normal! 2Gox\y\z" + normal 2jdd + normal k + GitGutterStageHunk + + let expected = [ + \ 'line=3 id=3000 name=GitGutterLineAdded', + \ 'line=4 id=3001 name=GitGutterLineAdded', + \ 'line=5 id=3002 name=GitGutterLineAdded' + \ ] + call assert_equal(expected, s:signs('fixture.txt')) + + let expected = [ + \ 'diff --git a/fixture.txt b/fixture.txt', + \ 'index 53b13df..8fdfda7 100644', + \ '--- a/fixture.txt', + \ '+++ b/fixture.txt', + \ '@@ -2,0 +3,3 @@ b', + \ '+x', + \ '+y', + \ '+z', + \ ] + call assert_equal(expected, s:git_diff()) + + let expected = [ + \ 'diff --git a/fixture.txt b/fixture.txt', + \ 'index f5c6aff..53b13df 100644', + \ '--- a/fixture.txt', + \ '+++ b/fixture.txt', + \ '@@ -4 +3,0 @@ c', + \ '-d', + \ ] + call assert_equal(expected, s:git_diff_staged()) +endfunction + + +function Test_hunk_undo() + let _shell = &shell + set shell=foo + + normal 5Gi* + GitGutterUndoHunk + write " write file so we can verify git diff (--staged) + + call assert_equal('foo', &shell) + let &shell = _shell + + call assert_equal([], s:signs('fixture.txt')) + call assert_equal([], s:git_diff()) + call assert_equal([], s:git_diff_staged()) +endfunction + + +function Test_undo_nearby_hunk() + execute "normal! 2Gox\y\z" + normal 2jdd + normal k + GitGutterUndoHunk + write " write file so we can verify git diff (--staged) + + let expected = [ + \ 'line=3 id=3000 name=GitGutterLineAdded', + \ 'line=4 id=3001 name=GitGutterLineAdded', + \ 'line=5 id=3002 name=GitGutterLineAdded' + \ ] + call assert_equal(expected, s:signs('fixture.txt')) + + let expected = [ + \ 'diff --git a/fixture.txt b/fixture.txt', + \ 'index f5c6aff..3fbde56 100644', + \ '--- a/fixture.txt', + \ '+++ b/fixture.txt', + \ '@@ -2,0 +3,3 @@ b', + \ '+x', + \ '+y', + \ '+z', + \ ] + call assert_equal(expected, s:git_diff()) + + call assert_equal([], s:git_diff_staged()) +endfunction diff --git a/bundle/nerdtree-git-plugin/README.md b/bundle/nerdtree-git-plugin/README.md new file mode 100644 index 0000000..e60ff2f --- /dev/null +++ b/bundle/nerdtree-git-plugin/README.md @@ -0,0 +1,65 @@ +nerdtree-git-plugin +=================== + +A plugin of NERDTree showing git status flags. Works with the **LATEST** version of NERDTree. + +The original project [git-nerdtree](https://github.com/Xuyuanp/git-nerdtree) will not be maintained any longer. + + +![Imgur](http://i.imgur.com/jSCwGjU.gif?1) + +## Installation + +For Vundle + +`Plugin 'scrooloose/nerdtree'` + +`Plugin 'Xuyuanp/nerdtree-git-plugin'` + +For NeoBundle + +`NeoBundle 'scrooloose/nerdtree'` + +`NeoBundle 'Xuyuanp/nerdtree-git-plugin'` + +For Plug + +`Plug 'scrooloose/nerdtree'` + +`Plug 'Xuyuanp/nerdtree-git-plugin'` + + +## FAQ + +> Got error message like `Error detected while processing function +177[2]..178[22]..181[7]..144[9]..142[36]..238[4]..NERDTreeGitStatusRefreshListener[2]..NERDTreeGitStatusRefresh: +line 6: +E484: Can't open file /tmp/vZEZ6gM/1` while nerdtree opening in fish, how to resolve this problem? + +This was because that vim couldn't execute `system` function in `fish`. Add `set shell=sh` in your vimrc. + +This issue has been fixed. + +> How to config custom symbols? + +Use this variable to change symbols. + + ```vimscript + let g:NERDTreeIndicatorMapCustom = { + \ "Modified" : "✹", + \ "Staged" : "✚", + \ "Untracked" : "✭", + \ "Renamed" : "➜", + \ "Unmerged" : "═", + \ "Deleted" : "✖", + \ "Dirty" : "✗", + \ "Clean" : "✔︎", + \ "Unknown" : "?" + \ } + ``` + +## Credits + +* [scrooloose](https://github.com/scrooloose): Open API for me. +* [git_nerd](https://github.com/swerner/git_nerd): Where my idea comes from. +* [PickRelated](https://github.com/PickRelated): Add custom indicators & Review code. diff --git a/bundle/nerdtree-git-plugin/nerdtree_plugin/git_status.vim b/bundle/nerdtree-git-plugin/nerdtree_plugin/git_status.vim new file mode 100644 index 0000000..073f38c --- /dev/null +++ b/bundle/nerdtree-git-plugin/nerdtree_plugin/git_status.vim @@ -0,0 +1,340 @@ +" ============================================================================ +" File: git_status.vim +" Description: plugin for NERD Tree that provides git status support +" Maintainer: Xuyuan Pang +" Last Change: 4 Apr 2014 +" License: This program is free software. It comes without any warranty, +" to the extent permitted by applicable law. You can redistribute +" it and/or modify it under the terms of the Do What The Fuck You +" Want To Public License, Version 2, as published by Sam Hocevar. +" See http://sam.zoy.org/wtfpl/COPYING for more details. +" ============================================================================ +if exists('g:loaded_nerdtree_git_status') + finish +endif +let g:loaded_nerdtree_git_status = 1 + +if !exists('g:NERDTreeShowGitStatus') + let g:NERDTreeShowGitStatus = 1 +endif + +if g:NERDTreeShowGitStatus == 0 + finish +endif + +if !exists('g:NERDTreeMapNextHunk') + let g:NERDTreeMapNextHunk = ']c' +endif + +if !exists('g:NERDTreeMapPrevHunk') + let g:NERDTreeMapPrevHunk = '[c' +endif + +if !exists('g:NERDTreeUpdateOnWrite') + let g:NERDTreeUpdateOnWrite = 1 +endif + +if !exists('g:NERDTreeUpdateOnCursorHold') + let g:NERDTreeUpdateOnCursorHold = 1 +endif + +if !exists('s:NERDTreeIndicatorMap') + let s:NERDTreeIndicatorMap = { + \ 'Modified' : '✹', + \ 'Staged' : '✚', + \ 'Untracked' : '✭', + \ 'Renamed' : '➜', + \ 'Unmerged' : '═', + \ 'Deleted' : '✖', + \ 'Dirty' : '✗', + \ 'Clean' : '✔︎', + \ 'Unknown' : '?' + \ } +endif + + +function! NERDTreeGitStatusRefreshListener(event) + if !exists('b:NOT_A_GIT_REPOSITORY') + call g:NERDTreeGitStatusRefresh() + endif + let l:path = a:event.subject + let l:flag = g:NERDTreeGetGitStatusPrefix(l:path) + call l:path.flagSet.clearFlags('git') + if l:flag !=# '' + call l:path.flagSet.addFlag('git', l:flag) + endif +endfunction + +" FUNCTION: g:NERDTreeGitStatusRefresh() {{{2 +" refresh cached git status +function! g:NERDTreeGitStatusRefresh() + let b:NERDTreeCachedGitFileStatus = {} + let b:NERDTreeCachedGitDirtyDir = {} + let b:NOT_A_GIT_REPOSITORY = 1 + + let l:root = b:NERDTree.root.path.str() + let l:gitcmd = 'git -c color.status=false status -s' + if exists('g:NERDTreeGitStatusIgnoreSubmodules') + let l:gitcmd = l:gitcmd . ' --ignore-submodules' + if g:NERDTreeGitStatusIgnoreSubmodules ==# 'all' || g:NERDTreeGitStatusIgnoreSubmodules ==# 'dirty' || g:NERDTreeGitStatusIgnoreSubmodules ==# 'untracked' + let l:gitcmd = l:gitcmd . '=' . g:NERDTreeGitStatusIgnoreSubmodules + endif + endif + let l:statusesStr = system(l:gitcmd . ' ' . l:root) + let l:statusesSplit = split(l:statusesStr, '\n') + if l:statusesSplit != [] && l:statusesSplit[0] =~# 'fatal:.*' + let l:statusesSplit = [] + return + endif + let b:NOT_A_GIT_REPOSITORY = 0 + + for l:statusLine in l:statusesSplit + " cache git status of files + let l:pathStr = substitute(l:statusLine, '...', '', '') + let l:pathSplit = split(l:pathStr, ' -> ') + if len(l:pathSplit) == 2 + call s:NERDTreeCacheDirtyDir(l:pathSplit[0]) + let l:pathStr = l:pathSplit[1] + else + let l:pathStr = l:pathSplit[0] + endif + let l:pathStr = s:NERDTreeTrimDoubleQuotes(l:pathStr) + if l:pathStr =~# '\.\./.*' + continue + endif + let l:statusKey = s:NERDTreeGetFileGitStatusKey(l:statusLine[0], l:statusLine[1]) + let b:NERDTreeCachedGitFileStatus[fnameescape(l:pathStr)] = l:statusKey + + call s:NERDTreeCacheDirtyDir(l:pathStr) + endfor +endfunction + +function! s:NERDTreeCacheDirtyDir(pathStr) + " cache dirty dir + let l:dirtyPath = s:NERDTreeTrimDoubleQuotes(a:pathStr) + if l:dirtyPath =~# '\.\./.*' + return + endif + let l:dirtyPath = substitute(l:dirtyPath, '/[^/]*$', '/', '') + while l:dirtyPath =~# '.\+/.*' && has_key(b:NERDTreeCachedGitDirtyDir, fnameescape(l:dirtyPath)) == 0 + let b:NERDTreeCachedGitDirtyDir[fnameescape(l:dirtyPath)] = 'Dirty' + let l:dirtyPath = substitute(l:dirtyPath, '/[^/]*/$', '/', '') + endwhile +endfunction + +function! s:NERDTreeTrimDoubleQuotes(pathStr) + let l:toReturn = substitute(a:pathStr, '^"', '', '') + let l:toReturn = substitute(l:toReturn, '"$', '', '') + return l:toReturn +endfunction + +" FUNCTION: g:NERDTreeGetGitStatusPrefix(path) {{{2 +" return the indicator of the path +" Args: path +let s:GitStatusCacheTimeExpiry = 2 +let s:GitStatusCacheTime = 0 +function! g:NERDTreeGetGitStatusPrefix(path) + if localtime() - s:GitStatusCacheTime > s:GitStatusCacheTimeExpiry + let s:GitStatusCacheTime = localtime() + call g:NERDTreeGitStatusRefresh() + endif + let l:pathStr = a:path.str() + let l:cwd = b:NERDTree.root.path.str() . a:path.Slash() + if nerdtree#runningWindows() + let l:pathStr = a:path.WinToUnixPath(l:pathStr) + let l:cwd = a:path.WinToUnixPath(l:cwd) + endif + let l:pathStr = substitute(l:pathStr, fnameescape(l:cwd), '', '') + let l:statusKey = '' + if a:path.isDirectory + let l:statusKey = get(b:NERDTreeCachedGitDirtyDir, fnameescape(l:pathStr . '/'), '') + else + let l:statusKey = get(b:NERDTreeCachedGitFileStatus, fnameescape(l:pathStr), '') + endif + return s:NERDTreeGetIndicator(l:statusKey) +endfunction + +" FUNCTION: s:NERDTreeGetCWDGitStatus() {{{2 +" return the indicator of cwd +function! g:NERDTreeGetCWDGitStatus() + if b:NOT_A_GIT_REPOSITORY + return '' + elseif b:NERDTreeCachedGitDirtyDir == {} && b:NERDTreeCachedGitFileStatus == {} + return s:NERDTreeGetIndicator('Clean') + endif + return s:NERDTreeGetIndicator('Dirty') +endfunction + +function! s:NERDTreeGetIndicator(statusKey) + if exists('g:NERDTreeIndicatorMapCustom') + let l:indicator = get(g:NERDTreeIndicatorMapCustom, a:statusKey, '') + if l:indicator !=# '' + return l:indicator + endif + endif + let l:indicator = get(s:NERDTreeIndicatorMap, a:statusKey, '') + if l:indicator !=# '' + return l:indicator + endif + return '' +endfunction + +function! s:NERDTreeGetFileGitStatusKey(us, them) + if a:us ==# '?' && a:them ==# '?' + return 'Untracked' + elseif a:us ==# ' ' && a:them ==# 'M' + return 'Modified' + elseif a:us =~# '[MAC]' + return 'Staged' + elseif a:us ==# 'R' + return 'Renamed' + elseif a:us ==# 'U' || a:them ==# 'U' || a:us ==# 'A' && a:them ==# 'A' || a:us ==# 'D' && a:them ==# 'D' + return 'Unmerged' + elseif a:them ==# 'D' + return 'Deleted' + else + return 'Unknown' + endif +endfunction + +" FUNCTION: s:jumpToNextHunk(node) {{{2 +function! s:jumpToNextHunk(node) + let l:position = search('\[[^{RO}].*\]', '') + if l:position + call nerdtree#echo('Jump to next hunk ') + endif +endfunction + +" FUNCTION: s:jumpToPrevHunk(node) {{{2 +function! s:jumpToPrevHunk(node) + let l:position = search('\[[^{RO}].*\]', 'b') + if l:position + call nerdtree#echo('Jump to prev hunk ') + endif +endfunction + +" Function: s:SID() {{{2 +function s:SID() + if !exists('s:sid') + let s:sid = matchstr(expand(''), '\zs\d\+\ze_SID$') + endif + return s:sid +endfun + +" FUNCTION: s:NERDTreeGitStatusKeyMapping {{{2 +function! s:NERDTreeGitStatusKeyMapping() + let l:s = '' . s:SID() . '_' + + call NERDTreeAddKeyMap({ + \ 'key': g:NERDTreeMapNextHunk, + \ 'scope': 'Node', + \ 'callback': l:s.'jumpToNextHunk', + \ 'quickhelpText': 'Jump to next git hunk' }) + + call NERDTreeAddKeyMap({ + \ 'key': g:NERDTreeMapPrevHunk, + \ 'scope': 'Node', + \ 'callback': l:s.'jumpToPrevHunk', + \ 'quickhelpText': 'Jump to prev git hunk' }) + +endfunction + +augroup nerdtreegitplugin + autocmd CursorHold * silent! call s:CursorHoldUpdate() +augroup END +" FUNCTION: s:CursorHoldUpdate() {{{2 +function! s:CursorHoldUpdate() + if g:NERDTreeUpdateOnCursorHold != 1 + return + endif + + if !g:NERDTree.IsOpen() + return + endif + + " Do not update when a special buffer is selected + if !empty(&l:buftype) + return + endif + + let l:winnr = winnr() + let l:altwinnr = winnr('#') + + call g:NERDTree.CursorToTreeWin() + call b:NERDTree.root.refreshFlags() + call NERDTreeRender() + + exec l:altwinnr . 'wincmd w' + exec l:winnr . 'wincmd w' +endfunction + +augroup nerdtreegitplugin + autocmd BufWritePost * call s:FileUpdate(expand('%:p')) +augroup END +" FUNCTION: s:FileUpdate(fname) {{{2 +function! s:FileUpdate(fname) + if g:NERDTreeUpdateOnWrite != 1 + return + endif + + if !g:NERDTree.IsOpen() + return + endif + + let l:winnr = winnr() + let l:altwinnr = winnr('#') + + call g:NERDTree.CursorToTreeWin() + let l:node = b:NERDTree.root.findNode(g:NERDTreePath.New(a:fname)) + if l:node == {} + return + endif + call l:node.refreshFlags() + let l:node = l:node.parent + while !empty(l:node) + call l:node.refreshDirFlags() + let l:node = l:node.parent + endwhile + + call NERDTreeRender() + + exec l:altwinnr . 'wincmd w' + exec l:winnr . 'wincmd w' +endfunction + +augroup AddHighlighting + autocmd FileType nerdtree call s:AddHighlighting() +augroup END +function! s:AddHighlighting() + let l:synmap = { + \ 'NERDTreeGitStatusModified' : s:NERDTreeGetIndicator('Modified'), + \ 'NERDTreeGitStatusStaged' : s:NERDTreeGetIndicator('Staged'), + \ 'NERDTreeGitStatusUntracked' : s:NERDTreeGetIndicator('Untracked'), + \ 'NERDTreeGitStatusRenamed' : s:NERDTreeGetIndicator('Renamed'), + \ 'NERDTreeGitStatusDirDirty' : s:NERDTreeGetIndicator('Dirty'), + \ 'NERDTreeGitStatusDirClean' : s:NERDTreeGetIndicator('Clean') + \ } + + for l:name in keys(l:synmap) + exec 'syn match ' . l:name . ' #' . escape(l:synmap[l:name], '~') . '# containedin=NERDTreeFlags' + endfor + + hi def link NERDTreeGitStatusModified Special + hi def link NERDTreeGitStatusStaged Function + hi def link NERDTreeGitStatusRenamed Title + hi def link NERDTreeGitStatusUnmerged Label + hi def link NERDTreeGitStatusUntracked Comment + hi def link NERDTreeGitStatusDirDirty Tag + hi def link NERDTreeGitStatusDirClean DiffAdd +endfunction + +function! s:SetupListeners() + call g:NERDTreePathNotifier.AddListener('init', 'NERDTreeGitStatusRefreshListener') + call g:NERDTreePathNotifier.AddListener('refresh', 'NERDTreeGitStatusRefreshListener') + call g:NERDTreePathNotifier.AddListener('refreshFlags', 'NERDTreeGitStatusRefreshListener') +endfunction + +if g:NERDTreeShowGitStatus && executable('git') + call s:NERDTreeGitStatusKeyMapping() + call s:SetupListeners() +endif diff --git a/vimrc b/vimrc index 40e8e57..ed095ee 100644 --- a/vimrc +++ b/vimrc @@ -188,6 +188,10 @@ nnoremap gg :Git nnoremap gd :Gdiff +"------ Git Gutter Options ------ +"Disable h* commands as they show down movement +let g:gitgutter_map_keys = 0 + "------ Text Editing Utilities ------ " T = Delete all Trailing space in file map T :%s/\s\+$// @@ -337,7 +341,7 @@ if has("gui_running") endfunction elseif has("gui_gtk2") " Linux - set guifont=monospace\ 9 + set guifont=monospace\ 10 " Alt+n = new buffer map :enew From fa8b8a1ff45f9194175bb5dab310d6f1b8aff81c Mon Sep 17 00:00:00 2001 From: Thomas Hunter II Date: Sun, 27 Aug 2017 11:45:09 -0700 Subject: [PATCH 27/96] async/await syntax --- bundle/javascript/ISSUE_TEMPLATE.md | 12 + bundle/javascript/README.md | 117 +++++ .../javascript/after/ftplugin/javascript.vim | 12 + bundle/javascript/compiler/eslint.vim | 16 + bundle/javascript/extras/ctags | 8 + bundle/javascript/extras/flow.vim | 105 ++++ bundle/javascript/extras/jsdoc.vim | 39 ++ bundle/javascript/extras/ngdoc.vim | 3 + bundle/javascript/ftdetect/javascript.vim | 17 + bundle/javascript/indent/javascript.vim | 496 ++++++++++++++++++ bundle/javascript/syntax/javascript.vim | 394 ++++++++++++++ 11 files changed, 1219 insertions(+) create mode 100644 bundle/javascript/ISSUE_TEMPLATE.md create mode 100644 bundle/javascript/README.md create mode 100644 bundle/javascript/after/ftplugin/javascript.vim create mode 100644 bundle/javascript/compiler/eslint.vim create mode 100644 bundle/javascript/extras/ctags create mode 100644 bundle/javascript/extras/flow.vim create mode 100644 bundle/javascript/extras/jsdoc.vim create mode 100644 bundle/javascript/extras/ngdoc.vim create mode 100644 bundle/javascript/ftdetect/javascript.vim create mode 100644 bundle/javascript/indent/javascript.vim create mode 100644 bundle/javascript/syntax/javascript.vim diff --git a/bundle/javascript/ISSUE_TEMPLATE.md b/bundle/javascript/ISSUE_TEMPLATE.md new file mode 100644 index 0000000..155ea8d --- /dev/null +++ b/bundle/javascript/ISSUE_TEMPLATE.md @@ -0,0 +1,12 @@ +If you are reporting an issue that involves any JSX (e.g. +
{`${example}`}
), PLEASE PLEASE PLEASE make sure you have properly +setup and are sourcing this plugin https://github.com/mxw/vim-jsx + +WE DO NOT support JSX automatically, you need another plugin to add get this +functionality. + +If applicable, include a snippet of code that we can easily copy and paste that +replicates your bug. + +Make sure the bug still exists if you disable all other javascript plugins +except the one noted above, mxw/vim-jsx diff --git a/bundle/javascript/README.md b/bundle/javascript/README.md new file mode 100644 index 0000000..b60614f --- /dev/null +++ b/bundle/javascript/README.md @@ -0,0 +1,117 @@ +# vim-javascript + +JavaScript bundle for vim, this bundle provides syntax highlighting and +improved indentation. + + +## Installation + +### Install with [pathogen](https://github.com/tpope/vim-pathogen) + + git clone https://github.com/pangloss/vim-javascript.git ~/.vim/bundle/vim-javascript + +alternatively, use a package manager like [vim-plug](https://github.com/junegunn/vim-plug) + + +## Configuration Variables + +The following variables control certain syntax highlighting plugins. You can +add them to your `.vimrc` to enable their features. + +----------------- + +``` +let g:javascript_plugin_jsdoc = 1 +``` + +Enables syntax highlighting for [JSDocs](http://usejsdoc.org/). + +Default Value: 0 + +----------------- + +``` +let g:javascript_plugin_ngdoc = 1 +``` + +Enables some additional syntax highlighting for NGDocs. Requires JSDoc plugin +to be enabled as well. + +Default Value: 0 + +----------------- + +``` +let g:javascript_plugin_flow = 1 +``` + +Enables syntax highlighting for [Flow](https://flowtype.org/). + +Default Value: 0 + +----------------- + +``` +set foldmethod=syntax +``` + +Enables code folding based on our syntax file. + +Please note this can have a dramatic effect on performance and because it is a +global vim option, we do not set it ourselves. + + +## Concealing Characters + +You can customize concealing characters, if your font provides the glyph you want, by defining one or more of the following +variables: + + let g:javascript_conceal_function = "ƒ" + let g:javascript_conceal_null = "ø" + let g:javascript_conceal_this = "@" + let g:javascript_conceal_return = "⇚" + let g:javascript_conceal_undefined = "¿" + let g:javascript_conceal_NaN = "ℕ" + let g:javascript_conceal_prototype = "¶" + let g:javascript_conceal_static = "•" + let g:javascript_conceal_super = "Ω" + let g:javascript_conceal_arrow_function = "⇒" + let g:javascript_conceal_noarg_arrow_function = "🞅" + let g:javascript_conceal_underscore_arrow_function = "🞅" + + +You can enable concealing within VIM with: + + set conceallevel=1 + +OR if you wish to toggle concealing you may wish to bind a command such as the following which will map `l` (leader is usually the `\` key) to toggling conceal mode: + + map l :exec &conceallevel ? "set conceallevel=0" : "set conceallevel=1" + + +## Indentation Specific + +* `:h cino-:` +* `:h cino-=` +* `:h cino-star` +* `:h cino-(` +* `:h cino-w` +* `:h cino-W` +* `:h cino-U` +* `:h cino-m` +* `:h cino-M` +* `:h 'indentkeys'` + +## Contributing + +Please follow the general code style +guides (read the code) and in your pull request explain the reason for the +proposed change and how it is valuable. All p.r.'s will be reviewed by a +maintainer(s) then, hopefully, merged. + +Thank you! + + +## License + +Distributed under the same terms as Vim itself. See `:help license`. diff --git a/bundle/javascript/after/ftplugin/javascript.vim b/bundle/javascript/after/ftplugin/javascript.vim new file mode 100644 index 0000000..c6c42d6 --- /dev/null +++ b/bundle/javascript/after/ftplugin/javascript.vim @@ -0,0 +1,12 @@ +" Vim filetype plugin file +" Language: JavaScript +" Maintainer: vim-javascript community +" URL: https://github.com/pangloss/vim-javascript + +setlocal iskeyword+=$ suffixesadd+=.js + +if exists('b:undo_ftplugin') + let b:undo_ftplugin .= ' | setlocal iskeyword< suffixesadd<' +else + let b:undo_ftplugin = 'setlocal iskeyword< suffixesadd<' +endif diff --git a/bundle/javascript/compiler/eslint.vim b/bundle/javascript/compiler/eslint.vim new file mode 100644 index 0000000..7695a07 --- /dev/null +++ b/bundle/javascript/compiler/eslint.vim @@ -0,0 +1,16 @@ +" Vim compiler plugin +" Language: JavaScript +" Maintainer: vim-javascript community +" URL: https://github.com/pangloss/vim-javascript + +if exists("current_compiler") + finish +endif +let current_compiler = "eslint" + +if exists(":CompilerSet") != 2 + command! -nargs=* CompilerSet setlocal +endif + +CompilerSet makeprg=eslint\ -f\ compact\ % +CompilerSet errorformat=%f:\ line\ %l\\,\ col\ %c\\,\ %m diff --git a/bundle/javascript/extras/ctags b/bundle/javascript/extras/ctags new file mode 100644 index 0000000..cdc4edc --- /dev/null +++ b/bundle/javascript/extras/ctags @@ -0,0 +1,8 @@ +--langdef=js +--langmap=js:.js +--regex-js=/([A-Za-z0-9._$]+)[ \t]*[:=][ \t]*\{/\1/,object/ +--regex-js=/([A-Za-z0-9._$()]+)[ \t]*[:=][ \t]*function[ \t]*\(/\1/,function/ +--regex-js=/function[ \t]+([A-Za-z0-9._$]+)[ \t]*([^)])/\1/,function/ +--regex-js=/([A-Za-z0-9._$]+)[ \t]*[:=][ \t]*\[/\1/,array/ +--regex-js=/([^= ]+)[ \t]*=[ \t]*[^"]'[^']*/\1/,string/ +--regex-js=/([^= ]+)[ \t]*=[ \t]*[^']"[^"]*/\1/,string/ diff --git a/bundle/javascript/extras/flow.vim b/bundle/javascript/extras/flow.vim new file mode 100644 index 0000000..204fdbe --- /dev/null +++ b/bundle/javascript/extras/flow.vim @@ -0,0 +1,105 @@ +syntax region jsFlowDefinition contained start=/:/ end=/\%(\s*[,=;)\n]\)\@=/ contains=@jsFlowCluster containedin=jsParen +syntax region jsFlowArgumentDef contained start=/:/ end=/\%(\s*[,)]\|=>\@!\)\@=/ contains=@jsFlowCluster +syntax region jsFlowArray contained matchgroup=jsFlowNoise start=/\[/ end=/\]/ contains=@jsFlowCluster,jsComment fold +syntax region jsFlowObject contained matchgroup=jsFlowNoise start=/{/ end=/}/ contains=@jsFlowCluster,jsComment fold +syntax region jsFlowExactObject contained matchgroup=jsFlowNoise start=/{|/ end=/|}/ contains=@jsFlowCluster,jsComment fold +syntax region jsFlowParens contained matchgroup=jsFlowNoise start=/(/ end=/)/ contains=@jsFlowCluster keepend fold +syntax match jsFlowNoise contained /[:;,<>]/ +syntax keyword jsFlowType contained boolean number string null void any mixed JSON array Function object array bool class +syntax keyword jsFlowTypeof contained typeof skipempty skipempty nextgroup=jsFlowTypeCustom,jsFlowType +syntax match jsFlowTypeCustom contained /[0-9a-zA-Z_.]*/ skipwhite skipempty nextgroup=jsFlowGroup +syntax region jsFlowGroup contained matchgroup=jsFlowNoise start=// contains=@jsFlowCluster +syntax region jsFlowArrowArguments contained matchgroup=jsFlowNoise start=/(/ end=/)\%(\s*=>\)\@=/ oneline skipwhite skipempty nextgroup=jsFlowArrow contains=@jsFlowCluster +syntax match jsFlowArrow contained /=>/ skipwhite skipempty nextgroup=jsFlowType,jsFlowTypeCustom,jsFlowParens +syntax match jsFlowObjectKey contained /[0-9a-zA-Z_$?]*\(\s*:\)\@=/ contains=jsFunctionKey,jsFlowMaybe skipwhite skipempty nextgroup=jsObjectValue containedin=jsObject +syntax match jsFlowOrOperator contained /|/ skipwhite skipempty nextgroup=@jsFlowCluster +syntax keyword jsFlowImportType contained type skipwhite skipempty nextgroup=jsModuleAsterisk,jsModuleKeyword,jsModuleGroup +syntax match jsFlowWildcard contained /*/ + +syntax match jsFlowReturn contained /:\s*/ contains=jsFlowNoise skipwhite skipempty nextgroup=@jsFlowReturnCluster,jsFlowArrow,jsFlowReturnParens +syntax region jsFlowReturnObject contained matchgroup=jsFlowNoise start=/{/ end=/}/ contains=@jsFlowCluster skipwhite skipempty nextgroup=jsFuncBlock,jsFlowReturnOrOp fold +syntax region jsFlowReturnArray contained matchgroup=jsFlowNoise start=/\[/ end=/\]/ contains=@jsFlowCluster skipwhite skipempty nextgroup=jsFuncBlock,jsFlowReturnOrOp fold +syntax region jsFlowReturnParens contained matchgroup=jsFlowNoise start=/(/ end=/)/ contains=@jsFlowCluster skipwhite skipempty nextgroup=jsFuncBlock,jsFlowReturnOrOp,jsFlowReturnArrow fold +syntax match jsFlowReturnArrow contained /=>/ skipwhite skipempty nextgroup=@jsFlowReturnCluster +syntax match jsFlowReturnKeyword contained /\k\+/ contains=jsFlowType,jsFlowTypeCustom skipwhite skipempty nextgroup=jsFlowReturnGroup,jsFuncBlock,jsFlowReturnOrOp +syntax match jsFlowReturnMaybe contained /?/ skipwhite skipempty nextgroup=jsFlowReturnKeyword,jsFlowReturnObject +syntax region jsFlowReturnGroup contained matchgroup=jsFlowNoise start=// contains=@jsFlowCluster skipwhite skipempty nextgroup=jsFuncBlock,jsFlowReturnOrOp +syntax match jsFlowReturnOrOp contained /\s*|\s*/ skipwhite skipempty nextgroup=@jsFlowReturnCluster +syntax match jsFlowWildcardReturn contained /*/ skipwhite skipempty nextgroup=jsFuncBlock + +syntax region jsFlowFunctionGroup contained matchgroup=jsFlowNoise start=// contains=@jsFlowCluster skipwhite skipempty nextgroup=jsFuncArgs +syntax region jsFlowClassGroup contained matchgroup=jsFlowNoise start=// contains=@jsFlowCluster skipwhite skipempty nextgroup=jsClassBlock + +syntax region jsFlowTypeStatement start=/type\%(\s\+\k\)\@=/ end=/=\@=/ contains=jsFlowTypeOperator oneline skipwhite skipempty nextgroup=jsFlowTypeValue keepend +syntax region jsFlowTypeValue contained matchgroup=jsFlowNoise start=/=/ end=/[\n;]/ contains=@jsFlowCluster,jsFlowGroup,jsFlowMaybe +syntax match jsFlowTypeOperator contained /=/ containedin=jsFlowTypeValue +syntax match jsFlowTypeOperator contained /=/ +syntax keyword jsFlowTypeKeyword contained type + +syntax keyword jsFlowDeclare declare skipwhite skipempty nextgroup=jsFlowTypeStatement,jsClassDefinition,jsStorageClass,jsFlowModule,jsFlowInterface +syntax match jsFlowClassProperty contained /\<[0-9a-zA-Z_$]*\>:\@=/ skipwhite skipempty nextgroup=jsFlowClassDef containedin=jsClassBlock +syntax region jsFlowClassDef contained start=/:/ end=/\%(\s*[,=;)\n]\)\@=/ contains=@jsFlowCluster skipwhite skipempty nextgroup=jsClassValue + +syntax region jsFlowModule contained start=/module/ end=/{\@=/ skipempty skipempty nextgroup=jsFlowDeclareBlock contains=jsString +syntax region jsFlowInterface contained start=/interface/ end=/{\@=/ skipempty skipempty nextgroup=jsFlowInterfaceBlock contains=@jsFlowCluster +syntax region jsFlowDeclareBlock contained matchgroup=jsFlowNoise start=/{/ end=/}/ contains=jsFlowDeclare,jsFlowNoise fold + +" NOTE: It appears the nextgroup was causing a ton of breakages... testing it +" witout a nextgroup, but keeping this arround for reference incase something breaks +" syntax match jsFlowMaybe contained /?/ nextgroup=jsFlowType,jsFlowTypeCustom,jsFlowParens,jsFlowArrowArguments,jsFlowObject,jsFlowReturnObject extend keepend +syntax match jsFlowMaybe contained /?/ +syntax region jsFlowInterfaceBlock contained matchgroup=jsFlowNoise start=/{/ end=/}/ contains=jsObjectKey,jsObjectKeyString,jsObjectKeyComputed,jsObjectSeparator,jsObjectFuncName,jsObjectMethodType,jsGenerator,jsComment,jsObjectStringKey,jsSpreadExpression,jsFlowNoise keepend fold + +syntax region jsFlowParenAnnotation contained start=/:/ end=/[,=)]\@=/ containedin=jsParen contains=@jsFlowCluster + +syntax cluster jsFlowReturnCluster contains=jsFlowNoise,jsFlowReturnObject,jsFlowReturnArray,jsFlowReturnKeyword,jsFlowReturnGroup,jsFlowReturnMaybe,jsFlowReturnOrOp,jsFlowWildcardReturn,jsFlowReturnArrow +syntax cluster jsFlowCluster contains=jsFlowArray,jsFlowObject,jsFlowExactObject,jsFlowNoise,jsFlowTypeof,jsFlowType,jsFlowGroup,jsFlowArrowArguments,jsFlowMaybe,jsFlowParens,jsFlowOrOperator,jsFlowWildcard + +if version >= 508 || !exists("did_javascript_syn_inits") + if version < 508 + let did_javascript_syn_inits = 1 + command -nargs=+ HiLink hi link + else + command -nargs=+ HiLink hi def link + endif + HiLink jsFlowDefinition PreProc + HiLink jsFlowClassDef jsFlowDefinition + HiLink jsFlowArgumentDef jsFlowDefinition + HiLink jsFlowType Type + HiLink jsFlowTypeCustom PreProc + HiLink jsFlowTypeof PreProc + HiLink jsFlowArray PreProc + HiLink jsFlowObject PreProc + HiLink jsFlowExactObject PreProc + HiLink jsFlowParens PreProc + HiLink jsFlowGroup PreProc + HiLink jsFlowReturn PreProc + HiLink jsFlowParenAnnotation PreProc + HiLink jsFlowReturnObject jsFlowReturn + HiLink jsFlowReturnArray jsFlowArray + HiLink jsFlowReturnParens jsFlowParens + HiLink jsFlowReturnGroup jsFlowGroup + HiLink jsFlowFunctionGroup PreProc + HiLink jsFlowClassGroup PreProc + HiLink jsFlowArrowArguments PreProc + HiLink jsFlowArrow PreProc + HiLink jsFlowReturnArrow PreProc + HiLink jsFlowTypeStatement PreProc + HiLink jsFlowTypeKeyword PreProc + HiLink jsFlowTypeOperator Operator + HiLink jsFlowMaybe PreProc + HiLink jsFlowReturnMaybe PreProc + HiLink jsFlowClassProperty jsClassProperty + HiLink jsFlowDeclare PreProc + HiLink jsFlowModule PreProc + HiLink jsFlowInterface PreProc + HiLink jsFlowNoise Noise + HiLink jsFlowObjectKey jsObjectKey + HiLink jsFlowOrOperator jsOperator + HiLink jsFlowReturnOrOp jsFlowOrOperator + HiLink jsFlowWildcard PreProc + HiLink jsFlowWildcardReturn PreProc + HiLink jsFlowImportType PreProc + HiLink jsFlowTypeValue PreProc + delcommand HiLink +endif diff --git a/bundle/javascript/extras/jsdoc.vim b/bundle/javascript/extras/jsdoc.vim new file mode 100644 index 0000000..a19f3a3 --- /dev/null +++ b/bundle/javascript/extras/jsdoc.vim @@ -0,0 +1,39 @@ +"" syntax coloring for javadoc comments (HTML) +syntax region jsComment matchgroup=jsComment start="/\*\s*" end="\*/" contains=jsDocTags,jsCommentTodo,jsCvsTag,@jsHtml,@Spell fold + +" tags containing a param +syntax match jsDocTags contained "@\(alias\|api\|augments\|borrows\|class\|constructs\|default\|defaultvalue\|emits\|exception\|exports\|extends\|fires\|kind\|link\|listens\|member\|member[oO]f\|mixes\|module\|name\|namespace\|requires\|template\|throws\|var\|variation\|version\)\>" skipwhite nextgroup=jsDocParam +" tags containing type and param +syntax match jsDocTags contained "@\(arg\|argument\|cfg\|param\|property\|prop\|typedef\)\>" skipwhite nextgroup=jsDocType +" tags containing type but no param +syntax match jsDocTags contained "@\(callback\|define\|enum\|external\|implements\|this\|type\|return\|returns\)\>" skipwhite nextgroup=jsDocTypeNoParam +" tags containing references +syntax match jsDocTags contained "@\(lends\|see\|tutorial\)\>" skipwhite nextgroup=jsDocSeeTag +" other tags (no extra syntax) +syntax match jsDocTags contained "@\(abstract\|access\|accessor\|async\|author\|classdesc\|constant\|const\|constructor\|copyright\|deprecated\|desc\|description\|dict\|event\|example\|file\|file[oO]verview\|final\|function\|global\|ignore\|inheritDoc\|inner\|instance\|interface\|license\|localdoc\|method\|mixin\|nosideeffects\|override\|overview\|preserve\|private\|protected\|public\|readonly\|since\|static\|struct\|todo\|summary\|undocumented\|virtual\)\>" + +syntax region jsDocType contained matchgroup=jsDocTypeBrackets start="{" end="}" contains=jsDocTypeRecord oneline skipwhite nextgroup=jsDocParam +syntax match jsDocType contained "\%(#\|\"\|\w\|\.\|:\|\/\)\+" skipwhite nextgroup=jsDocParam +syntax region jsDocTypeRecord contained start=/{/ end=/}/ contains=jsDocTypeRecord extend +syntax region jsDocTypeRecord contained start=/\[/ end=/\]/ contains=jsDocTypeRecord extend +syntax region jsDocTypeNoParam contained start="{" end="}" oneline +syntax match jsDocTypeNoParam contained "\%(#\|\"\|\w\|\.\|:\|\/\)\+" +syntax match jsDocParam contained "\%(#\|\$\|-\|'\|\"\|{.\{-}}\|\w\|\.\|:\|\/\|\[.\{-}]\|=\)\+" +syntax region jsDocSeeTag contained matchgroup=jsDocSeeTag start="{" end="}" contains=jsDocTags + +if version >= 508 || !exists("did_javascript_syn_inits") + if version < 508 + let did_javascript_syn_inits = 1 + command -nargs=+ HiLink hi link + else + command -nargs=+ HiLink hi def link + endif + HiLink jsDocTags Special + HiLink jsDocSeeTag Function + HiLink jsDocType Type + HiLink jsDocTypeBrackets jsDocType + HiLink jsDocTypeRecord jsDocType + HiLink jsDocTypeNoParam Type + HiLink jsDocParam Label + delcommand HiLink +endif diff --git a/bundle/javascript/extras/ngdoc.vim b/bundle/javascript/extras/ngdoc.vim new file mode 100644 index 0000000..c513d87 --- /dev/null +++ b/bundle/javascript/extras/ngdoc.vim @@ -0,0 +1,3 @@ +syntax match jsDocTags contained /@\(link\|method[oO]f\|ngdoc\|ng[iI]nject\|restrict\)/ nextgroup=jsDocParam skipwhite +syntax match jsDocType contained "\%(#\|\$\|\w\|\"\|-\|\.\|:\|\/\)\+" nextgroup=jsDocParam skipwhite +syntax match jsDocParam contained "\%(#\|\$\|\w\|\"\|-\|\.\|:\|{\|}\|\/\|\[\|]\|=\)\+" diff --git a/bundle/javascript/ftdetect/javascript.vim b/bundle/javascript/ftdetect/javascript.vim new file mode 100644 index 0000000..ff07f4d --- /dev/null +++ b/bundle/javascript/ftdetect/javascript.vim @@ -0,0 +1,17 @@ +au BufNewFile,BufRead *.{js,mjs,jsm,es,es6},Jakefile setf javascript + +fun! s:SourceFlowSyntax() + if !exists('javascript_plugin_flow') && !exists('b:flow_active') && + \ search('\v\C%^\_s*%(//\s*|/\*[ \t\n*]*)\@flow>','nw') + runtime extras/flow.vim + let b:flow_active = 1 + endif +endfun +au FileType javascript au BufRead,BufWritePost call s:SourceFlowSyntax() + +fun! s:SelectJavascript() + if getline(1) =~# '^#!.*/bin/\%(env\s\+\)\?node\>' + set ft=javascript + endif +endfun +au BufNewFile,BufRead * call s:SelectJavascript() diff --git a/bundle/javascript/indent/javascript.vim b/bundle/javascript/indent/javascript.vim new file mode 100644 index 0000000..ce91645 --- /dev/null +++ b/bundle/javascript/indent/javascript.vim @@ -0,0 +1,496 @@ +" Vim indent file +" Language: Javascript +" Maintainer: Chris Paul ( https://github.com/bounceme ) +" URL: https://github.com/pangloss/vim-javascript +" Last Change: August 12, 2017 + +" Only load this indent file when no other was loaded. +if exists('b:did_indent') + finish +endif +let b:did_indent = 1 + +" indent correctly if inside -``` - -blocks in html files. - -## CoffeeScript in Haml - -CoffeeScript is highlighted within the `:coffeescript` filter in haml files: - -```haml -:coffeescript - console.log "hullo" -``` - -At this time, coffee indenting doesn't work in these blocks. - -## Custom Autocmds - -You can [define commands][autocmd-explain] to be ran automatically on these -custom events. - -In all cases, the name of the command running the event (`CoffeeCompile`, -`CoffeeWatch`, or `CoffeeRun`) is matched by the [`{pat}`][autocmd] argument. -You can match all commands with a `*` or only specific commands by separating -them with a comma: `CoffeeCompile,CoffeeWatch`. - -[autocmd-explain]: http://vimdoc.sourceforge.net/htmldoc/usr_40.html#40.3 -[autocmd]: http://vimdoc.sourceforge.net/htmldoc/autocmd.html#:autocmd - -#### CoffeeBufNew - -CoffeeBufNew is ran when a new scratch buffer is created. It's called from the -new buffer, so it can be used to do additional set up. - -```vim -augroup CoffeeBufNew - autocmd User * set wrap -augroup END -``` - -*Used By*: CoffeeCompile, CoffeeWatch, CoffeeRun - -#### CoffeeBufUpdate - -CoffeeBufUpdate is ran when a scratch buffer is updated with output from -`coffee`. It's called from the scratch buffer, so it can be used to alter the -compiled output. - -```vim -" Switch back to the source buffer after updating. -augroup CoffeeBufUpdate - autocmd User CoffeeCompile,CoffeeRun exec bufwinnr(b:coffee_src_buf) 'wincmd w' -augroup END -``` - -For example, to strip off the "Generated by" comment on the first line, put this -in your vimrc: - -```vim -function! s:RemoveGeneratedBy() - " If there was an error compiling, there's no comment to remove. - if v:shell_error - return - endif - - " Save cursor position. - let pos = getpos('.') - - " Remove first line. - set modifiable - 1 delete _ - set nomodifiable - - " Restore cursor position. - call setpos('.', pos) -endfunction - -augroup CoffeeBufUpdate - autocmd User CoffeeCompile,CoffeeWatch call s:RemoveGeneratedBy() -augroup END -``` - -*Used By*: CoffeeCompile, CoffeeWatch, CoffeeRun - -## Configuration Variables - -This is the full list of configuration variables available, with example -settings and default values. Use these in your vimrc to control the default -behavior. - -#### coffee\_indent\_keep\_current - -By default, the indent function matches the indent of the previous line if it -doesn't find a reason to indent or outdent. To change this behavior so it -instead keeps the [current indent of the cursor][98], use - - let coffee_indent_keep_current = 1 - -[98]: https://github.com/kchmck/vim-coffee-script/pull/98 - -*Default*: `unlet coffee_indent_keep_current` - -Note that if you change this after a coffee file has been loaded, you'll have to -reload the indent script for the change to take effect: - - unlet b:did_indent | runtime indent/coffee.vim - -#### coffee\_compiler - -Path to the `coffee` executable used by the `Coffee` commands: - - let coffee_compiler = '/usr/bin/coffee' - -*Default*: `'coffee'` (search `$PATH` for executable) - -#### coffee\_make\_options - -Options to pass to `coffee` with `:make`: - - let coffee_make_options = '--bare' - -*Default*: `''` (nothing) - -Note that `coffee_make_options` is embedded into `'makeprg'`, so `:compiler -coffee` must be ran after changing `coffee_make_options` for the changes to take -effect. - -#### coffee\_cake - -Path to the `cake` executable: - - let coffee_cake = '/opt/bin/cake' - -*Default*: `'cake'` (search `$PATH` for executable) - -#### coffee\_cake\_options - -Options to pass to `cake` with `:make`: - - let coffee_cake_options = 'build' - -*Default*: `''` (nothing) - -#### coffee\_linter - -Path to the `coffeelint` executable: - - let coffee_linter = '/opt/bin/coffeelint' - -*Default*: `'coffeelint'` (search `$PATH` for executable) - -#### coffee\_lint\_options - -Options to pass to `coffeelint`: - - let coffee_lint_options = '-f lint.json' - -*Default*: `''` (nothing) - -#### coffee\_compile\_vert - -Open the CoffeeCompile buffer with a vertical split instead of a horizontal -one: - - let coffee_compile_vert = 1 - -*Default*: `unlet coffee_compile_vert` - -#### coffee\_watch\_vert - -Open the CoffeeWatch buffer with a vertical split instead of a horizontal -one: - - let coffee_watch_vert = 1 - -*Default*: `unlet coffee_watch_vert` - -#### coffee\_run\_vert - -Open the CoffeeRun buffer with a vertical split instead of a horizontal -one: - - let coffee_run_vert = 1 - -*Default*: `unlet coffee_run_vert` - -## Configure Syntax Highlighting - -Add these lines to your vimrc to disable the relevant syntax group. - -#### Disable trailing whitespace error - -Trailing whitespace is highlighted as an error by default. This can be disabled -with: - - hi link coffeeSpaceError NONE - -#### Disable trailing semicolon error - -Trailing semicolons are considered an error (for help transitioning from -JavaScript.) This can be disabled with: - - hi link coffeeSemicolonError NONE - -#### Disable reserved words error - -Reserved words like `function` and `var` are highlighted as an error where -they're not allowed in CoffeeScript. This can be disabled with: - - hi link coffeeReservedError NONE - -## Tune Vim for CoffeeScript - -Changing these core settings can make vim more CoffeeScript friendly. - -#### Fold by indentation - -Folding by indentation works well for CoffeeScript functions and classes: - - ![Folding](http://i.imgur.com/gDgUBdO.png) - -To fold by indentation in CoffeeScript files, add this line to your vimrc: - - autocmd BufNewFile,BufReadPost *.coffee setl foldmethod=indent nofoldenable - -With this, folding is disabled by default but can be quickly toggled per-file -by hitting `zi`. To enable folding by default, remove `nofoldenable`: - - autocmd BufNewFile,BufReadPost *.coffee setl foldmethod=indent - -#### Two-space indentation - -To get standard two-space indentation in CoffeeScript files, add this line to -your vimrc: - - autocmd BufNewFile,BufReadPost *.coffee setl shiftwidth=2 expandtab diff --git a/bundle/coffee-script/Thanks.md b/bundle/coffee-script/Thanks.md deleted file mode 100755 index 8ddcf23..0000000 --- a/bundle/coffee-script/Thanks.md +++ /dev/null @@ -1,44 +0,0 @@ -Thanks to all bug reporters, and special thanks to those who have contributed -code: - - Brian Egan (brianegan): - Initial compiling support - - Ches Martin (ches): - Initial vim docs - - Chris Hoffman (cehoffman): - Add new keywoards from, to, and do - Highlight the - in negative integers - Add here regex highlighting, increase fold level for here docs - - David Wilhelm (bigfish): - CoffeeRun command - - Jay Adkisson (jayferd): - Support for eco templates - - Karl Guertin (grayrest) - Cakefiles are coffeescript - - Maciej Konieczny (narfdotpl): - Fix funny typo - - Matt Sacks (mattsa): - Javascript omni-completion - coffee_compile_vert option - - Nick Stenning (nickstenning): - Fold by indentation for coffeescript - - Simon Lipp (sloonz): - Trailing spaces are not error on lines containing only spaces - - Stéphan Kochen (stephank): - Initial HTML CoffeeScript highlighting - - Sven Felix Oberquelle (Svelix): - Haml CoffeeScript highlighting - - Wei Dai (clvv): - Fix the use of Vim built-in make command. diff --git a/bundle/coffee-script/Todo.md b/bundle/coffee-script/Todo.md deleted file mode 100755 index 3d4ffaa..0000000 --- a/bundle/coffee-script/Todo.md +++ /dev/null @@ -1 +0,0 @@ -- Don't highlight bad operator combinations diff --git a/bundle/coffee-script/after/indent/html.vim b/bundle/coffee-script/after/indent/html.vim deleted file mode 100755 index 2fa8637..0000000 --- a/bundle/coffee-script/after/indent/html.vim +++ /dev/null @@ -1,33 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -" Load the coffee and html indent functions. -silent! unlet b:did_indent -runtime indent/coffee.vim -let s:coffeeIndentExpr = &l:indentexpr - -" Load html last so it can overwrite coffee settings. -silent! unlet b:did_indent -runtime indent/html.vim -let s:htmlIndentExpr = &l:indentexpr - -" Inject our wrapper indent function. -setlocal indentexpr=GetCoffeeHtmlIndent(v:lnum) - -function! GetCoffeeHtmlIndent(curlinenum) - " See if we're inside a coffeescript block. - let scriptlnum = searchpair('', 'bWn') - let prevlnum = prevnonblank(a:curlinenum) - - " If we're in the script block and the previous line isn't the script tag - " itself, use coffee indenting. - if scriptlnum && scriptlnum != prevlnum - exec 'return ' s:coffeeIndentExpr - endif - - " Otherwise use html indenting. - exec 'return ' s:htmlIndentExpr -endfunction diff --git a/bundle/coffee-script/after/syntax/haml.vim b/bundle/coffee-script/after/syntax/haml.vim deleted file mode 100755 index 4c517eb..0000000 --- a/bundle/coffee-script/after/syntax/haml.vim +++ /dev/null @@ -1,13 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Sven Felix Oberquelle -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -" Inherit coffee from html so coffeeComment isn't redefined and given higher -" priority than hamlInterpolation. -syn cluster hamlCoffeescript contains=@htmlCoffeeScript -syn region hamlCoffeescriptFilter matchgroup=hamlFilter -\ start="^\z(\s*\):coffee\z(script\)\?\s*$" -\ end="^\%(\z1 \| *$\)\@!" -\ contains=@hamlCoffeeScript,hamlInterpolation -\ keepend diff --git a/bundle/coffee-script/after/syntax/html.vim b/bundle/coffee-script/after/syntax/html.vim deleted file mode 100755 index 82b44f1..0000000 --- a/bundle/coffee-script/after/syntax/html.vim +++ /dev/null @@ -1,11 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -" Syntax highlighting for text/coffeescript script tags -syn include @htmlCoffeeScript syntax/coffee.vim -syn region coffeeScript start=##me=s-1 keepend -\ contains=@htmlCoffeeScript,htmlScriptTag,@htmlPreproc -\ containedin=htmlHead diff --git a/bundle/coffee-script/autoload/coffee.vim b/bundle/coffee-script/autoload/coffee.vim deleted file mode 100755 index 8d72795..0000000 --- a/bundle/coffee-script/autoload/coffee.vim +++ /dev/null @@ -1,54 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -" Set up some common global/buffer variables. -function! coffee#CoffeeSetUpVariables() - " Path to coffee executable - if !exists('g:coffee_compiler') - let g:coffee_compiler = 'coffee' - endif - - " Options passed to coffee with make - if !exists('g:coffee_make_options') - let g:coffee_make_options = '' - endif - - " Path to cake executable - if !exists('g:coffee_cake') - let g:coffee_cake = 'cake' - endif - - " Extra options passed to cake - if !exists('g:coffee_cake_options') - let g:coffee_cake_options = '' - endif - - " Path to coffeelint executable - if !exists('g:coffee_linter') - let g:coffee_linter = 'coffeelint' - endif - - " Options passed to CoffeeLint - if !exists('g:coffee_lint_options') - let g:coffee_lint_options = '' - endif - - " Pass the litcoffee flag to tools in this buffer if a litcoffee file is open. - " Let the variable be overwritten so it can be updated if a different filetype - " is set. - if &filetype == 'litcoffee' - let b:coffee_litcoffee = '--literate' - else - let b:coffee_litcoffee = '' - endif -endfunction - -function! coffee#CoffeeSetUpErrorFormat() - CompilerSet errorformat=Error:\ In\ %f\\,\ %m\ on\ line\ %l, - \Error:\ In\ %f\\,\ Parse\ error\ on\ line\ %l:\ %m, - \SyntaxError:\ In\ %f\\,\ %m, - \%f:%l:%c:\ error:\ %m, - \%-G%.%# -endfunction diff --git a/bundle/coffee-script/compiler/cake.vim b/bundle/coffee-script/compiler/cake.vim deleted file mode 100755 index b49638e..0000000 --- a/bundle/coffee-script/compiler/cake.vim +++ /dev/null @@ -1,15 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -if exists('current_compiler') - finish -endif - -let current_compiler = 'cake' -call coffee#CoffeeSetUpVariables() - -exec 'CompilerSet makeprg=' . escape(g:coffee_cake . ' ' . -\ g:coffee_cake_options . ' $*', ' ') -call coffee#CoffeeSetUpErrorFormat() diff --git a/bundle/coffee-script/compiler/coffee.vim b/bundle/coffee-script/compiler/coffee.vim deleted file mode 100755 index 5a91457..0000000 --- a/bundle/coffee-script/compiler/coffee.vim +++ /dev/null @@ -1,82 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -" All this is needed to support compiling filenames with spaces, quotes, and -" such. The filename is escaped and embedded into the `makeprg` setting. -" -" Because of this, `makeprg` must be updated on every file rename. And because -" of that, `CompilerSet` can't be used because it doesn't exist when the -" rename autocmd is ran. So, we have to do some checks to see whether `compiler` -" was called locally or globally, and respect that in the rest of the script. - -if exists('current_compiler') - finish -endif - -let current_compiler = 'coffee' -call coffee#CoffeeSetUpVariables() - -" Pattern to check if coffee is the compiler -let s:pat = '^' . current_compiler - -" Get a `makeprg` for the current filename. -function! s:GetMakePrg() - return g:coffee_compiler . - \ ' -c' . - \ ' ' . b:coffee_litcoffee . - \ ' ' . g:coffee_make_options . - \ ' $*' . - \ ' ' . fnameescape(expand('%')) -endfunction - -" Set `makeprg` and return 1 if coffee is still the compiler, else return 0. -function! s:SetMakePrg() - if &l:makeprg =~ s:pat - let &l:makeprg = s:GetMakePrg() - elseif &g:makeprg =~ s:pat - let &g:makeprg = s:GetMakePrg() - else - return 0 - endif - - return 1 -endfunction - -" Set a dummy compiler so we can check whether to set locally or globally. -exec 'CompilerSet makeprg=' . current_compiler -" Then actually set the compiler. -call s:SetMakePrg() -call coffee#CoffeeSetUpErrorFormat() - -function! s:CoffeeMakeDeprecated(bang, args) - echoerr 'CoffeeMake is deprecated! Please use :make instead, its behavior ' . - \ 'is identical.' - sleep 5 - exec 'make' . a:bang a:args -endfunction - -" Compile the current file. -command! -bang -bar -nargs=* CoffeeMake -\ call s:CoffeeMakeDeprecated(, ) - -" Set `makeprg` on rename since we embed the filename in the setting. -augroup CoffeeUpdateMakePrg - autocmd! - - " Update `makeprg` if coffee is still the compiler, else stop running this - " function. - function! s:UpdateMakePrg() - if !s:SetMakePrg() - autocmd! CoffeeUpdateMakePrg - endif - endfunction - - " Set autocmd locally if compiler was set locally. - if &l:makeprg =~ s:pat - autocmd BufWritePre,BufFilePost call s:UpdateMakePrg() - else - autocmd BufWritePre,BufFilePost call s:UpdateMakePrg() - endif -augroup END diff --git a/bundle/coffee-script/doc/coffee-script.txt b/bundle/coffee-script/doc/coffee-script.txt deleted file mode 100755 index 1b43cf3..0000000 --- a/bundle/coffee-script/doc/coffee-script.txt +++ /dev/null @@ -1,4 +0,0 @@ -Please see the project readme for up-to-date docs: -https://github.com/kchmck/vim-coffee-script - - vim:tw=78:ts=8:ft=help:norl: diff --git a/bundle/coffee-script/ftdetect/coffee.vim b/bundle/coffee-script/ftdetect/coffee.vim deleted file mode 100755 index e6c4d69..0000000 --- a/bundle/coffee-script/ftdetect/coffee.vim +++ /dev/null @@ -1,17 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -autocmd BufNewFile,BufRead *.coffee set filetype=coffee -autocmd BufNewFile,BufRead *Cakefile set filetype=coffee -autocmd BufNewFile,BufRead *.coffeekup,*.ck set filetype=coffee -autocmd BufNewFile,BufRead *._coffee set filetype=coffee - -function! s:DetectCoffee() - if getline(1) =~ '^#!.*\' - set filetype=coffee - endif -endfunction - -autocmd BufNewFile,BufRead * call s:DetectCoffee() diff --git a/bundle/coffee-script/ftplugin/coffee.vim b/bundle/coffee-script/ftplugin/coffee.vim deleted file mode 100755 index 347155a..0000000 --- a/bundle/coffee-script/ftplugin/coffee.vim +++ /dev/null @@ -1,405 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -if exists('b:did_ftplugin') - finish -endif - -let b:did_ftplugin = 1 -call coffee#CoffeeSetUpVariables() - -setlocal formatoptions-=t formatoptions+=croql -setlocal comments=:# commentstring=#\ %s -setlocal omnifunc=javascriptcomplete#CompleteJS -setlocal suffixesadd+=coffee - -" Create custom augroups. -augroup CoffeeBufUpdate | augroup END -augroup CoffeeBufNew | augroup END - -" Enable coffee compiler if a compiler isn't set already. -if !len(&l:makeprg) - compiler coffee -endif - -" Switch to the window for buf. -function! s:SwitchWindow(buf) - exec bufwinnr(a:buf) 'wincmd w' -endfunction - -" Create a new scratch buffer and return the bufnr of it. After the function -" returns, vim remains in the scratch buffer so more set up can be done. -function! s:ScratchBufBuild(src, vert, size) - if a:size <= 0 - if a:vert - let size = winwidth(bufwinnr(a:src)) / 2 - else - let size = winheight(bufwinnr(a:src)) / 2 - endif - endif - - if a:vert - vertical belowright new - exec 'vertical resize' size - else - belowright new - exec 'resize' size - endif - - setlocal bufhidden=wipe buftype=nofile nobuflisted noswapfile nomodifiable - nnoremap q :hide - - return bufnr('%') -endfunction - -" Replace buffer contents with text and delete the last empty line. -function! s:ScratchBufUpdate(buf, text) - " Move to the scratch buffer. - call s:SwitchWindow(a:buf) - - " Double check we're in the scratch buffer before overwriting. - if bufnr('%') != a:buf - throw 'unable to change to scratch buffer' - endif - - setlocal modifiable - silent exec '% delete _' - silent put! =a:text - silent exec '$ delete _' - setlocal nomodifiable -endfunction - -" Parse the output of coffee into a qflist entry for src buffer. -function! s:ParseCoffeeError(output, src, startline) - " Coffee error is always on first line? - let match = matchlist(a:output, - \ '^\(\f\+\|\[stdin\]\):\(\d\):\(\d\): error: \(.\{-}\)' . "\n") - - if !len(match) - return - endif - - " Consider the line number from coffee as relative and add it to the beginning - " line number of the range the command was called on, then subtract one for - " zero-based relativity. - call setqflist([{'bufnr': a:src, 'lnum': a:startline + str2nr(match[2]) - 1, - \ 'type': 'E', 'col': str2nr(match[3]), 'text': match[4]}], 'r') -endfunction - -" Reset source buffer variables. -function! s:CoffeeCompileResetVars() - " Variables defined in source buffer: - " b:coffee_compile_buf: bufnr of output buffer - " Variables defined in output buffer: - " b:coffee_src_buf: bufnr of source buffer - " b:coffee_compile_pos: previous cursor position in output buffer - - let b:coffee_compile_buf = -1 -endfunction - -function! s:CoffeeWatchResetVars() - " Variables defined in source buffer: - " b:coffee_watch_buf: bufnr of output buffer - " Variables defined in output buffer: - " b:coffee_src_buf: bufnr of source buffer - " b:coffee_watch_pos: previous cursor position in output buffer - - let b:coffee_watch_buf = -1 -endfunction - -function! s:CoffeeRunResetVars() - " Variables defined in CoffeeRun source buffer: - " b:coffee_run_buf: bufnr of output buffer - " Variables defined in CoffeeRun output buffer: - " b:coffee_src_buf: bufnr of source buffer - " b:coffee_run_pos: previous cursor position in output buffer - - let b:coffee_run_buf = -1 -endfunction - -" Clean things up in the source buffers. -function! s:CoffeeCompileClose() - " Switch to the source buffer if not already in it. - silent! call s:SwitchWindow(b:coffee_src_buf) - call s:CoffeeCompileResetVars() -endfunction - -function! s:CoffeeWatchClose() - silent! call s:SwitchWindow(b:coffee_src_buf) - silent! autocmd! CoffeeAuWatch * - call s:CoffeeWatchResetVars() -endfunction - -function! s:CoffeeRunClose() - silent! call s:SwitchWindow(b:coffee_src_buf) - call s:CoffeeRunResetVars() -endfunction - -" Compile the lines between startline and endline and put the result into buf. -function! s:CoffeeCompileToBuf(buf, startline, endline) - let src = bufnr('%') - let input = join(getline(a:startline, a:endline), "\n") - - " Coffee doesn't like empty input. - if !len(input) - " Function should still return within output buffer. - call s:SwitchWindow(a:buf) - return - endif - - " Pipe lines into coffee. - let output = system(g:coffee_compiler . - \ ' -scb' . - \ ' ' . b:coffee_litcoffee . - \ ' 2>&1', input) - - " Paste output into output buffer. - call s:ScratchBufUpdate(a:buf, output) - - " Highlight as JavaScript if there were no compile errors. - if v:shell_error - call s:ParseCoffeeError(output, src, a:startline) - setlocal filetype= - else - " Clear the quickfix list. - call setqflist([], 'r') - setlocal filetype=javascript - endif -endfunction - -" Peek at compiled CoffeeScript in a scratch buffer. We handle ranges like this -" to prevent the cursor from being moved (and its position saved) before the -" function is called. -function! s:CoffeeCompile(startline, endline, args) - if a:args =~ '\' - echoerr 'CoffeeCompile watch is deprecated! Please use CoffeeWatch instead' - sleep 5 - call s:CoffeeWatch(a:args) - return - endif - - " Switch to the source buffer if not already in it. - silent! call s:SwitchWindow(b:coffee_src_buf) - - " Bail if not in source buffer. - if !exists('b:coffee_compile_buf') - return - endif - - " Build the output buffer if it doesn't exist. - if bufwinnr(b:coffee_compile_buf) == -1 - let src = bufnr('%') - - let vert = exists('g:coffee_compile_vert') || a:args =~ '\' - let size = str2nr(matchstr(a:args, '\<\d\+\>')) - - " Build the output buffer and save the source bufnr. - let buf = s:ScratchBufBuild(src, vert, size) - let b:coffee_src_buf = src - - " Set the buffer name. - exec 'silent! file [CoffeeCompile ' . src . ']' - - " Clean up the source buffer when the output buffer is closed. - autocmd BufWipeout call s:CoffeeCompileClose() - " Save the cursor when leaving the output buffer. - autocmd BufLeave let b:coffee_compile_pos = getpos('.') - - " Run user-defined commands on new buffer. - silent doautocmd CoffeeBufNew User CoffeeCompile - - " Switch back to the source buffer and save the output bufnr. This also - " triggers BufLeave above. - call s:SwitchWindow(src) - let b:coffee_compile_buf = buf - endif - - " Fill the scratch buffer. - call s:CoffeeCompileToBuf(b:coffee_compile_buf, a:startline, a:endline) - " Reset cursor to previous position. - call setpos('.', b:coffee_compile_pos) - - " Run any user-defined commands on the scratch buffer. - silent doautocmd CoffeeBufUpdate User CoffeeCompile -endfunction - -" Update the scratch buffer and switch back to the source buffer. -function! s:CoffeeWatchUpdate() - call s:CoffeeCompileToBuf(b:coffee_watch_buf, 1, '$') - call setpos('.', b:coffee_watch_pos) - silent doautocmd CoffeeBufUpdate User CoffeeWatch - call s:SwitchWindow(b:coffee_src_buf) -endfunction - -" Continually compile a source buffer. -function! s:CoffeeWatch(args) - silent! call s:SwitchWindow(b:coffee_src_buf) - - if !exists('b:coffee_watch_buf') - return - endif - - if bufwinnr(b:coffee_watch_buf) == -1 - let src = bufnr('%') - - let vert = exists('g:coffee_watch_vert') || a:args =~ '\' - let size = str2nr(matchstr(a:args, '\<\d\+\>')) - - let buf = s:ScratchBufBuild(src, vert, size) - let b:coffee_src_buf = src - - exec 'silent! file [CoffeeWatch ' . src . ']' - - autocmd BufWipeout call s:CoffeeWatchClose() - autocmd BufLeave let b:coffee_watch_pos = getpos('.') - - silent doautocmd CoffeeBufNew User CoffeeWatch - - call s:SwitchWindow(src) - let b:coffee_watch_buf = buf - endif - - " Make sure only one watch autocmd is defined on this buffer. - silent! autocmd! CoffeeAuWatch * - - augroup CoffeeAuWatch - autocmd InsertLeave call s:CoffeeWatchUpdate() - autocmd BufWritePost call s:CoffeeWatchUpdate() - augroup END - - call s:CoffeeWatchUpdate() -endfunction - -" Run a snippet of CoffeeScript between startline and endline. -function! s:CoffeeRun(startline, endline, args) - silent! call s:SwitchWindow(b:coffee_src_buf) - - if !exists('b:coffee_run_buf') - return - endif - - if bufwinnr(b:coffee_run_buf) == -1 - let src = bufnr('%') - - let buf = s:ScratchBufBuild(src, exists('g:coffee_run_vert'), 0) - let b:coffee_src_buf = src - - exec 'silent! file [CoffeeRun ' . src . ']' - - autocmd BufWipeout call s:CoffeeRunClose() - autocmd BufLeave let b:coffee_run_pos = getpos('.') - - silent doautocmd CoffeeBufNew User CoffeeRun - - call s:SwitchWindow(src) - let b:coffee_run_buf = buf - endif - - if a:startline == 1 && a:endline == line('$') - let output = system(g:coffee_compiler . - \ ' ' . b:coffee_litcoffee . - \ ' ' . fnameescape(expand('%')) . - \ ' ' . a:args) - else - let input = join(getline(a:startline, a:endline), "\n") - - if !len(input) - return - endif - - let output = system(g:coffee_compiler . - \ ' -s' . - \ ' ' . b:coffee_litcoffee . - \ ' ' . a:args, input) - endif - - call s:ScratchBufUpdate(b:coffee_run_buf, output) - call setpos('.', b:coffee_run_pos) - - silent doautocmd CoffeeBufUpdate User CoffeeRun -endfunction - -" Run coffeelint on a file, and add any errors between startline and endline -" to the quickfix list. -function! s:CoffeeLint(startline, endline, bang, args) - let input = join(getline(a:startline, a:endline), "\n") - - if !len(input) - return - endif - - let output = system(g:coffee_linter . - \ ' -s --reporter csv' . - \ ' ' . b:coffee_litcoffee . - \ ' ' . g:coffee_lint_options . - \ ' ' . a:args . - \ ' 2>&1', input) - - " Convert output into an array and strip off the csv header. - let lines = split(output, "\n")[1:] - let buf = bufnr('%') - let qflist = [] - - for line in lines - let match = matchlist(line, '^stdin,\(\d\+\),\d*,\(error\|warn\),\(.\+\)$') - - " Ignore unmatched lines. - if !len(match) - continue - endif - - " The 'type' will result in either 'E' or 'W'. - call add(qflist, {'bufnr': buf, 'lnum': a:startline + str2nr(match[1]) - 1, - \ 'type': toupper(match[2][0]), 'text': match[3]}) - endfor - - " Replace the quicklist with our items. - call setqflist(qflist, 'r') - - " If not given a bang, jump to first error. - if !len(a:bang) - silent! cc 1 - endif -endfunction - -" Complete arguments for Coffee* commands. -function! s:CoffeeComplete(cmd, cmdline, cursor) - let args = ['vertical'] - - " If no partial command, return all possibilities. - if !len(a:cmd) - return args - endif - - let pat = '^' . a:cmd - - for arg in args - if arg =~ pat - return [arg] - endif - endfor -endfunction - -" Set initial state variables if they don't exist -if !exists('b:coffee_compile_buf') - call s:CoffeeCompileResetVars() -endif - -if !exists('b:coffee_watch_buf') - call s:CoffeeWatchResetVars() -endif - -if !exists('b:coffee_run_buf') - call s:CoffeeRunResetVars() -endif - -command! -buffer -range=% -bar -nargs=* -complete=customlist,s:CoffeeComplete -\ CoffeeCompile call s:CoffeeCompile(, , ) -command! -buffer -bar -nargs=* -complete=customlist,s:CoffeeComplete -\ CoffeeWatch call s:CoffeeWatch() -command! -buffer -range=% -bar -nargs=* CoffeeRun -\ call s:CoffeeRun(, , ) -command! -buffer -range=% -bang -bar -nargs=* CoffeeLint -\ call s:CoffeeLint(, , , ) diff --git a/bundle/coffee-script/indent/coffee.vim b/bundle/coffee-script/indent/coffee.vim deleted file mode 100755 index 4f4570a..0000000 --- a/bundle/coffee-script/indent/coffee.vim +++ /dev/null @@ -1,428 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -if exists('b:did_indent') - finish -endif - -let b:did_indent = 1 - -setlocal autoindent -setlocal indentexpr=GetCoffeeIndent(v:lnum) -" Make sure GetCoffeeIndent is run when these are typed so they can be -" indented or outdented. -setlocal indentkeys+=0],0),0.,=else,=when,=catch,=finally - -" If no indenting or outdenting is needed, either keep the indent of the cursor -" (use autoindent) or match the indent of the previous line. -if exists('g:coffee_indent_keep_current') - let s:DEFAULT_LEVEL = '-1' -else - let s:DEFAULT_LEVEL = 'indent(prevnlnum)' -endif - -" Only define the function once. -if exists('*GetCoffeeIndent') - finish -endif - -" Keywords that begin a block -let s:BEGIN_BLOCK_KEYWORD = '\C^\%(if\|unless\|else\|for\|while\|until\|' -\ . 'loop\|switch\|when\|try\|catch\|finally\|' -\ . 'class\)\>\%(\s*:\)\@!' - -" An expression that uses the result of a statement -let s:COMPOUND_EXPRESSION = '\C\%([^-]-\|[^+]+\|[^/]/\|[:=*%&|^<>]\)\s*' -\ . '\%(if\|unless\|for\|while\|until\|loop\|switch\|' -\ . 'try\|class\)\>' - -" Combine the two above -let s:BEGIN_BLOCK = s:BEGIN_BLOCK_KEYWORD . '\|' . s:COMPOUND_EXPRESSION - -" Operators that begin a block but also count as a continuation -let s:BEGIN_BLOCK_OP = '[([{:=]$' - -" Begins a function block -let s:FUNCTION = '[-=]>$' - -" Operators that continue a line onto the next line -let s:CONTINUATION_OP = '\C\%(\<\%(is\|isnt\|and\|or\)\>\|' -\ . '[^-]-\|[^+]+\|[^-=]>\|[^.]\.\|[<*/%&|^,]\)$' - -" Ancestor operators that prevent continuation indenting -let s:CONTINUATION = s:CONTINUATION_OP . '\|' . s:BEGIN_BLOCK_OP - -" A closing bracket by itself on a line followed by a continuation -let s:BRACKET_CONTINUATION = '^\s*[}\])]\s*' . s:CONTINUATION_OP - -" A continuation dot access -let s:DOT_ACCESS = '^\.' - -" Keywords that break out of a block -let s:BREAK_BLOCK_OP = '\C^\%(return\|break\|continue\|throw\)\>' - -" A condition attached to the end of a statement -let s:POSTFIX_CONDITION = '\C\S\s\+\zs\<\%(if\|unless\|when\|while\|until\)\>' - -" A then contained in brackets -let s:CONTAINED_THEN = '\C[(\[].\{-}\.\{-\}[)\]]' - -" An else with a condition attached -let s:ELSE_COND = '\C^\s*else\s\+\<\%(if\|unless\)\>' - -" A single-line else statement (without a condition attached) -let s:SINGLE_LINE_ELSE = '\C^else\s\+\%(\<\%(if\|unless\)\>\)\@!' - -" Pairs of starting and ending keywords, with an initial pattern to match -let s:KEYWORD_PAIRS = [ -\ ['\C^else\>', '\C\<\%(if\|unless\|when\|else\s\+\%(if\|unless\)\)\>', -\ '\C\'], -\ ['\C^catch\>', '\C\', '\C\'], -\ ['\C^finally\>', '\C\', '\C\'] -\] - -" Pairs of starting and ending brackets -let s:BRACKET_PAIRS = {']': '\[', '}': '{', ')': '('} - -" Max lines to look back for a match -let s:MAX_LOOKBACK = 50 - -" Syntax names for strings -let s:SYNTAX_STRING = 'coffee\%(String\|AssignString\|Embed\|Regex\|Heregex\|' -\ . 'Heredoc\)' - -" Syntax names for comments -let s:SYNTAX_COMMENT = 'coffee\%(Comment\|BlockComment\|HeregexComment\)' - -" Syntax names for strings and comments -let s:SYNTAX_STRING_COMMENT = s:SYNTAX_STRING . '\|' . s:SYNTAX_COMMENT - -" Compatibility code for shiftwidth() as recommended by the docs, but modified -" so there isn't as much of a penalty if shiftwidth() exists. -if exists('*shiftwidth') - let s:ShiftWidth = function('shiftwidth') -else - function! s:ShiftWidth() - return &shiftwidth - endfunction -endif - -" Get the linked syntax name of a character. -function! s:SyntaxName(lnum, col) - return synIDattr(synID(a:lnum, a:col, 1), 'name') -endfunction - -" Check if a character is in a comment. -function! s:IsComment(lnum, col) - return s:SyntaxName(a:lnum, a:col) =~ s:SYNTAX_COMMENT -endfunction - -" Check if a character is in a string. -function! s:IsString(lnum, col) - return s:SyntaxName(a:lnum, a:col) =~ s:SYNTAX_STRING -endfunction - -" Check if a character is in a comment or string. -function! s:IsCommentOrString(lnum, col) - return s:SyntaxName(a:lnum, a:col) =~ s:SYNTAX_STRING_COMMENT -endfunction - -" Search a line for a regex until one is found outside a string or comment. -function! s:SearchCode(lnum, regex) - " Start at the first column and look for an initial match (including at the - " cursor.) - call cursor(a:lnum, 1) - let pos = search(a:regex, 'c', a:lnum) - - while pos - if !s:IsCommentOrString(a:lnum, col('.')) - return 1 - endif - - " Move to the match and continue searching (don't accept matches at the - " cursor.) - let pos = search(a:regex, '', a:lnum) - endwhile - - return 0 -endfunction - -" Search for the nearest previous line that isn't a comment. -function! s:GetPrevNormalLine(startlnum) - let curlnum = a:startlnum - - while curlnum - let curlnum = prevnonblank(curlnum - 1) - - " Return the line if the first non-whitespace character isn't a comment. - if !s:IsComment(curlnum, indent(curlnum) + 1) - return curlnum - endif - endwhile - - return 0 -endfunction - -function! s:SearchPair(startlnum, lookback, skip, open, close) - " Go to the first column so a:close will be matched even if it's at the - " beginning of the line. - call cursor(a:startlnum, 1) - return searchpair(a:open, '', a:close, 'bnW', a:skip, max([1, a:lookback])) -endfunction - -" Skip if a match -" - is in a string or comment -" - is a single-line statement that isn't immediately -" adjacent -" - has a postfix condition and isn't an else statement or compound -" expression -function! s:ShouldSkip(startlnum, lnum, col) - return s:IsCommentOrString(a:lnum, a:col) || - \ s:SearchCode(a:lnum, '\C\') && a:startlnum - a:lnum > 1 || - \ s:SearchCode(a:lnum, s:POSTFIX_CONDITION) && - \ getline(a:lnum) !~ s:ELSE_COND && - \ !s:SearchCode(a:lnum, s:COMPOUND_EXPRESSION) -endfunction - -" Search for the nearest and farthest match for a keyword pair. -function! s:SearchMatchingKeyword(startlnum, open, close) - let skip = 's:ShouldSkip(' . a:startlnum . ", line('.'), line('.'))" - - " Search for the nearest match. - let nearestlnum = s:SearchPair(a:startlnum, a:startlnum - s:MAX_LOOKBACK, - \ skip, a:open, a:close) - - if !nearestlnum - return [] - endif - - " Find the nearest previous line with indent less than or equal to startlnum. - let ind = indent(a:startlnum) - let lookback = s:GetPrevNormalLine(a:startlnum) - - while lookback && indent(lookback) > ind - let lookback = s:GetPrevNormalLine(lookback) - endwhile - - " Search for the farthest match. If there are no other matches, then the - " nearest match is also the farthest one. - let matchlnum = nearestlnum - - while matchlnum - let lnum = matchlnum - let matchlnum = s:SearchPair(matchlnum, lookback, skip, a:open, a:close) - endwhile - - return [nearestlnum, lnum] -endfunction - -" Strip a line of a trailing comment and surrounding whitespace. -function! s:GetTrimmedLine(lnum) - " Try to find a comment starting at the first column. - call cursor(a:lnum, 1) - let pos = search('#', 'c', a:lnum) - - " Keep searching until a comment is found or search returns 0. - while pos - if s:IsComment(a:lnum, col('.')) - break - endif - - let pos = search('#', '', a:lnum) - endwhile - - if !pos - " No comment was found so use the whole line. - let line = getline(a:lnum) - else - " Subtract 1 to get to the column before the comment and another 1 for - " column indexing -> zero-based indexing. - let line = getline(a:lnum)[:col('.') - 2] - endif - - return substitute(substitute(line, '^\s\+', '', ''), - \ '\s\+$', '', '') -endfunction - -" Get the indent policy when no special rules are used. -function! s:GetDefaultPolicy(curlnum) - " Check whether equalprg is being ran on existing lines. - if strlen(getline(a:curlnum)) == indent(a:curlnum) - " If not indenting an existing line, use the default policy. - return s:DEFAULT_LEVEL - else - " Otherwise let autoindent determine what to do with an existing line. - return '-1' - endif -endfunction - -function! GetCoffeeIndent(curlnum) - " Get the previous non-blank line (may be a comment.) - let prevlnum = prevnonblank(a:curlnum - 1) - - " Bail if there's no code before. - if !prevlnum - return -1 - endif - - " Bail if inside a multiline string. - if s:IsString(a:curlnum, 1) - let prevnlnum = prevlnum - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - - " Get the code part of the current line. - let curline = s:GetTrimmedLine(a:curlnum) - " Get the previous non-comment line. - let prevnlnum = s:GetPrevNormalLine(a:curlnum) - - " Check if the current line is the closing bracket in a bracket pair. - if has_key(s:BRACKET_PAIRS, curline[0]) - " Search for a matching opening bracket. - let matchlnum = s:SearchPair(a:curlnum, a:curlnum - s:MAX_LOOKBACK, - \ "s:IsCommentOrString(line('.'), col('.'))", - \ s:BRACKET_PAIRS[curline[0]], curline[0]) - - if matchlnum - " Match the indent of the opening bracket. - return indent(matchlnum) - else - " No opening bracket found (bad syntax), so bail. - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - endif - - " Check if the current line is the closing keyword in a keyword pair. - for pair in s:KEYWORD_PAIRS - if curline =~ pair[0] - " Find the nearest and farthest matches within the same indent level. - let matches = s:SearchMatchingKeyword(a:curlnum, pair[1], pair[2]) - - if len(matches) - " Don't force indenting/outdenting as long as line is already lined up - " with a valid match - return max([min([indent(a:curlnum), indent(matches[0])]), - \ indent(matches[1])]) - else - " No starting keyword found (bad syntax), so bail. - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - endif - endfor - - " Check if the current line is a `when` and not the first in a switch block. - if curline =~ '\C^when\>' && !s:SearchCode(prevnlnum, '\C\') - " Look back for a `when`. - while prevnlnum - if getline(prevnlnum) =~ '\C^\s*when\>' - " Indent to match the found `when`, but don't force indenting (for when - " indenting nested switch blocks.) - return min([indent(a:curlnum), indent(prevnlnum)]) - endif - - let prevnlnum = s:GetPrevNormalLine(prevnlnum) - endwhile - - " No matching `when` found (bad syntax), so bail. - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - - " If the previous line is a comment, use its indentation, but don't force - " indenting. - if prevlnum != prevnlnum - return min([indent(a:curlnum), indent(prevlnum)]) - endif - - let prevline = s:GetTrimmedLine(prevnlnum) - - " Always indent after these operators. - if prevline =~ s:BEGIN_BLOCK_OP - return indent(prevnlnum) + s:ShiftWidth() - endif - - " Indent if the previous line starts a function block, but don't force - " indenting if the line is non-blank (for empty function bodies.) - if prevline =~ s:FUNCTION - if strlen(getline(a:curlnum)) > indent(a:curlnum) - return min([indent(prevnlnum) + s:ShiftWidth(), indent(a:curlnum)]) - else - return indent(prevnlnum) + s:ShiftWidth() - endif - endif - - " Check if continuation indenting is needed. If the line ends in a slash, make - " sure it isn't a regex. - if prevline =~ s:CONTINUATION_OP && - \ !(prevline =~ '/$' && s:IsString(prevnlnum, col([prevnlnum, '$']) - 1)) - " Don't indent if the continuation follows a closing bracket. - if prevline =~ s:BRACKET_CONTINUATION - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - - let prevprevnlnum = s:GetPrevNormalLine(prevnlnum) - - " Don't indent if not the first continuation. - if prevprevnlnum && s:GetTrimmedLine(prevprevnlnum) =~ s:CONTINUATION - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - - " Continuation indenting seems to vary between programmers, so if the line - " is non-blank, don't override the indentation - if strlen(getline(a:curlnum)) > indent(a:curlnum) - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - - " Otherwise indent a level. - return indent(prevnlnum) + s:ShiftWidth() - endif - - " Check if the previous line starts with a keyword that begins a block. - if prevline =~ s:BEGIN_BLOCK - " Indent if the current line doesn't start with `then` and the previous line - " isn't a single-line statement. - if curline !~ '\C^\' && !s:SearchCode(prevnlnum, '\C\') && - \ prevline !~ s:SINGLE_LINE_ELSE - return indent(prevnlnum) + s:ShiftWidth() - else - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - endif - - " Indent a dot access if it's the first. - if curline =~ s:DOT_ACCESS - if prevline !~ s:DOT_ACCESS - return indent(prevnlnum) + s:ShiftWidth() - else - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - endif - - " Outdent if a keyword breaks out of a block as long as it doesn't have a - " postfix condition (and the postfix condition isn't a single-line statement.) - if prevline =~ s:BREAK_BLOCK_OP - if !s:SearchCode(prevnlnum, s:POSTFIX_CONDITION) || - \ s:SearchCode(prevnlnum, '\C\') && - \ !s:SearchCode(prevnlnum, s:CONTAINED_THEN) - " Don't force indenting. - return min([indent(a:curlnum), indent(prevnlnum) - s:ShiftWidth()]) - else - exec 'return' s:GetDefaultPolicy(a:curlnum) - endif - endif - - " Check if inside brackets. - let matchlnum = s:SearchPair(a:curlnum, a:curlnum - s:MAX_LOOKBACK, - \ "s:IsCommentOrString(line('.'), col('.'))", - \ '\[\|(\|{', '\]\|)\|}') - - " If inside brackets, indent relative to the brackets, but don't outdent an - " already indented line. - if matchlnum - return max([indent(a:curlnum), indent(matchlnum) + s:ShiftWidth()]) - endif - - " No special rules applied, so use the default policy. - exec 'return' s:GetDefaultPolicy(a:curlnum) -endfunction diff --git a/bundle/coffee-script/syntax/coffee.vim b/bundle/coffee-script/syntax/coffee.vim deleted file mode 100755 index bfb252f..0000000 --- a/bundle/coffee-script/syntax/coffee.vim +++ /dev/null @@ -1,221 +0,0 @@ -" Language: CoffeeScript -" Maintainer: Mick Koch -" URL: http://github.com/kchmck/vim-coffee-script -" License: WTFPL - -" Bail if our syntax is already loaded. -if exists('b:current_syntax') && b:current_syntax == 'coffee' - finish -endif - -" Include JavaScript for coffeeEmbed. -syn include @coffeeJS syntax/javascript.vim -silent! unlet b:current_syntax - -" Highlight long strings. -syntax sync fromstart - -" These are `matches` instead of `keywords` because vim's highlighting -" priority for keywords is higher than matches. This causes keywords to be -" highlighted inside matches, even if a match says it shouldn't contain them -- -" like with coffeeAssign and coffeeDot. -syn match coffeeStatement /\<\%(return\|break\|continue\|throw\)\>/ display -hi def link coffeeStatement Statement - -syn match coffeeRepeat /\<\%(for\|while\|until\|loop\)\>/ display -hi def link coffeeRepeat Repeat - -syn match coffeeConditional /\<\%(if\|else\|unless\|switch\|when\|then\)\>/ -\ display -hi def link coffeeConditional Conditional - -syn match coffeeException /\<\%(try\|catch\|finally\)\>/ display -hi def link coffeeException Exception - -syn match coffeeKeyword /\<\%(new\|in\|of\|by\|and\|or\|not\|is\|isnt\|class\|extends\|super\|do\|yield\)\>/ -\ display -" The `own` keyword is only a keyword after `for`. -syn match coffeeKeyword /\/ contained containedin=coffeeRepeat -\ display -hi def link coffeeKeyword Keyword - -syn match coffeeOperator /\<\%(instanceof\|typeof\|delete\)\>/ display -hi def link coffeeOperator Operator - -" The first case matches symbol operators only if they have an operand before. -syn match coffeeExtendedOp /\%(\S\s*\)\@<=[+\-*/%&|\^=!<>?.]\{-1,}\|[-=]>\|--\|++\|:/ -\ display -syn match coffeeExtendedOp /\<\%(and\|or\)=/ display -hi def link coffeeExtendedOp coffeeOperator - -" This is separate from `coffeeExtendedOp` to help differentiate commas from -" dots. -syn match coffeeSpecialOp /[,;]/ display -hi def link coffeeSpecialOp SpecialChar - -syn match coffeeBoolean /\<\%(true\|on\|yes\|false\|off\|no\)\>/ display -hi def link coffeeBoolean Boolean - -syn match coffeeGlobal /\<\%(null\|undefined\)\>/ display -hi def link coffeeGlobal Type - -" A special variable -syn match coffeeSpecialVar /\<\%(this\|prototype\|arguments\)\>/ display -hi def link coffeeSpecialVar Special - -" An @-variable -syn match coffeeSpecialIdent /@\%(\%(\I\|\$\)\%(\i\|\$\)*\)\?/ display -hi def link coffeeSpecialIdent Identifier - -" A class-like name that starts with a capital letter -syn match coffeeObject /\<\u\w*\>/ display -hi def link coffeeObject Structure - -" A constant-like name in SCREAMING_CAPS -syn match coffeeConstant /\<\u[A-Z0-9_]\+\>/ display -hi def link coffeeConstant Constant - -" A variable name -syn cluster coffeeIdentifier contains=coffeeSpecialVar,coffeeSpecialIdent, -\ coffeeObject,coffeeConstant - -" A non-interpolated string -syn cluster coffeeBasicString contains=@Spell,coffeeEscape -" An interpolated string -syn cluster coffeeInterpString contains=@coffeeBasicString,coffeeInterp - -" Regular strings -syn region coffeeString start=/"/ skip=/\\\\\|\\"/ end=/"/ -\ contains=@coffeeInterpString -syn region coffeeString start=/'/ skip=/\\\\\|\\'/ end=/'/ -\ contains=@coffeeBasicString -hi def link coffeeString String - -" A integer, including a leading plus or minus -syn match coffeeNumber /\%(\i\|\$\)\@/ display -syn match coffeeNumber /\<0[bB][01]\+\>/ display -syn match coffeeNumber /\<0[oO][0-7]\+\>/ display -syn match coffeeNumber /\<\%(Infinity\|NaN\)\>/ display -hi def link coffeeNumber Number - -" A floating-point number, including a leading plus or minus -syn match coffeeFloat /\%(\i\|\$\)\@/ -\ display -hi def link coffeeReservedError Error - -" A normal object assignment -syn match coffeeObjAssign /@\?\%(\I\|\$\)\%(\i\|\$\)*\s*\ze::\@!/ contains=@coffeeIdentifier display -hi def link coffeeObjAssign Identifier - -syn keyword coffeeTodo TODO FIXME XXX contained -hi def link coffeeTodo Todo - -syn match coffeeComment /#.*/ contains=@Spell,coffeeTodo -hi def link coffeeComment Comment - -syn region coffeeBlockComment start=/####\@!/ end=/###/ -\ contains=@Spell,coffeeTodo -hi def link coffeeBlockComment coffeeComment - -" A comment in a heregex -syn region coffeeHeregexComment start=/#/ end=/\ze\/\/\/\|$/ contained -\ contains=@Spell,coffeeTodo -hi def link coffeeHeregexComment coffeeComment - -" Embedded JavaScript -syn region coffeeEmbed matchgroup=coffeeEmbedDelim -\ start=/`/ skip=/\\\\\|\\`/ end=/`/ keepend -\ contains=@coffeeJS -hi def link coffeeEmbedDelim Delimiter - -syn region coffeeInterp matchgroup=coffeeInterpDelim start=/#{/ end=/}/ contained -\ contains=@coffeeAll -hi def link coffeeInterpDelim PreProc - -" A string escape sequence -syn match coffeeEscape /\\\d\d\d\|\\x\x\{2\}\|\\u\x\{4\}\|\\./ contained display -hi def link coffeeEscape SpecialChar - -" A regex -- must not follow a parenthesis, number, or identifier, and must not -" be followed by a number -syn region coffeeRegex start=#\%(\%()\|\%(\i\|\$\)\@> #{ == { { { } } } == } << " -" >> #{ == { abc: { def: 42 } } == } << " diff --git a/bundle/coffee-script/test/test-ops.coffee b/bundle/coffee-script/test/test-ops.coffee deleted file mode 100755 index 54be8db..0000000 --- a/bundle/coffee-script/test/test-ops.coffee +++ /dev/null @@ -1,90 +0,0 @@ -# Various operators -abc instanceof def -typeof abc -delete abc -abc::def - -abc + def -abc - def -abc * def -abc / def -abc % def -abc & def -abc | def -abc ^ def -abc >> def -abc << def -abc >>> def -abc ? def -abc && def -abc and def -abc || def -abc or def - -abc += def -abc -= def -abc *= def -abc /= def -abc %= def -abc &= def -abc |= def -abc ^= def -abc >>= def -abc <<= def -abc >>>= def -abc ?= def -abc &&= def -abc ||= def - -abc and= def -abc or= def - -abc.def.ghi -abc?.def?.ghi - -abc < def -abc > def -abc = def -abc == def -abc != def -abc <= def -abc >= def - -abc++ -abc-- -++abc ---abc - -# Nested operators -abc[def] = ghi -abc[def[ghi: jkl]] = 42 -@abc[def] = ghi - -abc["#{def = 42}"] = 42 -abc["#{def.ghi = 42}"] = 42 -abc["#{def[ghi] = 42}"] = 42 -abc["#{def['ghi']}"] = 42 - -# Object assignments -abc = - def: 123 - DEF: 123 - @def: 123 - Def: 123 - 'def': 123 - 42: 123 - -# Operators shouldn't be highlighted -vector= -wand= - -abc+++ -abc--- -abc ** def -abc &&& def -abc ^^ def -abc ===== def -abc <==== def -abc >==== def -abc +== def -abc =^= def diff --git a/bundle/coffee-script/test/test-reserved.coffee b/bundle/coffee-script/test/test-reserved.coffee deleted file mode 100755 index b841760..0000000 --- a/bundle/coffee-script/test/test-reserved.coffee +++ /dev/null @@ -1,27 +0,0 @@ -# Should be an error -function = 42 -var = 42 - -# Shouldn't be an error -abc.with = 42 -function: 42 -var: 42 - -# Keywords shouldn't be highlighted -abc.function -abc.do -abc.break -abc.true - -abc::function -abc::do -abc::break -abc::true - -abc:: function -abc. function - -# Numbers should be highlighted -def.42 -def .42 -def::42 diff --git a/bundle/coffee-script/test/test.haml b/bundle/coffee-script/test/test.haml deleted file mode 100755 index ae19fba..0000000 --- a/bundle/coffee-script/test/test.haml +++ /dev/null @@ -1,3 +0,0 @@ -:coffeescript - class Hello - # test diff --git a/bundle/coffee-script/test/test.html b/bundle/coffee-script/test/test.html deleted file mode 100755 index 3479145..0000000 --- a/bundle/coffee-script/test/test.html +++ /dev/null @@ -1,7 +0,0 @@ - - - diff --git a/bundle/elixir/.travis.yml b/bundle/elixir/.travis.yml deleted file mode 100755 index 3e67b0c..0000000 --- a/bundle/elixir/.travis.yml +++ /dev/null @@ -1,8 +0,0 @@ -language: ruby -rvm: - - 1.9.3 -before_install: sudo apt-get install vim-gtk -before_script: - - "export DISPLAY=:99.0" - - "sh -e /etc/init.d/xvfb start" -script: "bundle exec rspec --color -f d" diff --git a/bundle/elixir/Gemfile b/bundle/elixir/Gemfile deleted file mode 100755 index c543a5d..0000000 --- a/bundle/elixir/Gemfile +++ /dev/null @@ -1,4 +0,0 @@ -source 'http://rubygems.org/' - -gem 'rspec' -gem 'vimrunner' diff --git a/bundle/elixir/Gemfile.lock b/bundle/elixir/Gemfile.lock deleted file mode 100755 index 8d4d64f..0000000 --- a/bundle/elixir/Gemfile.lock +++ /dev/null @@ -1,20 +0,0 @@ -GEM - remote: http://rubygems.org/ - specs: - diff-lcs (1.2.4) - rspec (2.13.0) - rspec-core (~> 2.13.0) - rspec-expectations (~> 2.13.0) - rspec-mocks (~> 2.13.0) - rspec-core (2.13.1) - rspec-expectations (2.13.0) - diff-lcs (>= 1.1.3, < 2.0) - rspec-mocks (2.13.1) - vimrunner (0.3.0) - -PLATFORMS - ruby - -DEPENDENCIES - rspec - vimrunner diff --git a/bundle/elixir/README.md b/bundle/elixir/README.md deleted file mode 100755 index 7ed3b46..0000000 --- a/bundle/elixir/README.md +++ /dev/null @@ -1,23 +0,0 @@ -# vim-elixir - -[![Build Status](https://travis-ci.org/elixir-lang/vim-elixir.png?branch=master)](https://travis-ci.org/elixir-lang/vim-elixir) - -This project contains some Vim configuration files to work with [Elixir](http://elixir-lang.org). - -So far it's included: - -* Syntax highlighting - -* Filetype detection - -* Auto indentation - -## Install - -* Copy the files to your `~/.vim` directory. - -* If you use vim-pathogen you can clone this repo into `~/.vim/bundle` - -## Snippets - -If you are looking for snipmate snippets take a look at: [elixir-snippets](https://github.com/carlosgaldino/elixir-snippets) diff --git a/bundle/elixir/compiler/exunit.vim b/bundle/elixir/compiler/exunit.vim deleted file mode 100755 index 2c9fb29..0000000 --- a/bundle/elixir/compiler/exunit.vim +++ /dev/null @@ -1,24 +0,0 @@ -" Vim compiler file -" Language: ExUnit -" Maintainer: Rein Henrichs -" URL: https://github.com/elixir-lang/vim-elixir - -if exists("current_compiler") - finish -endif -let current_compiler = "exunit" - -if exists(":CompilerSet") != 2 " older Vim always used :setlocal - command -nargs=* CompilerSet setlocal -endif - -let s:cpo_save = &cpo -set cpo-=C - -CompilerSet makeprg=mix\ test -CompilerSet errorformat=%A\ \ %.)\ %m(%.%#),%C\ \ \ \ \ **%m,%C\ \ \ \ \ \ \ %m,%Z\ \ \ \ \ at\ %f:%l,%-G%.%# - -let &cpo = s:cpo_save -unlet s:cpo_save - -" vim: nowrap sw=2 sts=2 ts=8: diff --git a/bundle/elixir/ftdetect/elixir.vim b/bundle/elixir/ftdetect/elixir.vim deleted file mode 100755 index df413e1..0000000 --- a/bundle/elixir/ftdetect/elixir.vim +++ /dev/null @@ -1,2 +0,0 @@ -au BufRead,BufNewFile *.ex,*.exs set filetype=elixir -au FileType elixir setl sw=2 sts=2 et iskeyword+=!,? diff --git a/bundle/elixir/ftplugin/elixir.vim b/bundle/elixir/ftplugin/elixir.vim deleted file mode 100755 index 5571fcf..0000000 --- a/bundle/elixir/ftplugin/elixir.vim +++ /dev/null @@ -1,25 +0,0 @@ -" Vim filetype plugin -" Language: Elixir -" Maintainer: Carlos Galdino -" URL: https://github.com/elixir-lang/vim-elixir - -if (exists("b:did_ftplugin")) - finish -endif -let b:did_ftplugin = 1 - - -" Matchit support -if exists("loaded_matchit") && !exists("b:match_words") - let b:match_ignorecase = 0 - - let b:match_words = '\<\%(do\|fn\)\:\@!\>' . - \ ':' . - \ '\<\%(else\|elsif\|catch\|after\|rescue\)\:\@!\>' . - \ ':' . - \ '\:\@' . - \ ',{:},\[:\],(:)' -endif - -setlocal comments=:# -setlocal commentstring=#\ %s diff --git a/bundle/elixir/indent/elixir.vim b/bundle/elixir/indent/elixir.vim deleted file mode 100755 index fababe4..0000000 --- a/bundle/elixir/indent/elixir.vim +++ /dev/null @@ -1,107 +0,0 @@ -" Vim indent file -" Language: Elixir -" Maintainer: Carlos Galdino -" Last Change: 2013 Apr 24 - -if exists("b:did_indent") - finish -endif -let b:did_indent = 1 - -setlocal nosmartindent - -setlocal indentexpr=GetElixirIndent() -setlocal indentkeys+==end,=else:,=match:,=elsif:,=catch:,=after:,=rescue: - -if exists("*GetElixirIndent") - finish -endif - -let s:cpo_save = &cpo -set cpo&vim - -let s:skip_syntax = '\%(Comment\|String\)$' -let s:block_skip = "synIDattr(synID(line('.'),col('.'),1),'name') =~? '" . s:skip_syntax . "'" -let s:block_start = 'do\|fn' -let s:block_middle = 'else\|match\|elsif\|catch\|after\|rescue' -let s:block_end = 'end' -let s:arrow = '^.*->$' -let s:pipeline = '^\s*|>.*$' - -let s:indent_keywords = '\<\%(' . s:block_start . '\|' . s:block_middle . '\)$' . '\|' . s:arrow -let s:deindent_keywords = '^\s*\<\%(' . s:block_end . '\|' . s:block_middle . '\)\>' . '\|' . s:arrow - -function! GetElixirIndent() - let lnum = prevnonblank(v:lnum - 1) - let ind = indent(lnum) - - " At the start of the file use zero indent. - if lnum == 0 - return 0 - endif - - " TODO: Remove these 2 lines - " I don't know why, but for the test on spec/indent/lists_spec.rb:24. - " Vim is making some mess on parsing the syntax of 'end', it is being - " recognized as 'elixirString' when should be recognized as 'elixirBlock'. - " This forces vim to sync the syntax. - call synID(v:lnum, 1, 1) - syntax sync fromstart - - if synIDattr(synID(v:lnum, 1, 1), "name") !~ s:skip_syntax - let current_line = getline(v:lnum) - let last_line = getline(lnum) - - let splited_line = split(last_line, '\zs') - let opened_symbol = 0 - let opened_symbol += count(splited_line, '[') - count(splited_line, ']') - let opened_symbol += count(splited_line, '{') - count(splited_line, '}') - - let ind += opened_symbol * &sw - - if current_line =~ '^\s*\(\]\|}\)' - let ind -= &sw - endif - - if last_line =~ s:indent_keywords - let ind += &sw - endif - - " if line starts with pipeline - " and last line is an attribution - " indents pipeline in same level as attribution - if current_line =~ s:pipeline && - \ last_line =~ '^[^=]\+=.\+$' - let b:old_ind = ind - let ind = float2nr(matchend(last_line, '=\s*[^ ]') / &sw) * &sw - endif - - " if last line starts with pipeline - " and current line doesn't start with pipeline - " returns the indentation before the pipeline - if last_line =~ s:pipeline && - \ current_line !~ s:pipeline - let ind = b:old_ind - endif - - if current_line =~ s:deindent_keywords - let bslnum = searchpair( '\<\%(' . s:block_start . '\):\@!\>', - \ '\<\%(' . s:block_middle . '\):\@!\>\zs', - \ '\<:\@\zs', - \ 'nbW', - \ s:block_skip ) - - let ind = indent(bslnum) - endif - - " indent case statements '->' - if current_line =~ s:arrow - let ind += &sw - endif - endif - - return ind -endfunction - -let &cpo = s:cpo_save -unlet s:cpo_save diff --git a/bundle/elixir/spec/indent/anonymous_functions_spec.rb b/bundle/elixir/spec/indent/anonymous_functions_spec.rb deleted file mode 100755 index e3dd40f..0000000 --- a/bundle/elixir/spec/indent/anonymous_functions_spec.rb +++ /dev/null @@ -1,67 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - context "single body functions inside do block" do - it "is declared with fn syntax" do - assert_correct_indenting <<-EOF - def do - some_func = fn x -> x end - end - EOF - end - - it "is declared with function syntax" do - assert_correct_indenting <<-EOF - def do - some_func = function do x -> x end - end - EOF - end - - it "spans in multiple lines" do - assert_correct_indenting <<-EOF - def test do - assert_raise Queue.Empty, fn -> - Q.new |> Q.deq! - end - end - EOF - end - - it "spans in multiple lines inside parentheses" do - assert_correct_indenting <<-EOF - defmodule Test do - def lol do - Enum.map([1,2,3], fn x -> - x * 3 - end) - end - end - EOF - end - end - - context "multiple body functions declaring" do - it "it with fn syntax" do - assert_correct_indenting <<-EOF - fizzbuzz = fn - 0, 0, _ -> "FizzBuzz" - 0, _, _ -> "Fizz" - _, 0, _ -> "Buzz" - _, _, x -> x - end - EOF - end - - it "it with function syntax" do - assert_correct_indenting <<-EOF - fizzbuzz = function do - 0, 0, _ -> "FizzBuzz" - 0, _, _ -> "Fizz" - _, 0, _ -> "Buzz" - _, _, x -> x - end - EOF - end - end -end diff --git a/bundle/elixir/spec/indent/blocks_spec.rb b/bundle/elixir/spec/indent/blocks_spec.rb deleted file mode 100755 index cbc0c82..0000000 --- a/bundle/elixir/spec/indent/blocks_spec.rb +++ /dev/null @@ -1,29 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - specify "'do' indenting" do - assert_correct_indenting <<-EOF - do - something - end - EOF - end - - it "does not consider :end as end" do - assert_correct_indenting <<-EOF - defmodule Test do - def lol do - IO.inspect :end - end - end - EOF - end - - it "does not consider do: as the start of a block" do - assert_correct_indenting <<-EOF - def f do - if true do: 42 - end - EOF - end -end diff --git a/bundle/elixir/spec/indent/case_spec.rb b/bundle/elixir/spec/indent/case_spec.rb deleted file mode 100755 index e0df5d6..0000000 --- a/bundle/elixir/spec/indent/case_spec.rb +++ /dev/null @@ -1,14 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - specify "case statements" do - assert_correct_indenting <<-EOF - case some_function do - :ok -> - :ok - { :error, :message } -> - { :error, :message } - end - EOF - end -end diff --git a/bundle/elixir/spec/indent/cond_spec.rb b/bundle/elixir/spec/indent/cond_spec.rb deleted file mode 100755 index d3534d1..0000000 --- a/bundle/elixir/spec/indent/cond_spec.rb +++ /dev/null @@ -1,12 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - it "conditional" do - assert_correct_indenting <<-EOF - cond do - foo -> 1 - bar -> 2 - end - EOF - end -end diff --git a/bundle/elixir/spec/indent/documentation_spec.rb b/bundle/elixir/spec/indent/documentation_spec.rb deleted file mode 100755 index 72d0c7d..0000000 --- a/bundle/elixir/spec/indent/documentation_spec.rb +++ /dev/null @@ -1,15 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - context "documentation" do - it "with end keyword" do - assert_correct_indenting <<-EOF - defmodule Test do - @doc """ - end - """ - end - EOF - end - end -end diff --git a/bundle/elixir/spec/indent/if_spec.rb b/bundle/elixir/spec/indent/if_spec.rb deleted file mode 100755 index 0d0970a..0000000 --- a/bundle/elixir/spec/indent/if_spec.rb +++ /dev/null @@ -1,21 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - it "if-clauses" do - assert_correct_indenting <<-EOF - if foo do - bar - end - EOF - end - - it "if-else-clauses" do - assert_correct_indenting <<-EOF - if foo do - bar - else - baz - end - EOF - end -end diff --git a/bundle/elixir/spec/indent/lists_spec.rb b/bundle/elixir/spec/indent/lists_spec.rb deleted file mode 100755 index 895c07f..0000000 --- a/bundle/elixir/spec/indent/lists_spec.rb +++ /dev/null @@ -1,77 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - specify "lists" do - assert_correct_indenting <<-EOF - def example do - [ :foo, - :bar, - :baz ] - end - EOF - end - - specify "keyword list" do - assert_correct_indenting <<-EOF - def project do - [ name: "mix", - version: "0.1.0", - deps: deps ] - end - EOF - end - - specify "keyword" do - assert_correct_indenting <<-EOF - def config do - [ name: - "John" ] - end - EOF - end - - specify "list of tuples" do - assert_correct_indenting <<-EOF - def test do - [ { :cowboy, github: "extend/cowboy" }, - { :dynamo, "0.1.0-dev", github: "elixir-lang/dynamo" }, - { :ecto, github: "elixir-lang/ecto" }, - { :pgsql, github: "semiocast/pgsql" } ] - end - EOF - end - - specify "list of lists" do - assert_correct_indenting <<-EOF - def test do - [ [:a, :b, :c], - [:d, :e, :f] ] - end - EOF - end - - specify "complex list" do - assert_correct_indenting <<-EOF - def test do - [ app: :first, - version: "0.0.1", - dynamos: [First.Dynamo], - compilers: [:elixir, :dynamo, :ecto, :app], - env: [prod: [compile_path: "ebin"]], - compile_path: "tmp/first/ebin", - deps: deps ] - end - EOF - end - - specify "lists with break line after square brackets" do - assert_correct_indenting <<-EOF - def project do - deps: [ - { :bar, path: "deps/umbrella/apps/bar" }, - { :umbrella, path: "deps/umbrella" } - ] - end - EOF - end -end diff --git a/bundle/elixir/spec/indent/pipeline_spec.rb b/bundle/elixir/spec/indent/pipeline_spec.rb deleted file mode 100755 index 26db511..0000000 --- a/bundle/elixir/spec/indent/pipeline_spec.rb +++ /dev/null @@ -1,54 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - it "using multiline pipeline" do - assert_correct_indenting <<-EOF - "a,b,c,d" - |> String.split(",") - |> Enum.reverse - EOF - end - - it "attribuition using multline pipeline operator" do - assert_correct_indenting <<-EOF - [ h | t ] = "a,b,c,d" - |> String.split(",") - |> Enum.reverse - EOF - end - - it "function with pipeline operator" do - assert_correct_indenting <<-EOF - def test do - [ h | t ] = "a,b,c,d" - |> String.split(",") - |> Enum.reverse - - { :ok, h } - end - EOF - end - - it "pipeline operator with block open" do - assert_correct_indenting <<-EOF - def test do - "a,b,c,d" - |> String.split(",") - |> Enum.first - |> case do - "a" -> "A" - _ -> "Z" - end - end - EOF - end - - it "using a record with pipeline" do - assert_correct_indenting <<-EOF - defrecord RECORD, field_a: nil, field_b: nil - - rec = RECORD.new - |> IO.inspect - EOF - end -end diff --git a/bundle/elixir/spec/indent/tuples_spec.rb b/bundle/elixir/spec/indent/tuples_spec.rb deleted file mode 100755 index 5464704..0000000 --- a/bundle/elixir/spec/indent/tuples_spec.rb +++ /dev/null @@ -1,24 +0,0 @@ -require 'spec_helper' - -describe "Indenting" do - specify "multiline tuple" do - assert_correct_indenting <<-EOF - def xpto do - { :a, - :b, - :c } - end - EOF - end - - specify "tuples with break line after square brackets" do - assert_correct_indenting <<-EOF - def method do - { - :bar, - path: "deps/umbrella/apps/bar" - } - end - EOF - end -end diff --git a/bundle/elixir/spec/spec_helper.rb b/bundle/elixir/spec/spec_helper.rb deleted file mode 100755 index ab86908..0000000 --- a/bundle/elixir/spec/spec_helper.rb +++ /dev/null @@ -1,91 +0,0 @@ -require 'tmpdir' -require 'vimrunner' - -module Support - def assert_correct_indenting(string) - content = write_file(string) - - @vim.edit file - # remove all indentation - @vim.normal 'ggVG999<<' - # force vim to indent the file - @vim.normal 'gg=G' - @vim.write - - read_file.should eq(content) - end - - def assert_correct_syntax(syntax, cursor, string) - write_file(string) - - @vim.edit file - @vim.search cursor - - cursor_syntax_stack.should include(syntax) - end - - def assert_incorrect_syntax(type, cursor, string) - write_file(string) - - @vim.edit file - @vim.search cursor - - cursor_syntax_stack.should_not include(type) - end - - private - - def write_file(string) - content = file_content(string) - File.open file, 'w' do |f| - f.write content - end - - content - end - - def file_content(string) - whitespace = string.scan(/^\s*/).first - string.split("\n").map { |line| - line.gsub(/^#{whitespace}/, '') - }.join("\n").strip - end - - def cursor_syntax_stack - @vim.echo <<-EOF - map(synstack(line('.'), col('.')), 'synIDattr(v:val, "name")') - EOF - end - - def read_file - IO.read(file).strip - end - - def file; 'test.exs'; end -end - -RSpec.configure do |config| - include Support - - config.before(:suite) do - VIM = Vimrunner.start_gvim - VIM.prepend_runtimepath(File.expand_path('../..', __FILE__)) - VIM.command('runtime ftdetect/elixir.vim') - end - - config.after(:suite) do - VIM.kill - end - - config.around(:each) do |example| - @vim = VIM - - # cd into a temporary directory for every example. - Dir.mktmpdir do |dir| - Dir.chdir(dir) do - @vim.command("cd #{dir}") - example.call - end - end - end -end diff --git a/bundle/elixir/spec/syntax/default_argument_spec.rb b/bundle/elixir/spec/syntax/default_argument_spec.rb deleted file mode 100755 index ec69a3e..0000000 --- a/bundle/elixir/spec/syntax/default_argument_spec.rb +++ /dev/null @@ -1,13 +0,0 @@ -require 'spec_helper' - -describe "Default argument syntax" do - it "default argument" do - assert_correct_syntax 'elixirOperator', '\\', <<-'EOF' - def foo(bar \\ :baz) - EOF - - assert_correct_syntax 'elixirOperator', '\/', <<-EOF - def foo(bar // :baz) - EOF - end -end diff --git a/bundle/elixir/spec/syntax/heredoc_spec.rb b/bundle/elixir/spec/syntax/heredoc_spec.rb deleted file mode 100755 index eb50a4f..0000000 --- a/bundle/elixir/spec/syntax/heredoc_spec.rb +++ /dev/null @@ -1,63 +0,0 @@ -require 'spec_helper' - -describe "Heredoc syntax" do - describe "binary" do - it "with multiline content" do - assert_correct_syntax 'elixirDocString', 'foo', <<-EOF - @doc """ - foo - """ - EOF - end - - it "escapes quotes unless only preceded by whitespace" do - assert_correct_syntax 'elixirDocString', %q(^\s*\zs"""), <<-EOF - @doc """ - foo """ - """ - EOF - end - - it "does not include content on initial line", focus: true do - assert_correct_syntax 'elixirNumber', '0', <<-EOF - String.at """, 0 - foo - end - EOF - end - - it "with interpolation" do - assert_correct_syntax 'elixirInterpolation', 'bar', <<-EOF - @doc """ - foo \#{bar} - """ - EOF - end - end - - describe "character list" do - it "with multiline content" do - assert_correct_syntax 'elixirDocString', 'foo', <<-EOF - @doc """ - foo - """ - EOF - end - - it "escapes quotes unless only preceded by whitespace" do - assert_correct_syntax 'elixirDocString', %q(^\s*\zs'''), <<-EOF - @doc ''' - foo ''' - ''' - EOF - end - - it "with interpolation" do - assert_correct_syntax 'elixirInterpolation', 'bar', <<-EOF - @doc ''' - foo \#{bar} - ''' - EOF - end - end -end diff --git a/bundle/elixir/spec/syntax/records_spec.rb b/bundle/elixir/spec/syntax/records_spec.rb deleted file mode 100755 index b68814a..0000000 --- a/bundle/elixir/spec/syntax/records_spec.rb +++ /dev/null @@ -1,10 +0,0 @@ -# encoding: utf-8 -require 'spec_helper' - -describe "Record syntax" do - it "private record symbol" do - assert_correct_syntax 'elixirSymbol', ':user', <<-EOF - defrecordp :user, name: "José", age: 25 - EOF - end -end diff --git a/bundle/elixir/spec/syntax/sigil_spec.rb b/bundle/elixir/spec/syntax/sigil_spec.rb deleted file mode 100755 index ef68304..0000000 --- a/bundle/elixir/spec/syntax/sigil_spec.rb +++ /dev/null @@ -1,109 +0,0 @@ -require 'spec_helper' - -describe "Sigil syntax" do - describe "upper case" do - it "string" do - assert_correct_syntax 'elixirDelimiter', 'S', '~S(string)' - assert_correct_syntax 'elixirSigil', 'foo', '~S(string)' - end - - it "character list" do - assert_correct_syntax 'elixirDelimiter', 'C', '~C(charlist)' - assert_correct_syntax 'elixirSigil', 'charlist', '~C(charlist)' - end - - it "regular expression" do - assert_correct_syntax 'elixirDelimiter', 'R', '~R(regex)' - assert_correct_syntax 'elixirSigil', 'regex', '~R(regex)' - end - - it "list of words" do - assert_correct_syntax 'elixirDelimiter', 'W', '~W(list of words)' - assert_correct_syntax 'elixirSigil', 'list', '~W(list of words)' - end - - it "delimited with parans" do - assert_correct_syntax 'elixirDelimiter', '(', '~S(foo bar)' - assert_correct_syntax 'elixirDelimiter', ')', '~S(foo bar)' - end - - it "delimited with braces" do - assert_correct_syntax 'elixirDelimiter', '{', '~S{foo bar}' - assert_correct_syntax 'elixirDelimiter', '}', '~S{foo bar}' - end - - it "delimited with brackets" do - assert_correct_syntax 'elixirDelimiter', '[', '~S[foo bar]' - assert_correct_syntax 'elixirDelimiter', ']', '~S[foo bar]' - end - - it "escapes double quotes unless only preceded by whitespace" do - assert_correct_syntax 'elixirDelimiter', %q(^\s*\zs"""), <<-EOF - ~r""" - foo """ - """ - EOF - end - - it "escapes single quotes unless only preceded by whitespace" do - assert_correct_syntax 'elixirDelimiter', %q(^\s*\zs'''), <<-EOF - ~r''' - foo ''' - ''' - EOF - end - - it "without escapes" do - assert_incorrect_syntax 'elixirRegexEscape', '\\', '~S(foo \n bar)' - end - - it "without interpolation" do - assert_incorrect_syntax 'elixirInterpolation', 'bar', '~S(foo #{bar})' - end - - it "without escaped parans" do - assert_incorrect_syntax 'elixirRegexEscapePunctuation', '( ', '~S(\( )' - end - end - - describe "lower case" do - it "string" do - assert_correct_syntax 'elixirDelimiter', 's', '~s(string)' - assert_correct_syntax 'elixirSigil', 'foo', '~s(string)' - end - - it "character list" do - assert_correct_syntax 'elixirDelimiter', 'c', '~c(charlist)' - assert_correct_syntax 'elixirSigil', 'charlist', '~c(charlist)' - end - - it "regular expression" do - assert_correct_syntax 'elixirDelimiter', 'r', '~r(regex)' - assert_correct_syntax 'elixirSigil', 'regex', '~r(regex)' - end - - it "list of words" do - assert_correct_syntax 'elixirDelimiter', 'w', '~w(list of words)' - assert_correct_syntax 'elixirSigil', 'list', '~w(list of words)' - end - - it "with escapes" do - assert_correct_syntax 'elixirRegexEscape', '\\', '~s(foo \n bar)' - end - - it "with interpolation" do - assert_correct_syntax 'elixirInterpolation', 'bar', '~s(foo #{bar})' - end - - it "with escaped parans" do - assert_correct_syntax 'elixirRegexEscapePunctuation', '( ', '~s(\( )' - end - end - - describe "old syntax" do - it "string" do - assert_correct_syntax 'elixirDelimiter', 's', '%s(string)' - assert_correct_syntax 'elixirSigil', 'foo', '%s(string)' - end - end -end diff --git a/bundle/elixir/spec/syntax/variable_spec.rb b/bundle/elixir/spec/syntax/variable_spec.rb deleted file mode 100755 index 2877e7f..0000000 --- a/bundle/elixir/spec/syntax/variable_spec.rb +++ /dev/null @@ -1,11 +0,0 @@ -require 'spec_helper' - -describe "Variable syntax" do - it "unused" do - assert_correct_syntax 'elixirUnusedVariable', '_from', <<-EOF - def handle_call(:pop, _from, [h|stack]) do - { :reply, h, stack } - end - EOF - end -end diff --git a/bundle/elixir/syntax/elixir.vim b/bundle/elixir/syntax/elixir.vim deleted file mode 100755 index ff58d55..0000000 --- a/bundle/elixir/syntax/elixir.vim +++ /dev/null @@ -1,166 +0,0 @@ -" Vim syntax file -" Language: Elixir -" Maintainer: Carlos Galdino -" Last Change: 2013 Apr 24 - -if exists("b:current_syntax") - finish -endif - -" syncing starts 2000 lines before top line so docstrings don't screw things up -syn sync minlines=2000 - -syn cluster elixirNotTop contains=@elixirRegexSpecial,@elixirStringContained,@elixirDeclaration,elixirTodo,elixirArguments - -syn match elixirComment '#.*' contains=elixirTodo -syn keyword elixirTodo FIXME NOTE TODO OPTIMIZE XXX HACK contained - -syn keyword elixirKeyword is_atom is_binary is_bitstring is_boolean is_float is_function is_integer is_list is_number is_pid is_port is_record is_reference is_tuple is_exception -syn keyword elixirKeyword case cond bc lc inlist inbits if unless try receive -syn keyword elixirKeyword exit raise throw after rescue catch else do end -syn keyword elixirKeyword quote unquote super -syn match elixirKeyword '\<\%(->\)\>\s*' - -syn keyword elixirInclude import require alias use - -syn keyword elixirOperator and not or when xor in -syn match elixirOperator '%=\|\*=\|\*\*=\|+=\|-=\|\^=\|||=' -syn match elixirOperator "\%(<=>\|<\%(<\|=\)\@!\|>\%(<\|=\|>\)\@!\|<=\|>=\|===\|==\|=\~\|!=\|!\~\|\s?[ \t]\@=\)" -syn match elixirOperator "!+[ \t]\@=\|&&\|||\|\^\|\*\|+\|-\|/" -syn match elixirOperator "|\|++\|--\|\*\*\|\/\/\|\\\\\|<-\|<>\|<<\|>>\|=\|\.\|::" - -syn match elixirSymbol '\(:\)\@=]\@!\)\?\|<>\|===\?\|>=\?\|<=\?\)' -syn match elixirSymbol '\(:\)\@\|&&\?\|%\(()\|\[\]\|{}\)\|++\?\|--\?\|||\?\|!\|//\|[%&`/|]\)' -syn match elixirSymbol "\%([a-zA-Z_]\w*\([?!]\)\?\):\(:\)\@!" - -syn keyword elixirName nil -syn match elixirName '\<[A-Z]\w*\>' - -syn match elixirUnusedVariable '\<_\w*\>' - -syn keyword elixirBoolean true false - -syn match elixirVariable '@[a-zA-Z_]\w*\|&\d' - -syn keyword elixirPseudoVariable __FILE__ __DIR__ __MODULE__ __ENV__ __CALLER__ - -syn match elixirNumber '\<\d\(_\?\d\)*\(\.[^[:space:][:digit:]]\@!\(_\?\d\)*\)\?\([eE][-+]\?\d\(_\?\d\)*\)\?\>' -syn match elixirNumber '\<0[xX][0-9A-Fa-f]\+\>' -syn match elixirNumber '\<0[bB][01]\+\>' - -syn match elixirRegexEscape "\\\\\|\\[aAbBcdDefGhHnrsStvVwW]\|\\\d\{3}\|\\x[0-9a-fA-F]\{2}" contained -syn match elixirRegexEscapePunctuation "?\|\\.\|*\|\\\[\|\\\]\|+\|\\^\|\\\$\|\\|\|\\(\|\\)\|\\{\|\\}" contained -syn match elixirRegexQuantifier "[*?+][?+]\=" contained display -syn match elixirRegexQuantifier "{\d\+\%(,\d*\)\=}?\=" contained display -syn match elixirRegexCharClass "\[:\(alnum\|alpha\|ascii\|blank\|cntrl\|digit\|graph\|lower\|print\|punct\|space\|upper\|word\|xdigit\):\]" contained display - -syn region elixirRegex matchgroup=elixirDelimiter start="%r/" end="/[uiomxfr]*" skip="\\\\" contains=@elixirRegexSpecial - -syn cluster elixirRegexSpecial contains=elixirRegexEscape,elixirRegexCharClass,elixirRegexQuantifier,elixirRegexEscapePunctuation -syn cluster elixirStringContained contains=elixirInterpolation,elixirRegexEscape,elixirRegexCharClass - -syn region elixirString matchgroup=elixirDelimiter start="'" end="'" skip="\\'" -syn region elixirString matchgroup=elixirDelimiter start='"' end='"' skip='\\"' contains=@elixirStringContained -syn region elixirInterpolation matchgroup=elixirDelimiter start="#{" end="}" contained contains=ALLBUT,elixirComment,@elixirNotTop - -syn region elixirDocStringStart matchgroup=elixirDocString start=+"""+ end=+$+ oneline contains=ALLBUT,@elixirNotTop -syn region elixirDocStringStart matchgroup=elixirDocString start=+'''+ end=+$+ oneline contains=ALLBUT,@elixirNotTop -syn region elixirDocString start=+\z("""\)+ end=+^\s*\zs\z1+ contains=elixirDocStringStart,elixirTodo,elixirInterpolation fold keepend -syn region elixirDocString start=+\z('''\)+ end=+^\s*\zs\z1+ contains=elixirDocStringStart,elixirTodo,elixirInterpolation fold keepend - -syn match elixirSymbolInterpolated ':\("\)\@=' contains=elixirString -syn match elixirString "\(\w\)\@\|0[0-7]{0,2}[0-7]\@!\>\|[^x0MC]\)\|(\\[MC]-)+\w\|[^\s\\]\)" - -syn region elixirBlock matchgroup=elixirKeyword start="\\(:\)\@!" end="\" contains=ALLBUT,@elixirNotTop fold -syn region elixirAnonymousFunction matchgroup=elixirKeyword start="\" end="\" contains=ALLBUT,@elixirNotTop fold - -syn region elixirArguments start="(" end=")" contained contains=elixirOperator,elixirSymbol,elixirPseudoVariable,elixirName,elixirBoolean,elixirVariable,elixirUnusedVariable,elixirNumber,elixirDocString,elixirSymbolInterpolated,elixirRegex,elixirString,elixirDelimiter - -syn match elixirDelimEscape "\\[(<{\[)>}\]]" transparent display contained contains=NONE - -syn region elixirSigil matchgroup=elixirDelimiter start="[%~]\z([~`!@#$%^&*_\-+|\:;"',.?/]\)" end="\z1" skip="\\\\\|\\\z1" fold -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][SCRW]\z([~`!@#$%^&*_\-+=|\:;"',.?/]\)" end="\z1" skip="\\\\\|\\\z1" fold -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][SCRW]\={" end="}" skip="\\\\\|\\}" contains=elixirDelimEscape fold -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][SCRW]\=<" end=">" skip="\\\\\|\\>" contains=elixirDelimEscape fold -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][SCRW]\=\[" end="\]" skip="\\\\\|\\\]" contains=elixirDelimEscape fold -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][SCRW]\=(" end=")" skip="\\\\\|\\)" contains=elixirDelimEscape fold - -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][scrw]\z([~`!@#$%^&*_\-+=|\:;"',.?/]\)" end="\z1" skip="\\\\\|\\\z1" fold -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][scrw]{" end="}" skip="\\\\\|\\}" fold contains=@elixirStringContained,elixirRegexEscapePunctuation -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][scrw]<" end=">" skip="\\\\\|\\>" fold contains=@elixirStringContained,elixirRegexEscapePunctuation -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][scrw]\[" end="\]" skip="\\\\\|\\\]" fold contains=@elixirStringContained,elixirRegexEscapePunctuation -syn region elixirSigil matchgroup=elixirDelimiter start="[%~][scrw](" end=")" skip="\\\\\|\\)" fold contains=@elixirStringContained,elixirRegexEscapePunctuation - -" Sigils surrounded with docString -syn region elixirSigil matchgroup=elixirDelimiter start=+[%~][SCRWscrw]\z("""\)+ end=+^\s*\zs\z1+ skip=+\\"+ fold -syn region elixirSigil matchgroup=elixirDelimiter start=+[%~][SCRWscrw]\z('''\)+ end=+^\s*\zs\z1+ skip=+\\'+ fold - -" Defines -syn keyword elixirDefine def nextgroup=elixirFunctionDeclaration skipwhite skipnl -syn keyword elixirDefine def nextgroup=elixirFunctionDeclaration skipwhite skipnl -syn keyword elixirPrivateDefine defp nextgroup=elixirFunctionDeclaration skipwhite skipnl -syn keyword elixirModuleDefine defmodule nextgroup=elixirModuleDeclaration skipwhite skipnl -syn keyword elixirProtocolDefine defprotocol nextgroup=elixirProtocolDeclaration skipwhite skipnl -syn keyword elixirImplDefine defimpl nextgroup=elixirImplDeclaration skipwhite skipnl -syn keyword elixirRecordDefine defrecord nextgroup=elixirRecordDeclaration skipwhite skipnl -syn keyword elixirPrivateRecordDefine defrecordp nextgroup=elixirRecordDeclaration skipwhite skipnl -syn keyword elixirMacroDefine defmacro nextgroup=elixirMacroDeclaration skipwhite skipnl -syn keyword elixirPrivateMacroDefine defmacrop nextgroup=elixirMacroDeclaration skipwhite skipnl -syn keyword elixirDelegateDefine defdelegate nextgroup=elixirDelegateDeclaration skipwhite skipnl -syn keyword elixirOverridableDefine defoverridable nextgroup=elixirOverridableDeclaration skipwhite skipnl -syn keyword elixirExceptionDefine defexception nextgroup=elixirExceptionDeclaration skipwhite skipnl -syn keyword elixirCallbackDefine defcallback nextgroup=elixirCallbackDeclaration skipwhite skipnl - -" Declarations -syn match elixirModuleDeclaration "[^[:space:];#<]\+" contained contains=elixirName nextgroup=elixirBlock skipwhite skipnl -syn match elixirFunctionDeclaration "[^[:space:];#<,()\[\]]\+" contained nextgroup=elixirArguments skipwhite skipnl -syn match elixirProtocolDeclaration "[^[:space:];#<]\+" contained contains=elixirName skipwhite skipnl -syn match elixirImplDeclaration "[^[:space:];#<]\+" contained contains=elixirName skipwhite skipnl -syn match elixirRecordDeclaration "[^[:space:];#<]\+" contained contains=elixirName,elixirSymbol skipwhite skipnl -syn match elixirMacroDeclaration "[^[:space:];#<,()\[\]]\+" contained nextgroup=elixirArguments skipwhite skipnl -syn match elixirDelegateDeclaration "[^[:space:];#<,()\[\]]\+" contained contains=elixirFunctionDeclaration skipwhite skipnl -syn region elixirDelegateDeclaration start='\[' end='\]' contained contains=elixirFunctionDeclaration skipwhite skipnl -syn match elixirOverridableDeclaration "[^[:space:];#<]\+" contained contains=elixirName skipwhite skipnl -syn match elixirExceptionDeclaration "[^[:space:];#<]\+" contained contains=elixirName skipwhite skipnl -syn match elixirCallbackDeclaration "[^[:space:];#<,()\[\]]\+" contained contains=elixirFunctionDeclaration skipwhite skipnl - -syn cluster elixirDeclaration contains=elixirFunctionDeclaration,elixirModuleDeclaration,elixirProtocolDeclaration,elixirImplDeclaration,elixirRecordDeclaration,elixirMacroDeclaration,elixirDelegateDeclaration,elixirOverridableDeclaration,elixirExceptionDeclaration,elixirCallbackDeclaration - -hi def link elixirDefine Define -hi def link elixirPrivateDefine Define -hi def link elixirModuleDefine Define -hi def link elixirProtocolDefine Define -hi def link elixirImplDefine Define -hi def link elixirRecordDefine Define -hi def link elixirPrivateRecordDefine Define -hi def link elixirMacroDefine Define -hi def link elixirPrivateMacroDefine Define -hi def link elixirDelegateDefine Define -hi def link elixirOverridableDefine Define -hi def link elixirExceptionDefine Define -hi def link elixirCallbackDefine Define -hi def link elixirFunctionDeclaration Function -hi def link elixirMacroDeclaration Macro -hi def link elixirInclude Include -hi def link elixirComment Comment -hi def link elixirTodo Todo -hi def link elixirKeyword Keyword -hi def link elixirOperator Operator -hi def link elixirSymbol Constant -hi def link elixirPseudoVariable Constant -hi def link elixirName Type -hi def link elixirBoolean Boolean -hi def link elixirVariable Identifier -hi def link elixirUnusedVariable Comment -hi def link elixirNumber Number -hi def link elixirDocString String -hi def link elixirSymbolInterpolated elixirSymbol -hi def link elixirRegex elixirString -hi def link elixirRegexEscape elixirSpecial -hi def link elixirRegexEscapePunctuation elixirSpecial -hi def link elixirRegexCharClass elixirSpecial -hi def link elixirRegexQuantifier elixirSpecial -hi def link elixirSpecial Special -hi def link elixirString String -hi def link elixirSigil String -hi def link elixirDelimiter Delimiter diff --git a/bundle/groovy/syntax/groovy.vim b/bundle/groovy/syntax/groovy.vim deleted file mode 100644 index 5f96dfb..0000000 --- a/bundle/groovy/syntax/groovy.vim +++ /dev/null @@ -1,450 +0,0 @@ -" Vim syntax file -" Language: Groovy -" Maintainer: Alessio Pace -" Version: 0.1.9b -" URL: http://www.vim.org/scripts/script.php?script_id=945 -" Last Change: 6/4/2004 - -" This is my very first vim script, I hope to have -" done it the right way. -" -" I must directly or indirectly thank the author of java.vim and ruby.vim: -" I copied from them most of the stuff :-) -" -" Relies on html.vim - -" For version 5.x: Clear all syntax items -" For version 6.x: Quit when a syntax file was already loaded -" -" HOWTO USE IT (INSTALL): -" [groovy is still not recognized by vim! :-( ] -" -" 1) copy the file in the (global or user's $HOME/.vim/syntax/) syntax folder -" -" 2) add this line to recognize groovy files by filename extension: -" -" au BufNewFile,BufRead *.groovy setf groovy -" in the global vim filetype.vim file or inside $HOME/.vim/filetype.vim -" -" 3) add this part to recognize by content groovy script (no extension needed :-) -" -" if did_filetype() -" finish -" endif -" if getline(1) =~ '^#!.*[/\\]groovy\>' -" setf groovy -" endif -" -" in the global scripts.vim file or in $HOME/.vim/scripts.vim -" -" 4) open/write a .groovy file or a groovy script :-) -" -" Let me know if you like it or send me patches, so that I can improve it -" when I have time - -" Quit when a syntax file was already loaded -if !exists("main_syntax") - if version < 600 - syntax clear - elseif exists("b:current_syntax") - finish - endif - " we define it here so that included files can test for it - let main_syntax='groovy' -endif - -" don't use standard HiLink, it will not work with included syntax files -if version < 508 - command! -nargs=+ GroovyHiLink hi link -else - command! -nargs=+ GroovyHiLink hi def link -endif - -" ########################## -" Java stuff taken from java.vim -" some characters that cannot be in a groovy program (outside a string) -" syn match groovyError "[\\@`]" -"syn match groovyError "<<<\|\.\.\|=>\|<>\|||=\|&&=\|[^-]->\|\*\/" -"syn match groovyOK "\.\.\." - -" keyword definitions -syn keyword groovyExternal native package -syn match groovyExternal "\\)\?" -syn keyword groovyError goto const -syn keyword groovyConditional if else switch -syn keyword groovyRepeat while for do -syn keyword groovyBoolean true false -syn keyword groovyConstant null -syn keyword groovyTypedef this super -syn keyword groovyOperator new instanceof -syn keyword groovyType boolean char byte short int long float double -syn keyword groovyType void -syn keyword groovyType Integer Double Date Boolean Float String Array Vector List -syn keyword groovyStatement return -syn keyword groovyStorageClass static synchronized transient volatile final strictfp serializable -syn keyword groovyExceptions throw try catch finally -syn keyword groovyAssert assert -syn keyword groovyMethodDecl synchronized throws -syn keyword groovyClassDecl extends implements interface -" to differentiate the keyword class from MyClass.class we use a match here -syn match groovyTypedef "\.\s*\"ms=s+1 -syn keyword groovyClassDecl enum -syn match groovyClassDecl "^class\>" -syn match groovyClassDecl "[^.]\s*\"ms=s+1 -syn keyword groovyBranch break continue nextgroup=groovyUserLabelRef skipwhite -syn match groovyUserLabelRef "\k\+" contained -syn keyword groovyScopeDecl public protected private abstract - - -if exists("groovy_highlight_groovy_lang_ids") || exists("groovy_highlight_groovy_lang") || exists("groovy_highlight_all") - " groovy.lang.* - syn keyword groovyLangClass Closure MetaMethod GroovyObject - - syn match groovyJavaLangClass "\" - syn keyword groovyJavaLangClass Cloneable Comparable Runnable Serializable Boolean Byte Class Object - syn keyword groovyJavaLangClass Character CharSequence ClassLoader Compiler - " syn keyword groovyJavaLangClass Integer Double Float Long - syn keyword groovyJavaLangClass InheritableThreadLocal Math Number Object Package Process - syn keyword groovyJavaLangClass Runtime RuntimePermission InheritableThreadLocal - syn keyword groovyJavaLangClass SecurityManager Short StrictMath StackTraceElement - syn keyword groovyJavaLangClass StringBuffer Thread ThreadGroup - syn keyword groovyJavaLangClass ThreadLocal Throwable Void ArithmeticException - syn keyword groovyJavaLangClass ArrayIndexOutOfBoundsException AssertionError - syn keyword groovyJavaLangClass ArrayStoreException ClassCastException - syn keyword groovyJavaLangClass ClassNotFoundException - syn keyword groovyJavaLangClass CloneNotSupportedException Exception - syn keyword groovyJavaLangClass IllegalAccessException - syn keyword groovyJavaLangClass IllegalArgumentException - syn keyword groovyJavaLangClass IllegalMonitorStateException - syn keyword groovyJavaLangClass IllegalStateException - syn keyword groovyJavaLangClass IllegalThreadStateException - syn keyword groovyJavaLangClass IndexOutOfBoundsException - syn keyword groovyJavaLangClass InstantiationException InterruptedException - syn keyword groovyJavaLangClass NegativeArraySizeException NoSuchFieldException - syn keyword groovyJavaLangClass NoSuchMethodException NullPointerException - syn keyword groovyJavaLangClass NumberFormatException RuntimeException - syn keyword groovyJavaLangClass SecurityException StringIndexOutOfBoundsException - syn keyword groovyJavaLangClass UnsupportedOperationException - syn keyword groovyJavaLangClass AbstractMethodError ClassCircularityError - syn keyword groovyJavaLangClass ClassFormatError Error ExceptionInInitializerError - syn keyword groovyJavaLangClass IllegalAccessError InstantiationError - syn keyword groovyJavaLangClass IncompatibleClassChangeError InternalError - syn keyword groovyJavaLangClass LinkageError NoClassDefFoundError - syn keyword groovyJavaLangClass NoSuchFieldError NoSuchMethodError - syn keyword groovyJavaLangClass OutOfMemoryError StackOverflowError - syn keyword groovyJavaLangClass ThreadDeath UnknownError UnsatisfiedLinkError - syn keyword groovyJavaLangClass UnsupportedClassVersionError VerifyError - syn keyword groovyJavaLangClass VirtualMachineError - - syn keyword groovyJavaLangObject clone equals finalize getClass hashCode - syn keyword groovyJavaLangObject notify notifyAll toString wait - - GroovyHiLink groovyLangClass groovyConstant - GroovyHiLink groovyJavaLangClass groovyExternal - GroovyHiLink groovyJavaLangObject groovyConstant - syn cluster groovyTop add=groovyJavaLangObject,groovyJavaLangClass,groovyLangClass - syn cluster groovyClasses add=groovyJavaLangClass,groovyLangClass -endif - - -" Groovy stuff -syn match groovyOperator "\.\." -syn match groovyOperator "<\{2,3}" -syn match groovyOperator ">\{2,3}" -syn match groovyOperator "->" -syn match groovyExternal '^#!.*[/\\]groovy\>' -syn match groovyExceptions "\\|\<[A-Z]\{1,}[a-zA-Z0-9]*Exception\>" - -" Groovy JDK stuff -syn keyword groovyJDKBuiltin as def in -syn keyword groovyJDKOperOverl div minus plus abs round power multiply -syn keyword groovyJDKMethods each call inject sort print println -syn keyword groovyJDKMethods getAt putAt size push pop toList getText writeLine eachLine readLines -syn keyword groovyJDKMethods withReader withStream withWriter withPrintWriter write read leftShift -syn keyword groovyJDKMethods withWriterAppend readBytes splitEachLine -syn keyword groovyJDKMethods newInputStream newOutputStream newPrintWriter newReader newWriter -syn keyword groovyJDKMethods compareTo next previous isCase -syn keyword groovyJDKMethods times step toInteger upto any collect dump every find findAll grep -syn keyword groovyJDKMethods inspect invokeMethods join -syn keyword groovyJDKMethods getErr getIn getOut waitForOrKill -syn keyword groovyJDKMethods count tokenize asList flatten immutable intersect reverse reverseEach -syn keyword groovyJDKMethods subMap append asWritable eachByte eachLine eachFile -syn cluster groovyTop add=groovyJDKBuiltin,groovyJDKOperOverl,groovyJDKMethods - -" no useful I think, so I comment it.. -"if filereadable(expand(":p:h")."/groovyid.vim") - " source :p:h/groovyid.vim -"endif - -if exists("groovy_space_errors") - if !exists("groovy_no_trail_space_error") - syn match groovySpaceError "\s\+$" - endif - if !exists("groovy_no_tab_space_error") - syn match groovySpaceError " \+\t"me=e-1 - endif -endif - -" it is a better case construct than java.vim to match groovy syntax -syn region groovyLabelRegion transparent matchgroup=groovyLabel start="\" matchgroup=NONE end=":\|$" contains=groovyNumber,groovyString,groovyLangClass,groovyJavaLangClass -syn match groovyUserLabel "^\s*[_$a-zA-Z][_$a-zA-Z0-9_]*\s*:"he=e-1 contains=groovyLabel -syn keyword groovyLabel default - -if !exists("groovy_allow_cpp_keywords") - syn keyword groovyError auto delete extern friend inline redeclared - syn keyword groovyError register signed sizeof struct template typedef union - syn keyword groovyError unsigned operator -endif - -" The following cluster contains all groovy groups except the contained ones -syn cluster groovyTop add=groovyExternal,groovyError,groovyError,groovyBranch,groovyLabelRegion,groovyLabel,groovyConditional,groovyRepeat,groovyBoolean,groovyConstant,groovyTypedef,groovyOperator,groovyType,groovyType,groovyStatement,groovyStorageClass,groovyAssert,groovyExceptions,groovyMethodDecl,groovyClassDecl,groovyClassDecl,groovyClassDecl,groovyScopeDecl,groovyError,groovyError2,groovyUserLabel,groovyLangObject - - -" Comments -syn keyword groovyTodo contained TODO FIXME XXX -if exists("groovy_comment_strings") - syn region groovyCommentString contained start=+"+ end=+"+ end=+$+ end=+\*/+me=s-1,he=s-1 contains=groovySpecial,groovyCommentStar,groovySpecialChar,@Spell - syn region groovyComment2String contained start=+"+ end=+$\|"+ contains=groovySpecial,groovySpecialChar,@Spell - syn match groovyCommentCharacter contained "'\\[^']\{1,6\}'" contains=groovySpecialChar - syn match groovyCommentCharacter contained "'\\''" contains=groovySpecialChar - syn match groovyCommentCharacter contained "'[^\\]'" - syn cluster groovyCommentSpecial add=groovyCommentString,groovyCommentCharacter,groovyNumber - syn cluster groovyCommentSpecial2 add=groovyComment2String,groovyCommentCharacter,groovyNumber -endif -syn region groovyComment start="/\*" end="\*/" contains=@groovyCommentSpecial,groovyTodo,@Spell -syn match groovyCommentStar contained "^\s*\*[^/]"me=e-1 -syn match groovyCommentStar contained "^\s*\*$" -syn match groovyLineComment "//.*" contains=@groovyCommentSpecial2,groovyTodo,@Spell -syn match groovyLineComment "#.*" contains=@groovyCommentSpecial2,groovyTodo,@Spell -GroovyHiLink groovyCommentString groovyString -GroovyHiLink groovyComment2String groovyString -GroovyHiLink groovyCommentCharacter groovyCharacter - -syn cluster groovyTop add=groovyComment,groovyLineComment - -if !exists("groovy_ignore_groovydoc") && main_syntax != 'jsp' - syntax case ignore - " syntax coloring for groovydoc comments (HTML) - " syntax include @groovyHtml :p:h/html.vim - syntax include @groovyHtml runtime! syntax/html.vim - unlet b:current_syntax - syn region groovyDocComment start="/\*\*" end="\*/" keepend contains=groovyCommentTitle,@groovyHtml,groovyDocTags,groovyTodo,@Spell - syn region groovyCommentTitle contained matchgroup=groovyDocComment start="/\*\*" matchgroup=groovyCommentTitle keepend end="\.$" end="\.[ \t\r<&]"me=e-1 end="[^{]@"me=s-2,he=s-1 end="\*/"me=s-1,he=s-1 contains=@groovyHtml,groovyCommentStar,groovyTodo,@Spell,groovyDocTags - - syn region groovyDocTags contained start="{@\(link\|linkplain\|inherit[Dd]oc\|doc[rR]oot\|value\)" end="}" - syn match groovyDocTags contained "@\(see\|param\|exception\|throws\|since\)\s\+\S\+" contains=groovyDocParam - syn match groovyDocParam contained "\s\S\+" - syn match groovyDocTags contained "@\(version\|author\|return\|deprecated\|serial\|serialField\|serialData\)\>" - syntax case match -endif - -" match the special comment /**/ -syn match groovyComment "/\*\*/" - -" Strings and constants -syn match groovySpecialError contained "\\." -syn match groovySpecialCharError contained "[^']" -syn match groovySpecialChar contained "\\\([4-9]\d\|[0-3]\d\d\|[\"\\'ntbrf]\|u\x\{4\}\)" -syn region groovyString start=+"+ end=+"+ end=+$+ contains=groovySpecialChar,groovySpecialError,@Spell,groovyELExpr -syn region groovyString start=+'+ end=+'+ end=+$+ contains=groovySpecialChar,groovySpecialError,@Spell,groovyELExpr -" syn region groovyELExpr start=+${+ end=+}+ keepend contained - syn match groovyELExpr /\${.\{-}}/ contained -GroovyHiLink groovyELExpr Identifier - -" TODO: better matching. I am waiting to understand how it really works in groovy -" syn region groovyClosureParamsBraces start=+|+ end=+|+ contains=groovyClosureParams -" syn match groovyClosureParams "[ a-zA-Z0-9_*]\+" contained -" GroovyHiLink groovyClosureParams Identifier - -" next line disabled, it can cause a crash for a long line -"syn match groovyStringError +"\([^"\\]\|\\.\)*$+ - -" disabled: in groovy strings or characters are written the same -" syn match groovyCharacter "'[^']*'" contains=groovySpecialChar,groovySpecialCharError -" syn match groovyCharacter "'\\''" contains=groovySpecialChar -" syn match groovyCharacter "'[^\\]'" -syn match groovyNumber "\<\(0[0-7]*\|0[xX]\x\+\|\d\+\)[lL]\=\>" -syn match groovyNumber "\(\<\d\+\.\d*\|\.\d\+\)\([eE][-+]\=\d\+\)\=[fFdD]\=" -syn match groovyNumber "\<\d\+[eE][-+]\=\d\+[fFdD]\=\>" -syn match groovyNumber "\<\d\+\([eE][-+]\=\d\+\)\=[fFdD]\>" - -" unicode characters -syn match groovySpecial "\\u\d\{4\}" - -syn cluster groovyTop add=groovyString,groovyCharacter,groovyNumber,groovySpecial,groovyStringError - -if exists("groovy_highlight_functions") - if groovy_highlight_functions == "indent" - syn match groovyFuncDef "^\(\t\| \{8\}\)[_$a-zA-Z][_$a-zA-Z0-9_. \[\]]*([^-+*/()]*)" contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses - syn region groovyFuncDef start=+^\(\t\| \{8\}\)[$_a-zA-Z][$_a-zA-Z0-9_. \[\]]*([^-+*/()]*,\s*+ end=+)+ contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses - syn match groovyFuncDef "^ [$_a-zA-Z][$_a-zA-Z0-9_. \[\]]*([^-+*/()]*)" contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses - syn region groovyFuncDef start=+^ [$_a-zA-Z][$_a-zA-Z0-9_. \[\]]*([^-+*/()]*,\s*+ end=+)+ contains=groovyScopeDecl,groovyType,groovyStorageClass,@groovyClasses - else - " This line catches method declarations at any indentation>0, but it assumes - " two things: - " 1. class names are always capitalized (ie: Button) - " 2. method names are never capitalized (except constructors, of course) - syn region groovyFuncDef start=+^\s\+\(\(public\|protected\|private\|static\|abstract\|final\|native\|synchronized\)\s\+\)*\(\(void\|boolean\|char\|byte\|short\|int\|long\|float\|double\|\([A-Za-z_][A-Za-z0-9_$]*\.\)*[A-Z][A-Za-z0-9_$]*\)\(<[^>]*>\)\=\(\[\]\)*\s\+[a-z][A-Za-z0-9_$]*\|[A-Z][A-Za-z0-9_$]*\)\s*([^0-9]+ end=+)+ contains=groovyScopeDecl,groovyType,groovyStorageClass,groovyComment,groovyLineComment,@groovyClasses - endif - syn match groovyBraces "[{}]" - syn cluster groovyTop add=groovyFuncDef,groovyBraces -endif - -if exists("groovy_highlight_debug") - - " Strings and constants - syn match groovyDebugSpecial contained "\\\d\d\d\|\\." - syn region groovyDebugString contained start=+"+ end=+"+ contains=groovyDebugSpecial - syn match groovyDebugStringError +"\([^"\\]\|\\.\)*$+ - syn match groovyDebugCharacter contained "'[^\\]'" - syn match groovyDebugSpecialCharacter contained "'\\.'" - syn match groovyDebugSpecialCharacter contained "'\\''" - syn match groovyDebugNumber contained "\<\(0[0-7]*\|0[xX]\x\+\|\d\+\)[lL]\=\>" - syn match groovyDebugNumber contained "\(\<\d\+\.\d*\|\.\d\+\)\([eE][-+]\=\d\+\)\=[fFdD]\=" - syn match groovyDebugNumber contained "\<\d\+[eE][-+]\=\d\+[fFdD]\=\>" - syn match groovyDebugNumber contained "\<\d\+\([eE][-+]\=\d\+\)\=[fFdD]\>" - syn keyword groovyDebugBoolean contained true false - syn keyword groovyDebugType contained null this super - syn region groovyDebugParen start=+(+ end=+)+ contained contains=groovyDebug.*,groovyDebugParen - - " to make this work you must define the highlighting for these groups - syn match groovyDebug "\= 508 || !exists("did_c_syn_inits") - GroovyHiLink groovyDebug Debug - GroovyHiLink groovyDebugString DebugString - GroovyHiLink groovyDebugStringError groovyError - GroovyHiLink groovyDebugType DebugType - GroovyHiLink groovyDebugBoolean DebugBoolean - GroovyHiLink groovyDebugNumber Debug - GroovyHiLink groovyDebugSpecial DebugSpecial - GroovyHiLink groovyDebugSpecialCharacter DebugSpecial - GroovyHiLink groovyDebugCharacter DebugString - GroovyHiLink groovyDebugParen Debug - - GroovyHiLink DebugString String - GroovyHiLink DebugSpecial Special - GroovyHiLink DebugBoolean Boolean - GroovyHiLink DebugType Type - endif -endif - -" Match all Exception classes -syn match groovyExceptions "\\|\<[A-Z]\{1,}[a-zA-Z0-9]*Exception\>" - - -if !exists("groovy_minlines") - let groovy_minlines = 10 -endif -exec "syn sync ccomment groovyComment minlines=" . groovy_minlines - - -" ################### -" Groovy stuff -" syn match groovyOperator "|[ ,a-zA-Z0-9_*]\+|" - -" All groovy valid tokens -" syn match groovyTokens ";\|,\|<=>\|<>\|:\|:=\|>\|>=\|=\|==\|<\|<=\|!=\|/\|/=\|\.\.|\.\.\.\|\~=\|\~==" -" syn match groovyTokens "\*=\|&\|&=\|\*\|->\|\~\|+\|-\|/\|?\|<<<\|>>>\|<<\|>>" - -" Must put explicit these ones because groovy.vim mark them as errors otherwise -" syn match groovyTokens "<=>\|<>\|==\~" -"syn cluster groovyTop add=groovyTokens - -" Mark these as operators - -" Hightlight brackets -" syn match groovyBraces "[{}]" -" syn match groovyBraces "[\[\]]" -" syn match groovyBraces "[\|]" - -if exists("groovy_mark_braces_in_parens_as_errors") - syn match groovyInParen contained "[{}]" - GroovyHiLink groovyInParen groovyError - syn cluster groovyTop add=groovyInParen -endif - -" catch errors caused by wrong parenthesis -syn region groovyParenT transparent matchgroup=groovyParen start="(" end=")" contains=@groovyTop,groovyParenT1 -syn region groovyParenT1 transparent matchgroup=groovyParen1 start="(" end=")" contains=@groovyTop,groovyParenT2 contained -syn region groovyParenT2 transparent matchgroup=groovyParen2 start="(" end=")" contains=@groovyTop,groovyParenT contained -syn match groovyParenError ")" -GroovyHiLink groovyParenError groovyError - -" catch errors caused by wrong square parenthesis -syn region groovyParenT transparent matchgroup=groovyParen start="\[" end="\]" contains=@groovyTop,groovyParenT1 -syn region groovyParenT1 transparent matchgroup=groovyParen1 start="\[" end="\]" contains=@groovyTop,groovyParenT2 contained -syn region groovyParenT2 transparent matchgroup=groovyParen2 start="\[" end="\]" contains=@groovyTop,groovyParenT contained -syn match groovyParenError "\]" - -" ############################### -" java.vim default highlighting -if version >= 508 || !exists("did_groovy_syn_inits") - if version < 508 - let did_groovy_syn_inits = 1 - endif - GroovyHiLink groovyFuncDef Function - GroovyHiLink groovyBraces Function - GroovyHiLink groovyBranch Conditional - GroovyHiLink groovyUserLabelRef groovyUserLabel - GroovyHiLink groovyLabel Label - GroovyHiLink groovyUserLabel Label - GroovyHiLink groovyConditional Conditional - GroovyHiLink groovyRepeat Repeat - GroovyHiLink groovyExceptions Exception - GroovyHiLink groovyAssert Statement - GroovyHiLink groovyStorageClass StorageClass - GroovyHiLink groovyMethodDecl groovyStorageClass - GroovyHiLink groovyClassDecl groovyStorageClass - GroovyHiLink groovyScopeDecl groovyStorageClass - GroovyHiLink groovyBoolean Boolean - GroovyHiLink groovySpecial Special - GroovyHiLink groovySpecialError Error - GroovyHiLink groovySpecialCharError Error - GroovyHiLink groovyString String - GroovyHiLink groovyCharacter Character - GroovyHiLink groovySpecialChar SpecialChar - GroovyHiLink groovyNumber Number - GroovyHiLink groovyError Error - GroovyHiLink groovyStringError Error - GroovyHiLink groovyStatement Statement - GroovyHiLink groovyOperator Operator - GroovyHiLink groovyComment Comment - GroovyHiLink groovyDocComment Comment - GroovyHiLink groovyLineComment Comment - GroovyHiLink groovyConstant Constant - GroovyHiLink groovyTypedef Typedef - GroovyHiLink groovyTodo Todo - - GroovyHiLink groovyCommentTitle SpecialComment - GroovyHiLink groovyDocTags Special - GroovyHiLink groovyDocParam Function - GroovyHiLink groovyCommentStar groovyComment - - GroovyHiLink groovyType Type - GroovyHiLink groovyExternal Include - - GroovyHiLink htmlComment Special - GroovyHiLink htmlCommentPart Special - GroovyHiLink groovySpaceError Error - GroovyHiLink groovyJDKBuiltin Special - GroovyHiLink groovyJDKOperOverl Operator - GroovyHiLink groovyJDKMethods Function -endif - -delcommand GroovyHiLink - - -let b:current_syntax = "groovy" -if main_syntax == 'groovy' - unlet main_syntax -endif - -let b:spell_options="contained" - -" vim: ts=8 diff --git a/bundle/jade/README.markdown b/bundle/jade/README.markdown deleted file mode 100755 index 2c2222e..0000000 --- a/bundle/jade/README.markdown +++ /dev/null @@ -1,19 +0,0 @@ -# vim-jade # - -Vim syntax highlighting for Jade templates. - -Installation ------------- - -I prefer to install plugins using Tim Pope's -[pathogen.vim](https://github.com/tpope/vim-pathogen). Installation using -pathogen is quite simple. - - cd ~/.vim/bundle - git clone git://github.com/digitaltoad/vim-jade.git - -If you do not want to use pathogen. You can always install vim-jade in the -normal manner by copying each directory to your ~/.vim directory. Make sure -not to overwrite any existing directory of the same name and instead copy only -the contents of the source directory to the directory of the same name in your -~/.vim directory. diff --git a/bundle/jade/ftdetect/jade.vim b/bundle/jade/ftdetect/jade.vim deleted file mode 100755 index c21dcff..0000000 --- a/bundle/jade/ftdetect/jade.vim +++ /dev/null @@ -1,2 +0,0 @@ -" Jade -autocmd BufNewFile,BufReadPost *.jade set filetype=jade diff --git a/bundle/jade/ftplugin/jade.vim b/bundle/jade/ftplugin/jade.vim deleted file mode 100755 index 577f554..0000000 --- a/bundle/jade/ftplugin/jade.vim +++ /dev/null @@ -1,57 +0,0 @@ -" Vim filetype plugin -" Language: Jade -" Maintainer: Joshua Borton -" Credits: Tim Pope - -" Only do this when not done yet for this buffer -if exists("b:did_ftplugin") - finish -endif - -let s:save_cpo = &cpo -set cpo-=C - -setlocal iskeyword+=- - -" Define some defaults in case the included ftplugins don't set them. -let s:undo_ftplugin = "" -let s:browsefilter = "All Files (*.*)\t*.*\n" -let s:match_words = "" - -runtime! ftplugin/html.vim ftplugin/html_*.vim ftplugin/html/*.vim -unlet! b:did_ftplugin - -" Override our defaults if these were set by an included ftplugin. -if exists("b:undo_ftplugin") - let s:undo_ftplugin = b:undo_ftplugin - unlet b:undo_ftplugin -endif -if exists("b:browsefilter") - let s:browsefilter = b:browsefilter - unlet b:browsefilter -endif -if exists("b:match_words") - let s:match_words = b:match_words - unlet b:match_words -endif - -" Change the browse dialog on Win32 to show mainly Haml-related files -if has("gui_win32") - let b:browsefilter="Jade Files (*.jade)\t*.jade\n" . s:browsefilter -endif - -" Load the combined list of match_words for matchit.vim -if exists("loaded_matchit") - let b:match_words = s:match_words -endif - -setlocal comments=://-,:// commentstring=//\ %s - -setlocal suffixesadd+=.jade - -let b:undo_ftplugin = "setl cms< com< " - \ " | unlet! b:browsefilter b:match_words | " . s:undo_ftplugin - -let &cpo = s:save_cpo - -" vim:set sw=2: diff --git a/bundle/jade/indent/jade.vim b/bundle/jade/indent/jade.vim deleted file mode 100755 index 8cfa656..0000000 --- a/bundle/jade/indent/jade.vim +++ /dev/null @@ -1,70 +0,0 @@ -" Vim indent file -" Language: Jade -" Maintainer: Joshua Borton -" Credits: Tim Pope (vim-jade) -" Last Change: 2010 Sep 22 - -if exists("b:did_indent") - finish -endif - -unlet! b:did_indent -let b:did_indent = 1 - -setlocal autoindent -setlocal indentexpr=GetJadeIndent() -setlocal indentkeys=o,O,*,},],0),!^F - -" Only define the function once. -if exists("*GetJadeIndent") - finish -endif - -let s:attributes = '\%((.\{-\})\)' -let s:tag = '\([%.#][[:alnum:]_-]\+\|'.s:attributes.'\)*[<>]*' - -if !exists('g:jade_self_closing_tags') - let g:jade_self_closing_tags = 'meta|link|img|hr|br|input' -endif - -setlocal formatoptions+=r -setlocal comments+=n:\| - -function! GetJadeIndent() - let lnum = prevnonblank(v:lnum-1) - if lnum == 0 - return 0 - endif - let line = substitute(getline(lnum),'\s\+$','','') - let cline = substitute(substitute(getline(v:lnum),'\s\+$','',''),'^\s\+','','') - let lastcol = strlen(line) - let line = substitute(line,'^\s\+','','') - let indent = indent(lnum) - let cindent = indent(v:lnum) - let increase = indent + &sw - if indent == indent(lnum) - let indent = cindent <= indent ? -1 : increase - endif - - let group = synIDattr(synID(lnum,lastcol,1),'name') - - if line =~ '^!!!' - return indent - elseif line =~ '^/\%(\[[^]]*\]\)\=$' - return increase - elseif line =~ '^\%(if\|else\|unless\|for\|each\|block\|mixin\|append\|case\|when\)' - return increase - elseif line =~ '^'.s:tag.'[&!]\=[=~-].*,\s*$' - return increase - elseif line == '-#' - return increase - elseif line =~? '^\v%('.g:jade_self_closing_tags.')>' - return indent - elseif group =~? '\v^%(jadeAttributesDelimiter|jadeClass|jadeId|htmlTagName|htmlSpecialTagName|jadeFilter|jadeTagBlockChar)$' - return increase - else - return indent - endif -endfunction - -" vim:set sw=2: diff --git a/bundle/jade/syntax/jade.vim b/bundle/jade/syntax/jade.vim deleted file mode 100755 index 360c876..0000000 --- a/bundle/jade/syntax/jade.vim +++ /dev/null @@ -1,102 +0,0 @@ -" Vim syntax file -" Language: Jade -" Maintainer: Joshua Borton -" Credits: Tim Pope -" Filenames: *.jade - -if exists("b:current_syntax") - finish -endif - -if !exists("main_syntax") - let main_syntax = 'jade' -endif - -silent! syntax include @htmlCoffeescript syntax/coffee.vim -unlet! b:current_syntax -silent! syntax include @htmlStylus syntax/stylus.vim -unlet! b:current_syntax -silent! syntax include @htmlMarkdown syntax/markdown.vim -unlet! b:current_syntax - -syn case match - -syn region javascriptParenthesisBlock start="(" end=")" contains=@htmlJavascript contained keepend -syn cluster htmlJavascript add=javascriptParenthesisBlock - -syn region jadeJavascript matchgroup=jadeJavascriptOutputChar start="[!&]\==\|\~" skip=",\s*$" end="$" contained contains=@htmlJavascript keepend -syn region jadeJavascript matchgroup=jadeJavascriptChar start="-" skip=",\s*$" end="$" contained contains=@htmlJavascript keepend -syn cluster jadeTop contains=jadeBegin,jadeComment,jadeHtmlComment,jadeJavascript -syn match jadeBegin "^\s*\%([<>]\|&[^=~ ]\)\@!" nextgroup=jadeTag,jadeClassChar,jadeIdChar,jadePlainChar,jadeJavascript,jadeScriptConditional,jadeScriptStatement,jadePipedText -syn match jadeTag "+\?\w\+\%(:\w\+\)\=" contained contains=htmlTagName,htmlSpecialTagName nextgroup=@jadeComponent -syn cluster jadeComponent contains=jadeAttributes,jadeIdChar,jadeBlockExpansionChar,jadeClassChar,jadePlainChar,jadeJavascript,jadeTagBlockChar,jadeTagInlineText -syn match jadeComment '\s*\/\/.*$' -syn region jadeCommentBlock start="\z(\s*\)\/\/.*$" end="^\%(\z1\s\|\s*$\)\@!" keepend -syn region jadeHtmlConditionalComment start="" -syn region jadeAttributes matchgroup=jadeAttributesDelimiter start="(" end=")" contained contains=@htmlJavascript,jadeHtmlArg,htmlArg,htmlEvent,htmlCssDefinition nextgroup=@jadeComponent -syn match jadeClassChar "\." contained nextgroup=jadeClass -syn match jadeBlockExpansionChar ":\s\+" contained nextgroup=jadeTag -syn match jadeIdChar "#[[{]\@!" contained nextgroup=jadeId -syn match jadeClass "\%(\w\|-\)\+" contained nextgroup=@jadeComponent -syn match jadeId "\%(\w\|-\)\+" contained nextgroup=@jadeComponent -syn region jadeDocType start="^\s*\(!!!\|doctype\)" end="$" -" Unless I'm mistaken, syntax/html.vim requires -" that the = sign be present for these matches. -" This adds the matches back for jade. -syn keyword jadeHtmlArg contained href title - -syn match jadePlainChar "\\" contained -syn region jadeInterpolation matchgroup=jadeInterpolationDelimiter start="[#!]{" end="}" contains=@htmlJavascript -syn match jadeInterpolationEscape "\\\@[?!]\@!" -syn match jadeScriptStatement "^\s*\<\%(each\|for\|block\|prepend\|append\|mixin\|extends\|include\)\>[?!]\@!" -syn region jadeScriptLoopRegion start="^\s*\(for \)" end="$" contains=jadeScriptLoopKeywords -syn keyword jadeScriptLoopKeywords for in contained - -syn region jadeJavascript start="^\z(\s*\)script\%(:\w\+\)\=" end="^\%(\z1\s\|\s*$\)\@!" contains=@htmlJavascript,jadeJavascriptTag,jadeCoffeescriptFilter keepend - -syn region jadeCoffeescriptFilter matchgroup=jadeFilter start="^\z(\s*\):coffee-\?script\s*$" end="^\%(\z1\s\|\s*$\)\@!" contains=@htmlCoffeescript contained -syn region jadeJavascriptTag contained start="^\z(\s*\)script\%(:\w\+\)\=" end="$" contains=jadeBegin,jadeTag -syn region jadeCssBlock start="^\z(\s*\)style" nextgroup=@jadeComponent,jadeError end="^\%(\z1\s\|\s*$\)\@!" contains=@htmlCss keepend - -syn match jadeError "\$" contained - -hi def link jadePlainChar Special -hi def link jadeScriptConditional PreProc -hi def link jadeScriptLoopKeywords PreProc -hi def link jadeScriptStatement PreProc -hi def link jadeHtmlArg htmlArg -hi def link jadeAttributeString String -hi def link jadeAttributesDelimiter Identifier -hi def link jadeIdChar Special -hi def link jadeClassChar Special -hi def link jadeBlockExpansionChar Special -hi def link jadePipeChar Special -hi def link jadeTagBlockChar Special -hi def link jadeId Identifier -hi def link jadeClass Type -hi def link jadeInterpolationDelimiter Delimiter -hi def link jadeInlineDelimiter Delimiter -hi def link jadeFilter PreProc -hi def link jadeDocType PreProc -hi def link jadeComment Comment -hi def link jadeCommentBlock Comment -hi def link jadeHtmlConditionalComment jadeComment - -let b:current_syntax = "jade" - -if main_syntax == "jade" - unlet main_syntax -endif diff --git a/bundle/jsx/README.md b/bundle/jsx/README.md deleted file mode 100644 index 9362651..0000000 --- a/bundle/jsx/README.md +++ /dev/null @@ -1,56 +0,0 @@ -vim-jsx -======= - -Syntax highlighting and indenting for JSX. JSX is a JavaScript syntax -transformer which translates inline XML document fragments into JavaScript -objects. It was developed by Facebook alongside [React][1]. - -This bundle requires pangloss's [vim-javascript][2] syntax highlighting. - -Vim support for inline XML in JS is remarkably similar to the same for PHP, -which you can find [here][3]. - -Usage ------ - -By default, JSX syntax highlighting and indenting will be enabled only for -files with the `.jsx` extension. If you would like JSX in `.js` files, add - - let g:jsx_ext_required = 0 - -to your .vimrc or somewhere in your include path. If you wish to restrict JSX -to files with the pre-v0.12 `@jsx React.DOM` pragma, add - - let g:jsx_pragma_required = 1 - -to your .vimrc or somewhere in your include path. - -Installation ------------- - -### Pathogen - -The recommended installation method is via [Pathogen][4]. Then simply execute - - cd ~/.vim/bundle - git clone https://github.com/mxw/vim-jsx.git - -### Manual Installation - -If you have no `~/.vim/after` directory, you can download the tarball or zip -and copy the contents to `~/.vim`. - -If you have existing `~/.vim/after` files, copy the syntax and indent files -directly into their respective destinations. If you have existing after syntax -or indent files for Javascript, you'll probably want to do something like - - mkdir -p ~/.vim/after/syntax/javascript - cp path/to/vim-jsx/after/syntax/javascript.vim ~/.vim/after/syntax/javascript/javascript.vim - mkdir -p ~/.vim/after/indent/javascript - cp path/to/vim-jsx/after/indent/javascript.vim ~/.vim/after/indent/javascript/javascript.vim - - -[1]: http://facebook.github.io/react/ "React" -[2]: https://github.com/pangloss/vim-javascript "pangloss: vim-javascript" -[3]: https://github.com/mxw/vim-xhp "mxw: vim-xhp" -[4]: https://github.com/tpope/vim-pathogen "tpope: vim-pathogen" diff --git a/bundle/jsx/after/ftdetect/javascript.vim b/bundle/jsx/after/ftdetect/javascript.vim deleted file mode 100644 index 7cd1f9d..0000000 --- a/bundle/jsx/after/ftdetect/javascript.vim +++ /dev/null @@ -1,10 +0,0 @@ -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" -" Vim ftdetect file -" -" Language: JSX (JavaScript) -" Maintainer: Max Wang -" -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" - -autocmd BufNewFile,BufRead *.jsx let b:jsx_ext_found = 1 -autocmd BufNewFile,BufRead *.jsx set filetype=javascript diff --git a/bundle/jsx/after/ftplugin/javascript.vim b/bundle/jsx/after/ftplugin/javascript.vim deleted file mode 100644 index 1a8da4d..0000000 --- a/bundle/jsx/after/ftplugin/javascript.vim +++ /dev/null @@ -1,15 +0,0 @@ -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" -" Vim ftplugin file -" -" Language: JSX (JavaScript) -" Maintainer: Max Wang -" Depends: pangloss/vim-javascript -" -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" - -" modified from html.vim -if exists("loaded_matchit") - let b:match_ignorecase = 0 - let b:match_words = '(:),\[:\],{:},<:>,' . - \ '<\@<=\([^/][^ \t>]*\)[^>]*\%(>\|$\):<\@<=/\1>' -endif diff --git a/bundle/jsx/after/indent/javascript.vim b/bundle/jsx/after/indent/javascript.vim deleted file mode 100644 index d0b4d4e..0000000 --- a/bundle/jsx/after/indent/javascript.vim +++ /dev/null @@ -1,98 +0,0 @@ -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" -" Vim indent file -" -" Language: JSX (JavaScript) -" Maintainer: Max Wang -" Depends: pangloss/vim-javascript -" -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" - -" Do nothing if we don't find the @jsx pragma (and we care). -exec 'source '.fnameescape(expand(':p:h:h').'/jsx-config.vim') -if g:jsx_pragma_required && !b:jsx_pragma_found | finish | endif - -" Do nothing if we don't have the .jsx extension (and we care). -if g:jsx_ext_required && !exists('b:jsx_ext_found') | finish | endif - -" Prologue; load in XML indentation. -if exists('b:did_indent') - let s:did_indent=b:did_indent - unlet b:did_indent -endif -exe 'runtime! indent/xml.vim' -if exists('s:did_indent') - let b:did_indent=s:did_indent -endif - -setlocal indentexpr=GetJsxIndent() - -" JS indentkeys -setlocal indentkeys=0{,0},0),0],0\,,!^F,o,O,e -" XML indentkeys -setlocal indentkeys+=*,<>>,<<>,/ - -" Self-closing tag regex. -let s:sctag = '^\s*\/>\s*;\=' - -" Get all syntax types at the beginning of a given line. -fu! SynSOL(lnum) - return map(synstack(a:lnum, 1), 'synIDattr(v:val, "name")') -endfu - -" Get all syntax types at the end of a given line. -fu! SynEOL(lnum) - let lnum = prevnonblank(a:lnum) - let col = strlen(getline(lnum)) - return map(synstack(lnum, col), 'synIDattr(v:val, "name")') -endfu - -" Check if a syntax attribute is XMLish. -fu! SynAttrXMLish(synattr) - return a:synattr =~ "^xml" || a:synattr =~ "^jsx" -endfu - -" Check if a synstack is XMLish (i.e., has an XMLish last attribute). -fu! SynXMLish(syns) - return SynAttrXMLish(get(a:syns, -1)) -endfu - -" Check if a synstack has any XMLish attribute. -fu! SynXMLishAny(syns) - for synattr in a:syns - if SynAttrXMLish(synattr) - return 1 - endif - endfor - return 0 -endfu - -" Check if a synstack denotes the end of a JSX block. -fu! SynJSXBlockEnd(syns) - return get(a:syns, -1) == 'jsBraces' && SynAttrXMLish(get(a:syns, -2)) -endfu - -" Cleverly mix JS and XML indentation. -fu! GetJsxIndent() - let cursyn = SynSOL(v:lnum) - let prevsyn = SynEOL(v:lnum - 1) - - " Use XML indenting if the syntax at the end of the previous line was either - " JSX or was the closing brace of a jsBlock whose parent syntax was JSX. - if (SynXMLish(prevsyn) || SynJSXBlockEnd(prevsyn)) && SynXMLishAny(cursyn) - let ind = XmlIndentGet(v:lnum, 0) - - " Align '/>' with '<' for multiline self-closing tags. - if getline(v:lnum) =~? s:sctag - let ind = ind - &sw - endif - - " Then correct the indentation of any JSX following '/>'. - if getline(v:lnum - 1) =~? s:sctag - let ind = ind + &sw - endif - else - let ind = GetJavascriptIndent() - endif - - return ind -endfu diff --git a/bundle/jsx/after/jsx-config.vim b/bundle/jsx/after/jsx-config.vim deleted file mode 100644 index a1d4cbe..0000000 --- a/bundle/jsx/after/jsx-config.vim +++ /dev/null @@ -1,33 +0,0 @@ -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" -" Vimscript file -" -" Set up a bunch of configuration variables. -" -" Also check (if desired) whether or not the @jsx pragma is correctly included -" in '%'. Set the result in b:jsx_pragma_found. -" -" Language: JSX (JavaScript) -" Maintainer: Max Wang -" -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" - -" Only check once. -if exists('b:jsx_pragma_found') - finish -endif - -" Whether the .jsx extension is required to enable JSX syntax/indent. -if !exists('g:jsx_ext_required') - let g:jsx_ext_required = 1 -endif - -" Whether the @jsx pragma is required to enable JSX syntax/indent. -if !exists('g:jsx_pragma_required') - let g:jsx_pragma_required = 0 -endif -if !g:jsx_pragma_required | finish | endif - -" Look for the @jsx pragma. It must be included in a docblock comment before -" anything else in the file (except whitespace). -let s:jsx_pragma_pattern = '\%^\_s*\/\*\*\%(\_.\%(\*\/\)\@!\)*@jsx\_.\{-}\*\/' -let b:jsx_pragma_found = search(s:jsx_pragma_pattern, 'npw') diff --git a/bundle/jsx/after/syntax/javascript.vim b/bundle/jsx/after/syntax/javascript.vim deleted file mode 100644 index 5bebc94..0000000 --- a/bundle/jsx/after/syntax/javascript.vim +++ /dev/null @@ -1,43 +0,0 @@ -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" -" Vim syntax file -" -" Language: JSX (JavaScript) -" Maintainer: Max Wang -" Depends: pangloss/vim-javascript -" -" CREDITS: Inspired by Facebook. -" -""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""" - -" Do nothing if we don't find the @jsx pragma (and we care). -exec 'source '.fnameescape(expand(':p:h:h').'/jsx-config.vim') -if g:jsx_pragma_required && !b:jsx_pragma_found | finish | endif - -" Do nothing if we don't have the .jsx extension (and we care). -if g:jsx_ext_required && !exists('b:jsx_ext_found') | finish | endif - -" Prologue; load in XML syntax. -if exists('b:current_syntax') - let s:current_syntax=b:current_syntax - unlet b:current_syntax -endif -syn include @XMLSyntax syntax/xml.vim -if exists('s:current_syntax') - let b:current_syntax=s:current_syntax -endif - -" Highlight JSX regions as XML; recursively match. -syn region jsxRegion contains=@XMLSyntax,jsxRegion,jsBlock,jsStringD,jsStringS - \ start=+<\@+ - \ end=++ - \ end=+/>+ - \ keepend - \ extend - -" JSX attributes should color as JS. Note the trivial end pattern; we let -" jsBlock take care of ending the region. -syn region xmlString contained start=+{+ end=++ contains=jsBlock - -" Add jsxRegion to the lowest-level JS syntax cluster. -syn cluster jsExpression add=jsxRegion diff --git a/bundle/less/.gitignore b/bundle/less/.gitignore deleted file mode 100644 index 1377554..0000000 --- a/bundle/less/.gitignore +++ /dev/null @@ -1 +0,0 @@ -*.swp diff --git a/bundle/less/README.md b/bundle/less/README.md deleted file mode 100644 index 697ad12..0000000 --- a/bundle/less/README.md +++ /dev/null @@ -1,49 +0,0 @@ -# VIM-LESS - -This vim bundle adds syntax highlighting, indenting and autocompletion for the dynamic stylesheet language [LESS](http://lesscss.org). - -This bundle is compatible with [vim-css-color](https://github.com/skammer/vim-css-color), -[vim-css3-syntax](https://github.com/hail2u/vim-css3-syntax) and possibly other plugins that place code -in `after/syntax/css.vim` or `after/syntax/css/*.vim`. - -![vim-less with vim-css-color and vim-css3-syntax (colorscheme solarized)](https://github.com/lenniboy/vim-less/raw/master/screenshot.png) - - -## Installing and Using - -- Install [pathogen](http://www.vim.org/scripts/script.php?script_id=2332) into `~/.vim/autoload/` and add the - following line to your `~/.vimrc`: - - call pathogen#infect() - -- Make a clone of the `vim-less` repository: - - $ mkdir -p ~/.vim/bundle - $ cd ~/.vim/bundle - $ git clone https://github.com/groenewege/vim-less - -- OR use [vundle](https://github.com/gmarik/vundle), adding this line to your `~/.vimrc`: - - Bundle 'groenewege/vim-less' - -- OR use git submodules: - - $ git submodule add https://github.com/groenewege/vim-less.git bundle/vim-less - $ git submodule init - - -### Map -.less to .css , lessc is required. - - nnoremap ,m :w !lessc % > %:t:r.css - - -## Credits - -Inspiration from [vim-haml](https://github.com/tpope/vim-haml), -[scss-syntax.vim](https://github.com/cakebaker/scss-syntax.vim) and -[vim-less](https://github.com/lunaru/vim-less) - -## License ## - -MIT : [groenewege.mit-license.org](http://groenewege.mit-license.org/) diff --git a/bundle/less/ftdetect/less.vim b/bundle/less/ftdetect/less.vim deleted file mode 100644 index f1cb1d7..0000000 --- a/bundle/less/ftdetect/less.vim +++ /dev/null @@ -1 +0,0 @@ -autocmd BufNewFile,BufRead *.less setf less diff --git a/bundle/less/ftplugin/less.vim b/bundle/less/ftplugin/less.vim deleted file mode 100644 index b6eaf6a..0000000 --- a/bundle/less/ftplugin/less.vim +++ /dev/null @@ -1,25 +0,0 @@ -" Vim filetype plugin -" Language: LessCSS -" Author: Tim Pope -" Maintainer: Leonard Ehrenfried -" Last Change: 2011 Sep 30 - -" Only do this when not done yet for this buffer -if exists("b:did_ftplugin") - finish -endif -let b:did_ftplugin = 1 - -let b:undo_ftplugin = "setl cms< def< inc< inex< ofu< sua<" - -setlocal iskeyword+=- -setlocal commentstring=//\ %s -setlocal define=^\\s*\\%(@mixin\\\|=\\) -setlocal includeexpr=substitute(v:fname,'\\%(.*/\\\|^\\)\\zs','_','') -setlocal omnifunc=csscomplete#CompleteCSS -setlocal suffixesadd=.less -setlocal comments=s1:/*,mb:*,ex:*/ - -let &l:include = '^\s*@import\s\+\%(url(http://github.com/)\=["'']\=' - -" vim:set sw=2: diff --git a/bundle/less/indent/less.vim b/bundle/less/indent/less.vim deleted file mode 100644 index fea8846..0000000 --- a/bundle/less/indent/less.vim +++ /dev/null @@ -1,11 +0,0 @@ -" Vim indent file -" Language: LessCSS -" Maintainer: Leonard Ehrenfried -" Last Change: 2011 Sep 26 - -if exists("b:did_indent") - finish -endif - -runtime! indent/css.vim - diff --git a/bundle/less/screenshot.png b/bundle/less/screenshot.png deleted file mode 100644 index ce25624a83a2a34c2c91a0df3eaff57a86d0e815..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 52352 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 `{{_}}` - - `{{{` => `{{{_}}}` - - `{{!` => `{{!_}}` - - `{{>` => `{{>_}}` - - `{{<` => `{{<_}}` - - `{{#` produces - - ``` - {{# _}} - {{/}} - ``` - - `{{if` produces - - ``` - {{#if _}} - {{/if}} - ``` - - `{{ife` produces - - ``` - {{#if _}} - {{else}} - {{/if}} - ``` - -### Section movement mappings - -Following the vim convention of jumping from section to section, `[[` and `]]` -mappings are implemented for easier movement between mustache tags. - - - `]]` jumps to the first following tag - - `[[` jumps to the first previous tag - -Count with section movements is supported: - - - `2]]` jumps to the second next tag - -### Text objects - -Vim has a very powerful concept of "text objects". If you aren't using text objects, -you can get familiar with it on [this vim help -link](http://vimdoc.sourceforge.net/htmldoc/motion.html#text-objects). Learning -text objects really speeds up the vim workflow. - -In that spirit, this plugin defines 2 text objects: - - `ie` a mnemonic for `inside element`, selects all the text inside the - mustache tag. - For example, when used with `vie` it will visually select the - bold text in the following snippets: {{**some_variable**}}, - {{{**different_variable**}}}. - - `ae` a mnemonic for `around element`, selects the whole mustache tag, - including the curly braces. - Example, `vae` visually selects the bold text in the following - snippets: **{{some_variable}}** or **{{{another_variable}}}**. - -Here are other usage examples: - - `dae` - deletes the whole mustache tag, including the curly braces - - `die` - deletes **inside** the mustache tag, leaving only curly braces - - `yae` - "yanks" the whole mustache tag - with curly braces - - `cie` - deletes **inside** the mustache tag and goes in insert mode - -`ie` and `ae` text objects are enabled by default. To disable them, put the -following in your `.vimrc`: - - let g:mustache_operators = 0 - -## Maintainers - -* [Bruno Michel](http://github.com/nono) -* [Bruno Sutic](http://github.com/bruno-) -* [Juvenn Woo](http://github.com/juvenn) - -This is combined work from -[juvenn/mustache.vim](http://github.com/juvenn/mustache.vim) and -[nono/vim-handlebars](http://github.com/nono/vim-handlebars). - ----- - -Thanks [@5long](http://github.com/5long) for adding matchit support. - -You're encouraged to propose ideas or have discussions via github -issues. - -[mustache]: http://mustache.github.io -[handlebars]: http://handlebarsjs.com -[pathogen]: https://github.com/tpope/vim-pathogen diff --git a/bundle/mustache-handlebars/example.mustache b/bundle/mustache-handlebars/example.mustache deleted file mode 100644 index 1390231..0000000 --- a/bundle/mustache-handlebars/example.mustache +++ /dev/null @@ -1,66 +0,0 @@ - - - - - {{title}} - - {{!}} - - -
-

Mustache Showdown

- - Basic mustache {{hello}} - {{ hello}}, {{hello }} and {{ hello }} are OK - - {{d d d}} - - {{Everything will be highlighted here}} - - Mustaches highlighted in - attribute value - - {{#repo}} - This is a mustache [enumerable] section -
  • {{ name }}
  • - {{/repo}} - - Inverted sections are supported too - {{^repo}} - No repos :( - {{/repo}} - - You can {{{yield}}} here - - {{! <> this is a comment TODO:}} - - Another {{!-- comment --}}, this one is a block comment. - - {{!-- TODO: some remark -
    - Multiline {{comments}} with - {{variables}} -
    --}} - - This is a partial {{> partial1 }} - Yet another partial {{< partial2 }}, for ctemplate - - {{=<% %>=}}Sorry, customized delimiter not handled yet<%={{}}=%> - - {{#if some_helper}} - And here is an example of handlebars if... - {{else}} - ... with optional else added. Try matchit `%` command over if/else/if. - {{/if}} - - Thanks goes to {{@defunkt}} - Feedback/blames go to {{@juvenn}} - {{Frustrations}} go to /dev/null - - Multiline {{comments}} with - {{variables}} -
    - - - - diff --git a/bundle/mustache-handlebars/ftdetect/mustache.vim b/bundle/mustache-handlebars/ftdetect/mustache.vim deleted file mode 100644 index 8a6981e..0000000 --- a/bundle/mustache-handlebars/ftdetect/mustache.vim +++ /dev/null @@ -1,4 +0,0 @@ -if has("autocmd") - au BufNewFile,BufRead *.mustache,*.hogan,*.hulk,*.hjs set filetype=html.mustache syntax=mustache | runtime! ftplugin/mustache.vim ftplugin/mustache*.vim ftplugin/mustache/*.vim - au BufNewFile,BufRead *.handlebars,*.hbs set filetype=html.handlebars syntax=mustache | runtime! ftplugin/mustache.vim ftplugin/mustache*.vim ftplugin/mustache/*.vim -endif diff --git a/bundle/mustache-handlebars/ftplugin/mustache.vim b/bundle/mustache-handlebars/ftplugin/mustache.vim deleted file mode 100644 index 61b5896..0000000 --- a/bundle/mustache-handlebars/ftplugin/mustache.vim +++ /dev/null @@ -1,120 +0,0 @@ -if exists('g:loaded_mustache_handlebars') && g:loaded_mustache_handlebars - finish -endif -let g:loaded_mustache_handlebars = 1 - -let s:cpo_save = &cpo -set cpo&vim - -" Matchit support for Mustache & Handlebars -" extending HTML matchit groups -if exists("loaded_matchit") && exists("b:match_words") - let b:match_words = b:match_words - \ . ',{:},[:],(:),' - \ . '\%({{\)\@<=#\s*\%(if\|unless\)\s*.\{-}}}' - \ . ':' - \ . '\%({{\)\@<=\s*else\s*}}' - \ . ':' - \ . '\%({{\)\@<=/\s*\%(if\|unless\)\s*}},' - \ . '\%({{\)\@<=[#^]\s*\([-0-9a-zA-Z_?!/.]\+\).\{-}}}' - \ . ':' - \ . '\%({{\)\@<=/\s*\1\s*}}' -endif - -if exists("g:mustache_abbreviations") - inoremap {{{ {{{}}} - inoremap {{ {{}} - inoremap {{! {{!}} - inoremap {{< {{<}} - inoremap {{> {{>}} - inoremap {{# {{#}}{{/}} - inoremap {{if {{#if }}{{/if}} - inoremap {{ife {{#if }}{{else}}{{/if}} -endif - - -" Section movement -" Adapted from vim-ruby - many thanks to the maintainers of that plugin - -function! s:sectionmovement(pattern,flags,mode,count) - norm! m' - if a:mode ==# 'v' - norm! gv - endif - let i = 0 - while i < a:count - let i = i + 1 - " saving current position - let line = line('.') - let col = col('.') - let pos = search(a:pattern,'W'.a:flags) - " if there's no more matches, return to last position - if pos == 0 - call cursor(line,col) - return - endif - endwhile -endfunction - -nnoremap [[ :call sectionmovement('{{','b','n',v:count1) -nnoremap ]] :call sectionmovement('{{','' ,'n',v:count1) -xnoremap [[ :call sectionmovement('{{','b','v',v:count1) -xnoremap ]] :call sectionmovement('{{','' ,'v',v:count1) - - -" Operator pending mappings - -" Operators are available by default. Set `let g:mustache_operators = 0` in -" your .vimrc to disable them. -if ! exists("g:mustache_operators") - let g:mustache_operators = 1 -endif - -if exists("g:mustache_operators") && g:mustache_operators - onoremap ie :call wrap_inside() - onoremap ae :call wrap_around() - xnoremap ie :call wrap_inside() - xnoremap ae :call wrap_around() -endif - -function! s:wrap_around() - " If the cursor is at the end of the tag element, move back - " so that the end tag can be detected. - while getline('.')[col('.')-1] ==# '}' - execute 'norm h' - endwhile - - " Moves to the end of the closing tag - let pos = search('}}','We') - if pos != 0 - if getline('.')[col('.')] ==# '}' - " Ending tag contains 3 closing brackets '}}}', - " move to the last bracket. - execute 'norm l' - endif - - " select the whole tag - execute 'norm v%' - endif -endfunction - -function! s:wrap_inside() - " If the cursor is at the end of the tag element, move back - " so that the end tag can be detected. - while getline('.')[col('.')-1] ==# '}' - execute 'norm h' - endwhile - - " Moves to the end of the closing tag - let pos = search('}}','W') - if pos != 0 - " select only inside the tag - execute 'norm v%loho' - endif -endfunction - - -let &cpo = s:cpo_save -unlet s:cpo_save - -" vim: nofoldenable diff --git a/bundle/mustache-handlebars/indent/handlebars.vim b/bundle/mustache-handlebars/indent/handlebars.vim deleted file mode 100644 index 74b0c45..0000000 --- a/bundle/mustache-handlebars/indent/handlebars.vim +++ /dev/null @@ -1,100 +0,0 @@ -" Mustache & Handlebars syntax -" Language: Mustache, Handlebars -" Maintainer: Juvenn Woo -" Screenshot: http://imgur.com/6F408 -" Version: 2 -" Last Change: Oct 10th 2015 -" Remarks: based on eruby indent plugin by tpope -" References: -" [Mustache](http://github.com/defunkt/mustache) -" [Handlebars](https://github.com/wycats/handlebars.js) -" [ctemplate](http://code.google.com/p/google-ctemplate/) -" [ctemplate doc](http://google-ctemplate.googlecode.com/svn/trunk/doc/howto.html) -" [et](http://www.ivan.fomichev.name/2008/05/erlang-template-engine-prototype.html) - -if exists("b:did_indent_hbs") - finish -endif - -unlet! b:did_indent -setlocal indentexpr= - -runtime! indent/html.vim -unlet! b:did_indent - -" Force HTML indent to not keep state. -let b:html_indent_usestate = 0 - -if &l:indentexpr == '' - if &l:cindent - let &l:indentexpr = 'cindent(v:lnum)' - else - let &l:indentexpr = 'indent(prevnonblank(v:lnum-1))' - endif -endif -let b:handlebars_subtype_indentexpr = &l:indentexpr - -let b:did_indent = 1 -let b:did_indent_hbs = 1 - -setlocal indentexpr=GetHandlebarsIndent() -setlocal indentkeys=o,O,*,<>>,{,},0),0],o,O,!^F,=end,=else,=elsif,=rescue,=ensure,=when - -" Only define the function once. -if exists("*GetHandlebarsIndent") - finish -endif - -function! GetHandlebarsIndent(...) - " The value of a single shift-width - if exists('*shiftwidth') - let sw = shiftwidth() - else - let sw = &sw - endif - - if a:0 && a:1 == '.' - let v:lnum = line('.') - elseif a:0 && a:1 =~ '^\d' - let v:lnum = a:1 - endif - let vcol = col('.') - call cursor(v:lnum,1) - call cursor(v:lnum,vcol) - exe "let ind = ".b:handlebars_subtype_indentexpr - - " Workaround for Andy Wokula's HTML indent. This should be removed after - " some time, since the newest version is fixed in a different way. - if b:handlebars_subtype_indentexpr =~# '^HtmlIndent(' - \ && exists('b:indent') - \ && type(b:indent) == type({}) - \ && has_key(b:indent, 'lnum') - " Force HTML indent to not keep state - let b:indent.lnum = -1 - endif - let lnum = prevnonblank(v:lnum-1) - let line = getline(lnum) - let cline = getline(v:lnum) - - " all indent rules only apply if the block opening/closing - " tag is on a separate line - - " indent after block {{#block - if line =~# '\v\s*\{\{\#.*\s*' - let ind = ind + sw - endif - " unindent after block close {{/block}} - if cline =~# '\v^\s*\{\{\/\S*\}\}\s*' - let ind = ind - sw - endif - " unindent {{else}} - if cline =~# '\v^\s*\{\{else.*\}\}\s*$' - let ind = ind - sw - endif - " indent again after {{else}} - if line =~# '\v^\s*\{\{else.*\}\}\s*$' - let ind = ind + sw - endif - - return ind -endfunction diff --git a/bundle/mustache-handlebars/syntax/mustache.vim b/bundle/mustache-handlebars/syntax/mustache.vim deleted file mode 100644 index ec7d4fe..0000000 --- a/bundle/mustache-handlebars/syntax/mustache.vim +++ /dev/null @@ -1,89 +0,0 @@ -" Mustache & Handlebars syntax -" Language: Mustache, Handlebars -" Maintainer: Juvenn Woo -" Screenshot: http://imgur.com/6F408 -" Version: 2 -" Last Change: Oct 26th 2013 -" Remark: -" It lexically hilights embedded mustaches (exclusively) in html file. -" While it was written for Ruby-based Mustache template system, it should -" work for Google's C-based *ctemplate* as well as Erlang-based *et*. All -" of them are, AFAIK, based on the idea of ctemplate. -" References: -" [Mustache](http://github.com/defunkt/mustache) -" [Handlebars](https://github.com/wycats/handlebars.js) -" [ctemplate](http://code.google.com/p/google-ctemplate/) -" [ctemplate doc](http://google-ctemplate.googlecode.com/svn/trunk/doc/howto.html) -" [et](http://www.ivan.fomichev.name/2008/05/erlang-template-engine-prototype.html) -" TODO: Feedback is welcomed. - - -" Read the HTML syntax to start with -if version < 600 - so :p:h/html.vim -else - runtime! syntax/html.vim - unlet b:current_syntax -endif - -if version < 600 - syntax clear -elseif exists("b:current_syntax") - finish -endif - -" Standard HiLink will not work with included syntax files -if version < 508 - command! -nargs=+ HtmlHiLink hi link -else - command! -nargs=+ HtmlHiLink hi def link -endif - -syntax match mustacheError '}}}\?' -syntax match mustacheInsideError '{{[{$#<>=!\/]\?' -syntax region mustacheInside start=/{{/ end=/}}}\?/ keepend containedin=TOP,@htmlMustacheContainer -syntax match mustacheOperators '=\|\.\|/' contained containedin=mustacheInside,@htmlMustacheContainer -syntax region mustacheSection start='{{[$#^/]'lc=2 end=/}}/me=e-2 contained containedin=mustacheInside,@htmlMustacheContainer -syntax region mustachePartial start=/{{[<>]/lc=2 end=/}}/me=e-2 contained containedin=mustacheInside,@htmlMustacheContainer -syntax region mustacheMarkerSet start=/{{=/lc=2 end=/=}}/me=e-2 contained containedin=mustacheInside,@htmlMustacheContainer -syntax match mustacheHandlebars '{{\|}}' contained containedin=mustacheInside,@htmlMustacheContainer -syntax match mustacheUnescape '{{{\|}}}' contained containedin=mustacheInside,@htmlMustacheContainer -syntax match mustacheConditionals '\([/#]\(if\|unless\)\|else\)' contained containedin=mustacheInside -syntax match mustacheHelpers '[/#]\(with\|each\)' contained containedin=mustacheSection -syntax region mustacheComment start=/{{!/rs=s+2 skip=/{{.\{-}}}/ end=/}}/re=e-2 contains=Todo contained containedin=mustacheInside,@htmlMustacheContainer -syntax region mustacheBlockComment start=/{{!--/rs=s+2 skip=/{{.\{-}}}/ end=/--}}/re=e-2 contains=Todo contained extend containedin=mustacheInside,@htmlMustacheContainer -syntax region mustacheQString start=/'/ skip=/\\'/ end=/'/ contained containedin=mustacheInside -syntax region mustacheDQString start=/"/ skip=/\\"/ end=/"/ contained containedin=mustacheInside - -" Clustering -syntax cluster htmlMustacheContainer add=htmlHead,htmlTitle,htmlString,htmlH1,htmlH2,htmlH3,htmlH4,htmlH5,htmlH6,htmlLink,htmlBold,htmlUnderline,htmlItalic,htmlValue - - -" Hilighting -" mustacheInside hilighted as Number, which is rarely used in html -" you might like change it to Function or Identifier -HtmlHiLink mustacheVariable Number -HtmlHiLink mustacheVariableUnescape Number -HtmlHiLink mustachePartial Number -HtmlHiLink mustacheSection Number -HtmlHiLink mustacheMarkerSet Number - -HtmlHiLink mustacheComment Comment -HtmlHiLink mustacheBlockComment Comment -HtmlHiLink mustacheError Error -HtmlHiLink mustacheInsideError Error - -HtmlHiLink mustacheHandlebars Special -HtmlHiLink mustacheUnescape Identifier -HtmlHiLink mustacheOperators Operator -HtmlHiLink mustacheConditionals Conditional -HtmlHiLink mustacheHelpers Repeat -HtmlHiLink mustacheQString String -HtmlHiLink mustacheDQString String - -syn region mustacheScriptTemplate start=++me=s-1 keepend -\ contains=mustacheInside,@htmlMustacheContainer,htmlTag,htmlEndTag,htmlTagName,htmlSpecialChar - -let b:current_syntax = "mustache" -delcommand HtmlHiLink diff --git a/bundle/puppet/README.md b/bundle/puppet/README.md deleted file mode 100755 index bec8ffc..0000000 --- a/bundle/puppet/README.md +++ /dev/null @@ -1,38 +0,0 @@ -vim-puppet -========== - -Make vim more Puppet friendly! - -Provides --------- - - * Formatting based on the latest Puppetlabs Style Guide - * Syntax highlighting - * Automatic => alignment (when the [tabular](https://github.com/godlygeek/tabular) plugin is also installed) - * If you don't like that, add `let g:puppet_align_hashes = 0` to your vimrc. - * Doesn't require a bloated JRE - * Doesn't take minutes to open - -Additional useful plugins -------------------------- - - * [syntastic](https://github.com/scrooloose/syntastic) plugin for automatic - syntax checking while in vim. - * [vim-snippets](https://github.com/honza/vim-snippets) is a library of - snippets for multiple languages, including Puppet. Works with both - [snipmate](https://github.com/garbas/vim-snipmate) and - [ultisnips](https://github.com/SirVer/ultisnips). - -Installation ------------- - -If you're using [pathogen](https://github.com/tpope/vim-pathogen) to manage your vim modules (and if you're not, why -aren't you), you can simply add this as a submodule in your `~/.vim/bundle/` -directory. - -My entire home directory is a git repository, so for me it's simply a case of - - $ git submodule add -f git://github.com/rodjek/vim-puppet.git .vim/bundle/puppet - -If you're not using pathogen, you can just manually place the files in the -appropriate places under `~/.vim/` diff --git a/bundle/puppet/after/ftplugin/puppet.vim b/bundle/puppet/after/ftplugin/puppet.vim deleted file mode 100755 index f976a45..0000000 --- a/bundle/puppet/after/ftplugin/puppet.vim +++ /dev/null @@ -1,16 +0,0 @@ -if !exists('g:puppet_align_hashes') - let g:puppet_align_hashes = 1 -endif - -if g:puppet_align_hashes && exists(':Tabularize') - inoremap > >:call puppetalign()a - function! s:puppetalign() - let p = '^\s*\w+\s*[=+]>.*$' - let column = strlen(substitute(getline('.')[0:col('.')],'\([^=]\|=[^>]\)','','g')) - let position = strlen(matchstr(getline('.')[0:col('.')],'.*=>\s*\zs.*')) - Tabularize /=>/l1 - normal! 0 - echo repeat('\([^=]\|=[^>]\)*=>',column).'\s\{-\}'.repeat('.',position) - call search(repeat('\([^=]\|=[^>]\)*=>',column).'\s\{-\}'.repeat('.',position),'ce',line('.')) - endfunction -endif diff --git a/bundle/puppet/ftdetect/puppet.vim b/bundle/puppet/ftdetect/puppet.vim deleted file mode 100755 index dc87505..0000000 --- a/bundle/puppet/ftdetect/puppet.vim +++ /dev/null @@ -1,2 +0,0 @@ -au! BufRead,BufNewFile *.pp setfiletype puppet -au! BufRead,BufNewFile Puppetfile setfiletype ruby diff --git a/bundle/puppet/ftplugin/puppet.vim b/bundle/puppet/ftplugin/puppet.vim deleted file mode 100755 index 175ac12..0000000 --- a/bundle/puppet/ftplugin/puppet.vim +++ /dev/null @@ -1,6 +0,0 @@ -setl ts=2 -setl sts=2 -setl sw=2 -setl et -setl keywordprg=puppet\ describe\ --providers -setl iskeyword=-,:,@,48-57,_,192-255 diff --git a/bundle/puppet/indent/puppet.vim b/bundle/puppet/indent/puppet.vim deleted file mode 100755 index cf49de8..0000000 --- a/bundle/puppet/indent/puppet.vim +++ /dev/null @@ -1,94 +0,0 @@ -" Vim indent file -" Language: Puppet -" Maintainer: Todd Zullinger -" Last Change: 2009 Aug 19 -" vim: set sw=4 sts=4: - -if exists("b:did_indent") - finish -endif -let b:did_indent = 1 - -setlocal autoindent smartindent -setlocal indentexpr=GetPuppetIndent() -setlocal indentkeys+=0],0) - -if exists("*GetPuppetIndent") - finish -endif - -" Check if a line is part of an include 'block', e.g.: -" include foo, -" bar, -" baz -function! s:PartOfInclude(lnum) - let lnum = a:lnum - while lnum - let lnum = lnum - 1 - let line = getline(lnum) - if line !~ ',$' - break - endif - if line =~ '^\s*include\s\+[^,]\+,$' - return 1 - endif - endwhile - return 0 -endfunction - -function! s:OpenBrace(lnum) - call cursor(a:lnum, 1) - return searchpair('{\|\[\|(', '', '}\|\]\|)', 'nbW') -endfunction - -function! GetPuppetIndent() - let pnum = prevnonblank(v:lnum - 1) - if pnum == 0 - return 0 - endif - - let line = getline(v:lnum) - let pline = getline(pnum) - let ind = indent(pnum) - - if pline =~ '^\s*#' - return ind - endif - - if pline =~ '\({\|\[\|(\|:\)$' - let ind += &sw - elseif pline =~ ';$' && pline !~ '[^:]\+:.*[=+]>.*' - let ind -= &sw - elseif pline =~ '^\s*include\s\+.*,$' - let ind += &sw - endif - - if pline !~ ',$' && s:PartOfInclude(pnum) - let ind -= &sw - endif - - " Match } }, }; ] ]: ], ]; ) - if line =~ '^\s*\(}\(,\|;\)\?$\|]:\|],\|}]\|];\?$\|)\)' - let ind = indent(s:OpenBrace(v:lnum)) - endif - - " Don't actually shift over for } else { - if line =~ '^\s*}\s*els\(e\|if\).*{\s*$' - let ind -= &sw - endif - - " Don't indent resources that are one after another with a ->(ordering arrow) - " file {'somefile': - " ... - " } -> - " - " package { 'mycoolpackage': - " ... - " } - if line =~ '->$' - let ind -= &sw - endif - - - return ind -endfunction diff --git a/bundle/puppet/syntax/puppet.vim b/bundle/puppet/syntax/puppet.vim deleted file mode 100755 index a979aca..0000000 --- a/bundle/puppet/syntax/puppet.vim +++ /dev/null @@ -1,166 +0,0 @@ -" puppet syntax file -" Filename: puppet.vim -" Language: puppet configuration file -" Maintainer: Luke Kanies -" URL: -" Last Change: -" Version: -" - -" Copied from the cfengine, ruby, and perl syntax files -" For version 5.x: Clear all syntax items -" For version 6.x: Quit when a syntax file was already loaded -if version < 600 - syntax clear -elseif exists("b:current_syntax") - finish -endif - -" match class/definition/node declarations -syn region puppetDefine start="^\s*\(class\|define\|node\)\s" end="{" contains=puppetDefType,puppetDefName,puppetDefArguments,puppetNodeRe,@NoSpell -syn keyword puppetDefType class define node inherits contained -syn region puppetDefArguments start="(" end=")" contained contains=puppetArgument,puppetString,puppetComment,puppetMultilineComment -syn match puppetArgument "\w\+" contained -syn match puppetArgument "\$\w\+" contained -syn match puppetArgument "'[^']+'" contained -syn match puppetArgument '"[^"]+"' contained -syn match puppetDefName "\w\+" contained -syn match puppetNodeRe "/.*/" contained - -" match 'foo' in 'class foo { ...' -" match 'foo::bar' in 'class foo::bar { ...' -" match 'Foo::Bar' in 'Foo::Bar["..."] -"FIXME: "Foo-bar" doesn't get highlighted as expected, although "foo-bar" does. -syn match puppetInstance "[A-Za-z0-9_-]\+\(::[A-Za-z0-9_-]\+\)*\s*{" contains=puppetTypeName,puppetTypeDefault,@NoSpell -syn match puppetInstance "[A-Z][a-z_-]\+\(::[A-Z][a-z_-]\+\)*\s*[[{]" contains=puppetTypeName,puppetTypeDefault,@NoSpell -syn match puppetInstance "[A-Z][a-z_-]\+\(::[A-Z][a-z_-]\+\)*\s*<\?<|" contains=puppetTypeName,puppetTypeDefault,@NoSpell -syn match puppetTypeName "[a-z]\w*" contained -syn match puppetTypeDefault "[A-Z]\w*" contained - -syn match puppetParam "\w\+\s*\(=\|+\)>" contains=puppetTypeRArrow,puppetParamName -syn match puppetParamRArrow "\(=\|+\)>" contained -syn match puppetParamName "\w\+" contained contains=@NoSpell -syn match puppetVariable "$\(\(\(::\)\?\w\+\)\+\|{\(\(::\)\?\w\+\)\+}\)" -syn match puppetParen "(" -syn match puppetParen ")" -syn match puppetBrace "{" -syn match puppetBrace "}" -syn match puppetBrack "\[" -syn match puppetBrack "\]" -syn match puppetBrack "<|" -syn match puppetBrack "|>" - -" match 'present' in 'ensure => present' -" match '2755' in 'mode => 2755' -" don't match 'bar' in 'foo => bar' -syn match puppetParam "\w\+\s*[=+]>\s*[a-z0-9]\+" contains=puppetParamString,puppetParamName -syn match puppetParamString "[=+]>\s*\w\+" contains=puppetParamKeyword,puppetParamSpecial,puppetParamDigits contained -syn keyword puppetParamKeyword present absent purged latest installed running stopped mounted unmounted role configured file directory link contained -syn keyword puppetParamSpecial true false undef contained -syn match puppetParamDigits "[0-9]\+" - -" match 'template' in 'content => template("...")' -syn match puppetParam "\w\+\s*[=+]>\s*\w\+\s*(" contains=puppetFunction,puppetParamName -" statements -syn region puppetFunction start="^\s*\(alert\|crit\|debug\|emerg\|err\|fail\|include\|info\|notice\|realize\|require\|search\|tag\|warning\)\s*(" end=")" contained contains=puppetString -" rvalues -syn region puppetFunction start="^\s*\(defined\|file\|fqdn_rand\|generate\|inline_template\|regsubst\|sha1\|shellquote\|split\|sprintf\|tagged\|template\|versioncmp\)\s*(" end=")" contained contains=puppetString - -syn match puppetVariable "$[a-zA-Z0-9_:]\+" contains=@NoSpell -syn match puppetVariable "${[a-zA-Z0-9_:]\+}" contains=@NoSpell - -" match anything between simple/double quotes. -" don't match variables if preceded by a backslash. -syn region puppetString start=+'+ skip=+\\\\\|\\'+ end=+'+ -syn region puppetString start=+"+ skip=+\\\\\|\\"+ end=+"+ contains=puppetVariable,puppetNotVariable -syn match puppetNotVariable "\\$\w\+" contained -syn match puppetNotVariable "\\${\w\+}" contained - -syn keyword puppetKeyword import inherits include require contains -syn keyword puppetControl case default if else elsif -syn keyword puppetSpecial true false undef - -syn match puppetClass "[A-Za-z0-9_-]\+\(::[A-Za-z0-9_-]\+\)\+" contains=@NoSpell - -" Match the Regular Expression type -" XXX: Puppet does not currently support a few features available in the -" full Ruby Regexp class, namely, interpolation, lookbehind and named -" sub-expressions. Matches for these features are included in the -" commented-out versions of puppetRegexParen and puppetRegexSubName, -" plus the supporting groups puppetRegexAngBrack and puppetRegexTick. -syn region puppetRegex start="/" skip="\\/" end="/" contains=puppetRegexParen,puppetRegexBrace,puppetRegexOrpuppetRegexBrack,puppetRegexComment -syn match puppetRegexParen "(\(?\([imx]\{0,4}:\|[=!]\)\)\?" contains=puppetRegexSpecChar,puppetRegexSubName contained -"syn match puppetRegexParen "(\(?\([imxo]\{0,4}:\|['<][[:alnum:]]\+[>']\|" contained -"syn match puppetRegexTick +'+ contained -syn match puppetRegexOr "|" contained -"syn match puppetRegexSubName "['<][[:alnum:]]\+[>']" contains=puppetRegexAngBrack,puppetRegexTick contained -syn match puppetRegexSpecialChar "[?:imx]\|\(= 508 || !exists("did_puppet_syn_inits") - if version < 508 - let did_puppet_syn_inits = 1 - command -nargs=+ HiLink hi link - else - command -nargs=+ HiLink hi def link - endif - - HiLink puppetVariable Identifier - HiLink puppetType Identifier - HiLink puppetKeyword Keyword - HiLink puppetComment Comment - HiLink puppetMultilineComment Comment - HiLink puppetString String - HiLink puppetRegex Constant - HiLink puppetRegexParen Delimiter - HiLink puppetRegexBrace Delimiter - HiLink puppetRegexBrack Delimiter - HiLink puppetRegexAngBrack Delimiter - HiLink puppetRegexTick Delimiter - HiLink puppetRegexOr Delimiter - HiLink puppetRegexSubName Identifier - HiLink puppetRegexSpecChar SpecialChar - HiLink puppetRegexComment Comment - HiLink puppetParamKeyword Keyword - HiLink puppetParamDigits String - HiLink puppetNotVariable String - HiLink puppetParamSpecial Boolean - HiLink puppetSpecial Special - HiLink puppetTodo Todo - HiLink puppetBrack Delimiter - HiLink puppetTypeBrack Delimiter - HiLink puppetBrace Delimiter - HiLink puppetTypeBrace Delimiter - HiLink puppetParen Delimiter - HiLink puppetDelimiter Delimiter - HiLink puppetControl Statement - HiLink puppetDefType Define - HiLink puppetDefName Type - HiLink puppetNodeRe Type - HiLink puppetTypeName Statement - HiLink puppetTypeDefault Type - HiLink puppetParamName Identifier - HiLink puppetArgument Identifier - HiLink puppetFunction Function - HiLink puppetClass Include - - delcommand HiLink -endif - -let b:current_syntax = "puppet" diff --git a/bundle/scala/.gitignore b/bundle/scala/.gitignore deleted file mode 100644 index 01716d2..0000000 --- a/bundle/scala/.gitignore +++ /dev/null @@ -1,6 +0,0 @@ -# Ignore Vim tag files -tags - -# Ignore Vim swap files -.*.swp -.*.swo diff --git a/bundle/scala/.travis.yml b/bundle/scala/.travis.yml deleted file mode 100644 index c1ac6c5..0000000 --- a/bundle/scala/.travis.yml +++ /dev/null @@ -1,11 +0,0 @@ -language: ruby -rvm: - - 1.9.3 -before_install: sudo apt-get install vim-gtk -before_script: - - "export DISPLAY=:99.0" - - "sh -e /etc/init.d/xvfb start" -notifications: - email: - on_success: never - on_failure: change diff --git a/bundle/scala/Gemfile b/bundle/scala/Gemfile deleted file mode 100644 index 414fd03..0000000 --- a/bundle/scala/Gemfile +++ /dev/null @@ -1,5 +0,0 @@ -source 'https://rubygems.org/' -gem 'vimrunner', '0.3.0' -gem 'rake', '10.0.4' -gem 'rspec', '~> 2.13.0' - diff --git a/bundle/scala/Gemfile.lock b/bundle/scala/Gemfile.lock deleted file mode 100644 index ea5528e..0000000 --- a/bundle/scala/Gemfile.lock +++ /dev/null @@ -1,20 +0,0 @@ -GEM - remote: https://rubygems.org/ - specs: - diff-lcs (1.1.3) - rake (0.9.2.2) - rspec (2.9.0) - rspec-core (~> 2.9.0) - rspec-expectations (~> 2.9.0) - rspec-mocks (~> 2.9.0) - rspec-core (2.9.0) - rspec-expectations (2.9.1) - diff-lcs (~> 1.1.3) - rspec-mocks (2.9.0) - -PLATFORMS - ruby - -DEPENDENCIES - rake - rspec diff --git a/bundle/scala/LICENSE.TXT b/bundle/scala/LICENSE.TXT deleted file mode 100644 index 66b0c46..0000000 --- a/bundle/scala/LICENSE.TXT +++ /dev/null @@ -1,201 +0,0 @@ - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - -TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - -1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - -2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - -3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - -4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - -5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - -6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - -7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - -8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - -9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - -END OF TERMS AND CONDITIONS - -APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "{}" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - -Copyright {yyyy} {name of copyright owner} - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. diff --git a/bundle/scala/README.md b/bundle/scala/README.md deleted file mode 100644 index c786a1c..0000000 --- a/bundle/scala/README.md +++ /dev/null @@ -1,36 +0,0 @@ -vim-scala [![Build Status](https://secure.travis-ci.org/lenniboy/vim-scala.png)](http://travis-ci.org/lenniboy/vim-scala) -========== - -This is a "bundle" for Vim that builds off of the initial Scala plugin modules -by Stefan Matthias Aust and adds some more "stuff" that I find useful, including -all of my notes and customizations. - -##Installation - -You really should be using Tim Pope's [Pathogen](https://github.com/tpope/vim-pathogen) module for Vim (http://tammersaleh.com/posts/the-modern-vim-config-with-pathogen) if you're going to clone this repository because, well... you should. - -###Vundle -Alternatively, you can use [Vundle](https://github.com/gmarik/vundle) to -manage your plugins. - -If you have Vundle installed, simply add the following to your .vimrc: - -```vim -Bundle 'derekwyatt/vim-scala' -``` - -and then run - -```vim -:BundleInstall -``` - -to install it. - -##Sorting of import statements - :SortScalaImports - -There are different modes for import sorting available. For details, please -consult the vimdoc help with - - :help :SortScalaImports diff --git a/bundle/scala/Rakefile b/bundle/scala/Rakefile deleted file mode 100644 index 7c84562..0000000 --- a/bundle/scala/Rakefile +++ /dev/null @@ -1,6 +0,0 @@ -require 'rspec/core/rake_task' - -RSpec::Core::RakeTask.new - -task :test => :spec -task :default => :spec diff --git a/bundle/scala/after/plugin/help.vim b/bundle/scala/after/plugin/help.vim deleted file mode 100644 index 785160a..0000000 --- a/bundle/scala/after/plugin/help.vim +++ /dev/null @@ -1,50 +0,0 @@ - -function! FixTOCLine(beginning, colonCol) - let l = strlen(a:beginning) - let c = 0 - let dots = "" - while c < (a:colonCol - l) - let dots = dots . "." - let c += 1 - endwhile - return (a:beginning . dots . ":") -endfunction - -function! BuildTOC() - let lnum = getpos(".")[1] - call append(lnum - 1, "<<<") - call append(lnum, ">>>") - :g/^\d\+\./co/>>>/- - :g/^<<>>/s/ {{{\d\s*// - :g/^<<>>/s/\*/|/g - :g/^<<>>/s/^\ze\d\.\d\+\./ / - :g/^<<>>/s/^\ze\d\d\.\d\+\./ / - :g/^<<>>/s/^\ze\d\.\d\+/ / - :g/^<<>>/s/^\ze\d\d\.\d\+/ / - :g/^<<>>/s/^\ze\d\./ / - :g/^<<>>/s/^\ze\d\d\./ / - :g/^\s\+0\. Content/d - :g/<<>>/-s/^\(.\{-}\)\(\s\+\)\ze |/\=FixTOCLine(submatch(1), 45)/ - :g/<<>>/d -endfunction - -command! BuildNewTableOfContents silent! call BuildTOC() - -function! JustifyCurrentLine() - let cline = getline('.') - let matches = matchlist(cline, '^\(.*\)\s\+\(\*.*\)$') - let st = matches[1] - let fin = matches[2] - let spcnum = 78 - strlen(st) - strlen(fin) - let c = 0 - let spcs = "" - while c < spcnum - let spcs = spcs . " " - let c = c + 1 - endwhile - let newline = st . spcs . fin - :norm dd - let lnum = getpos('.')[1] - call append(lnum - 1, newline) -endfunction diff --git a/bundle/scala/after/syntax/help.vim b/bundle/scala/after/syntax/help.vim deleted file mode 100644 index b352a1e..0000000 --- a/bundle/scala/after/syntax/help.vim +++ /dev/null @@ -1,8 +0,0 @@ -let b:current_syntax = '' -unlet b:current_syntax -syntax include @ScalaCode syntax/scala.vim -if has('conceal') - syntax region rgnScala matchgroup=Ignore concealends start='!sc!' end='!/sc!' contains=@ScalaCode -else - syntax region rgnScala matchgroup=Ignore start='!sc!' end='!/sc!' contains=@ScalaCode -endif diff --git a/bundle/scala/doc/scala.txt b/bundle/scala/doc/scala.txt deleted file mode 100644 index d3277b4..0000000 --- a/bundle/scala/doc/scala.txt +++ /dev/null @@ -1,44 +0,0 @@ -*scala.txt* Syntax highlighting and helper functions for the Scala language. - -INTRODUCTION *scala* - -Syntax highlighting and helper functions for the scala language. - -COMMANDS *scala-commands* - - *:SortScalaImports* -:SortScalaImports There are two modes in which this command can operate. - By default it walks all import groups at the top of - the Scala file and orders their lines alphabetically. - A group is a series of lines starting with the - import keyword separated by one or more blank lines. - - The second, more advanced mode, can be activated by - setting - - let g:scala_sort_across_groups=1 - - This makes this command include all imports in the - sorting regardless of blank lines in between them and - puts them in three predefined groups instead. - The three groups in which the imports can fall are: - - 1. Scala and Java core - 2. Third party libraries - 3. First party code (ie. your own) - - Java and Scala core imports are identified by the - java(x) and scala namespaces. - Everything else that isn't a first party namespace - will be a third party import. - You can define a regex that matches first party - namespaces by setting - - g:scala_first_party_namespaces - - For example in a standard Play app this would be - set to - g:scala_first_party_namespaces= - \ '\(controllers\|views\|models\)' - - diff --git a/bundle/scala/ftdetect/scala.vim b/bundle/scala/ftdetect/scala.vim deleted file mode 100644 index 997a701..0000000 --- a/bundle/scala/ftdetect/scala.vim +++ /dev/null @@ -1,8 +0,0 @@ -fun! s:DetectScala() - if getline(1) == '#!/usr/bin/env scala' - set filetype=scala - endif -endfun - -au BufRead,BufNewFile *.scala,*.sbt set filetype=scala -au BufRead,BufNewFile * call s:DetectScala() diff --git a/bundle/scala/ftplugin/scala.vim b/bundle/scala/ftplugin/scala.vim deleted file mode 100644 index 3f0de96..0000000 --- a/bundle/scala/ftplugin/scala.vim +++ /dev/null @@ -1,195 +0,0 @@ -setlocal formatoptions+=ro -setlocal commentstring=//%s -let &l:include = '^\s*import' -let &l:includeexpr = 'substitute(v:fname,"\\.","/","g")' -setlocal path+=src/main/scala,src/test/scala -setlocal suffixesadd=.scala - -set makeprg=sbt\ -Dsbt.log.noformat=true\ compile -set efm=%E\ %#[error]\ %f:%l:\ %m,%C\ %#[error]\ %p^,%-C%.%#,%Z, - \%W\ %#[warn]\ %f:%l:\ %m,%C\ %#[warn]\ %p^,%-C%.%#,%Z, - \%-G%.%# - -if globpath(&rtp, 'plugin/fuf.vim') != '' - " - " FuzzyFinder stuff - " - " - " SanitizeDirForFuzzyFinder() - " - " This is really just a convenience function to clean up any stray '/' - " characters in the path, should they be there. - " - function! scala#SanitizeDirForFuzzyFinder(dir) - let dir = expand(a:dir) - let dir = substitute(dir, '/\+$', '', '') - let dir = substitute(dir, '/\+', '/', '') - - return dir - endfunction - - " - " GetDirForFuzzyFinder() - " - " Given a directory to start 'from', walk up the hierarchy, looking for a path - " that matches the 'addon' you want to see. - " - " If nothing can be found, then we just return the 'from' so we don't really get - " the advantage of a hint, but just let the user start from wherever he was - " starting from anyway. - " - function! scala#GetDirForFuzzyFinder(from, addon) - let from = scala#SanitizeDirForFuzzyFinder(a:from) - let addon = expand(a:addon) - let addon = substitute(addon, '^/\+', '', '') - let found = '' - " If the addon is right here, then we win - if isdirectory(from . '/' . addon) - let found = from . '/' . addon - else - let dirs = split(from, '/') - if !has('win32') && !has('win64') - let dirs[0] = '/' . dirs[0] - endif - " Walk up the tree and see if it's anywhere there - for n in range(len(dirs) - 1, 0, -1) - let path = join(dirs[0:n], '/') - if isdirectory(path . '/' . addon) - let found = path . '/' . addon - break - endif - endfor - endif - " If we found it, then let's see if we can go deeper - " - " For example, we may have found component_name/include - " but what if that directory only has a single directory - " in it, and that subdirectory only has a single directory - " in it, etc... ? This can happen when you're segmenting - " by namespace like this: - " - " component_name/include/org/vim/CoolClass.h - " - " You may find yourself always typing '' from the - " 'include' directory just to go into 'org/vim' so let's - " just eliminate the need to hit the ''. - if found != '' - let tempfrom = found - let globbed = globpath(tempfrom, '*') - while len(split(globbed, "\n")) == 1 - let tempfrom = globbed - let globbed = globpath(tempfrom, '*') - endwhile - let found = scala#SanitizeDirForFuzzyFinder(tempfrom) . '/' - else - let found = from - endif - - return found - endfunction - - " - " GetTestDirForFuzzyFinder() - " - " Now overload GetDirForFuzzyFinder() specifically for the test directory (I'm - " really only interested in going down into test/src 90% of the time, so let's - " hit that 90% and leave the other 10% to couple of extra keystrokes) - " - function! scala#GetTestDirForFuzzyFinder(from) - return scala#GetDirForFuzzyFinder(a:from, 'src/test/scala/') - endfunction - - " - " GetMainDirForFuzzyFinder() - " - " Now overload GetDirForFuzzyFinder() specifically for the main directory. - " - function! scala#GetMainDirForFuzzyFinder(from) - return scala#GetDirForFuzzyFinder(a:from, 'src/main/scala/') - endfunction - - " - " GetRootDirForFuzzyFinder() - " - " Now overload GetDirForFuzzyFinder() specifically for the root directory. - " - function! scala#GetRootDirForFuzzyFinder(from) - return scala#GetDirForFuzzyFinder(a:from, 'src/../') - endfunction - - " If you want to disable the default key mappings, write the following line in - " your ~/.vimrc - " let g:scala_use_default_keymappings = 0 - if get(g:, 'scala_use_default_keymappings', 1) - nnoremap ft :FufFile =scala#GetTestDirForFuzzyFinder('%:p:h') - nnoremap fs :FufFile =scala#GetMainDirForFuzzyFinder('%:p:h') - nnoremap fr :FufFile =scala#GetRootDirForFuzzyFinder('%:p:h') - endif -endif - -" If you want to disable the default key mappings, write the following line in -" your ~/.vimrc -" let g:scala_use_default_keymappings = 0 -if get(g:, 'scala_use_default_keymappings', 1) - nnoremap jt :call JustifyCurrentLine() -endif - -" -" TagBar -" -let g:tagbar_type_scala = { - \ 'ctagstype' : 'scala', - \ 'kinds' : [ - \ 'p:packages:1', - \ 'V:values', - \ 'v:variables', - \ 'T:types', - \ 't:traits', - \ 'o:objects', - \ 'a:aclasses', - \ 'c:classes', - \ 'r:cclasses', - \ 'm:methods' - \ ], - \ 'sro' : '.', - \ 'kind2scope' : { - \ 'T' : 'type', - \ 't' : 'trait', - \ 'o' : 'object', - \ 'a' : 'abstract class', - \ 'c' : 'class', - \ 'r' : 'case class' - \ }, - \ 'scope2kind' : { - \ 'type' : 'T', - \ 'trait' : 't', - \ 'object' : 'o', - \ 'abstract class' : 'a', - \ 'class' : 'c', - \ 'case class' : 'r' - \ } -\ } - -function! s:CreateOrExpression(keywords) - return '('.join(a:keywords, '|').')' -endfunction - -function! s:NextSection(backwards) - if a:backwards - let dir = '?' - else - let dir = '/' - endif - let keywords = [ 'def', 'class', 'trait', 'object' ] - let keywordsOrExpression = s:CreateOrExpression(keywords) - - let modifiers = [ 'public', 'private', 'private\[\w*\]', 'protected', 'abstract', 'case', 'override', 'implicit', 'final', 'sealed'] - let modifierOrExpression = s:CreateOrExpression(modifiers) - - let regex = '^ *('.modifierOrExpression.' )* *'.keywordsOrExpression."\r" - execute 'silent normal! ' . dir . '\v'.regex -endfunction - -noremap