mirror of
https://github.com/amix/vimrc
synced 2025-06-23 06:35:01 +08:00
Updated plugins
This commit is contained in:
@ -1,6 +1,6 @@
|
||||
## vim-gitgutter
|
||||
|
||||
A Vim plugin which shows a git diff in the 'gutter' (sign column). It shows which lines have been added, modified, or removed. You can also preview, stage, and undo individual hunks. The plugin also provides a hunk text object.
|
||||
A Vim plugin which shows a git diff in the 'gutter' (sign column). It shows which lines have been added, modified, or removed. You can also preview, stage, and undo individual hunks; and stage partial hunks. The plugin also provides a hunk text object.
|
||||
|
||||
The signs are always up to date and the plugin never saves your buffer.
|
||||
|
||||
@ -12,10 +12,13 @@ Features:
|
||||
* Never saves the buffer.
|
||||
* Quick jumping between blocks of changed lines ("hunks").
|
||||
* Stage/undo/preview individual hunks.
|
||||
* Previews highlight intra-line changes.
|
||||
* Stage partial hunks.
|
||||
* Provides a hunk text object.
|
||||
* Diffs against index (default) or any commit.
|
||||
* Allows folding all unchanged text.
|
||||
* Provides fold text showing whether folded lines have been changed.
|
||||
* Can load all hunk locations into quickfix list.
|
||||
* Handles line endings correctly, even with repos that do CRLF conversion.
|
||||
* Optional line highlighting.
|
||||
* Optional line number highlighting. (Only available in Neovim 0.3.2 or higher)
|
||||
@ -33,77 +36,38 @@ Constraints:
|
||||
|
||||
### Screenshot
|
||||
|
||||

|
||||

|
||||
|
||||
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.
|
||||
* Lines 183-184 are new.
|
||||
* Lines 186-187 have been modified.
|
||||
* The preview for the modified lines highlights changed regions within the line.
|
||||
|
||||
|
||||
### 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.
|
||||
Install using your favourite package manager, or use Vim's built-in package support.
|
||||
|
||||
You install vim-gitgutter like any other vim plugin.
|
||||
|
||||
##### Pathogen
|
||||
Vim:
|
||||
|
||||
```
|
||||
cd ~/.vim/bundle
|
||||
git clone git://github.com/airblade/vim-gitgutter.git
|
||||
mkdir -p ~/.vim/pack/airblade/start
|
||||
cd ~/.vim/pack/airblade/start
|
||||
git clone https://github.com/airblade/vim-gitgutter.git
|
||||
vim -u NONE -c "helptags vim-gitgutter/doc" -c q
|
||||
```
|
||||
|
||||
##### Voom
|
||||
Neovim:
|
||||
|
||||
Edit your plugin manifest (`voom edit`) and add:
|
||||
|
||||
```
|
||||
airblade/vim-gitgutter
|
||||
mkdir -p ~/.config/nvim/pack/airblade/start
|
||||
cd ~/.config/nvim/pack/airblade/start
|
||||
git clone https://github.com/airblade/vim-gitgutter.git
|
||||
nvim -u NONE -c "helptags vim-gitgutter/doc" -c q
|
||||
```
|
||||
|
||||
##### 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`.
|
||||
|
||||
|
||||
### Windows
|
||||
|
||||
@ -179,10 +143,12 @@ Both of those take a preceding count.
|
||||
To set your own mappings for these, for example `]h` and `[h`:
|
||||
|
||||
```viml
|
||||
nmap ]h <Plug>GitGutterNextHunk
|
||||
nmap [h <Plug>GitGutterPrevHunk
|
||||
nmap ]h <Plug>(GitGutterNextHunk)
|
||||
nmap [h <Plug>(GitGutterPrevHunk)
|
||||
```
|
||||
|
||||
You can load all your hunks into the quickfix list with `:GitGutterQuickFix`. Note this ignores any unsaved changes in your buffers.
|
||||
|
||||
You can stage or undo an individual hunk when your cursor is in it:
|
||||
|
||||
* stage the hunk with `<Leader>hs` or
|
||||
@ -200,21 +166,23 @@ To stage part of any hunk:
|
||||
* delete the lines you do not want to stage;
|
||||
* stage the remaining lines: either write (`:w`) the window or stage via `<Leader>hs` or `:GitGutterStageHunk`.
|
||||
|
||||
Note the above workflow is not possible if you have opted in to preview hunks with Vim's popup windows.
|
||||
|
||||
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:
|
||||
To set your own mappings for these, for example if you prefer `g`-based maps:
|
||||
|
||||
```viml
|
||||
nmap <Leader>ha <Plug>GitGutterStageHunk
|
||||
nmap <Leader>hr <Plug>GitGutterUndoHunk
|
||||
nmap ghs <Plug>(GitGutterStageHunk)
|
||||
nmap ghu <Plug>(GitGutterUndoHunk)
|
||||
```
|
||||
|
||||
And you can preview a hunk's changes with `<Leader>hp`. The location of the preview window is configured with `g:gitgutter_preview_win_location` (default `'bo'`). You can of course change this mapping, e.g:
|
||||
|
||||
```viml
|
||||
nmap <Leader>hv <Plug>GitGutterPreviewHunk
|
||||
nmap ghp <Plug>(GitGutterPreviewHunk)
|
||||
```
|
||||
|
||||
A hunk text object is provided which works in visual and operator-pending modes.
|
||||
@ -225,10 +193,10 @@ A hunk text object is provided which works in visual and operator-pending modes.
|
||||
To re-map these, for example to `ih` and `ah`:
|
||||
|
||||
```viml
|
||||
omap ih <Plug>GitGutterTextObjectInnerPending
|
||||
omap ah <Plug>GitGutterTextObjectOuterPending
|
||||
xmap ih <Plug>GitGutterTextObjectInnerVisual
|
||||
xmap ah <Plug>GitGutterTextObjectOuterVisual
|
||||
omap ih <Plug>(GitGutterTextObjectInnerPending)
|
||||
omap ah <Plug>(GitGutterTextObjectOuterPending)
|
||||
xmap ih <Plug>(GitGutterTextObjectInnerVisual)
|
||||
xmap ah <Plug>(GitGutterTextObjectOuterVisual)
|
||||
```
|
||||
|
||||
If you don't want vim-gitgutter to set up any mappings at all, use this:
|
||||
@ -248,6 +216,21 @@ Use the `GitGutterFold` command to fold all unchanged lines, leaving just the hu
|
||||
|
||||
Execute `GitGutterFold` a second time to restore the previous view.
|
||||
|
||||
Use `gitgutter#fold#foldtext()` to augment the default `foldtext()` with an indicator of whether the folded lines have been changed.
|
||||
|
||||
```viml
|
||||
set foldtext=gitgutter#fold#foldtext()
|
||||
```
|
||||
|
||||
For a closed fold with changed lines:
|
||||
|
||||
```
|
||||
Default foldtext(): +-- 45 lines: abcdef
|
||||
gitgutter#fold#foldtext(): +-- 45 lines (*): abcdef
|
||||
```
|
||||
|
||||
You can use `gitgutter#fold#is_changed()` in your own `foldtext` expression to find out whether the folded lines have been changed.
|
||||
|
||||
|
||||
### Customisation
|
||||
|
||||
@ -258,6 +241,7 @@ You can customise:
|
||||
* How to handle non-gitgutter signs
|
||||
* The signs' colours and symbols
|
||||
* Line highlights
|
||||
* Whether the diff is relative to the index (default) or working tree.
|
||||
* The base of the diff
|
||||
* Extra arguments for `git` when running `git diff`
|
||||
* Extra arguments for `git diff`
|
||||
@ -269,6 +253,7 @@ You can customise:
|
||||
* Whether vim-gitgutter runs asynchronously (defaults to yes)
|
||||
* Whether to clobber or preserve non-gitgutter signs
|
||||
* The priority of gitgutter's signs.
|
||||
* Whether to use a floating/popup window for hunk previews
|
||||
|
||||
Please note that vim-gitgutter won't override any colours or highlights you've set in your colorscheme.
|
||||
|
||||
@ -380,6 +365,15 @@ highlight link GitGutterChangeLineNr Underlined
|
||||
```
|
||||
|
||||
|
||||
#### Whether the diff is relative to the index or working tree
|
||||
|
||||
By default diffs are relative to the index. How you can make them relative to the working tree:
|
||||
|
||||
```viml
|
||||
let g:gitgutter_diff_relative_to = 'working_tree'
|
||||
```
|
||||
|
||||
|
||||
#### The base of the diff
|
||||
|
||||
By default buffers are diffed against the index. However you can diff against any commit by setting:
|
||||
@ -388,6 +382,8 @@ By default buffers are diffed against the index. However you can diff against a
|
||||
let g:gitgutter_diff_base = '<commit SHA>'
|
||||
```
|
||||
|
||||
This setting is ignored when the diffs are relative to the working tree.
|
||||
|
||||
|
||||
#### Extra arguments for `git` when running `git diff`
|
||||
|
||||
@ -454,6 +450,11 @@ let g:gitgutter_async = 0
|
||||
```
|
||||
|
||||
|
||||
#### To use floating/popup windows for hunk previews
|
||||
|
||||
Add `let g:gitgutter_preview_win_floating = 1` to your vimrc. Note that on Vim this prevents you staging (partial) hunks via the preview window.
|
||||
|
||||
|
||||
### Extensions
|
||||
|
||||
#### Operate on every line in a hunk
|
||||
@ -514,7 +515,9 @@ Let's say, for example, you want to remove trailing whitespace from all changed
|
||||
|
||||
#### Cycle through hunks in all buffers
|
||||
|
||||
`]c` and `[c` jump from one hunk to the next in the current buffer. You can use this code to jump to the next hunk no matter which buffer it's in.
|
||||
You can use `:GitGutterQuickFix` to load all hunks into the quickfix list.
|
||||
|
||||
Alternatively, given that`]c` and `[c` jump from one hunk to the next in the current buffer, you can use this code to jump to the next hunk no matter which buffer it's in.
|
||||
|
||||
```viml
|
||||
function! NextHunkAllBuffers()
|
||||
@ -585,12 +588,22 @@ autocmd BufWritePost * GitGutter
|
||||
|
||||
> Why can't I unstage staged changes?
|
||||
|
||||
This plugin is for showing changes between the working tree and the index (and staging/undoing those changes). Unstaging a staged hunk would require showing changes between the index and HEAD, which is out of scope.
|
||||
This plugin is for showing changes between the buffer and the index (and staging/undoing those changes). Unstaging a staged hunk would require showing changes between the index and HEAD, which is out of scope.
|
||||
|
||||
> 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.
|
||||
|
||||
> Why are the colours in the preview window weird?
|
||||
|
||||
Probably because your colourscheme doesn't configure the `diff{Added,Changed,Removed}` highlight groups. Try this in `after/syntax/diff.vim`:
|
||||
|
||||
```viml
|
||||
highlight link diffAdded DiffAdd
|
||||
highlight link diffChanged DiffChange
|
||||
highlight link diffRemoved DiffDelete
|
||||
```
|
||||
|
||||
> What happens if I also use another plugin which uses signs (e.g. Syntastic)?
|
||||
|
||||
You can configure whether GitGutter preserves or clobbers other signs using `g:gitgutter_sign_allow_clobber`. Set to `1` to clobber other signs (default on Vim >= 8.1.0614 and NeoVim >= 0.4.0) or `0` to preserve them.
|
||||
|
@ -39,7 +39,7 @@ function! gitgutter#process_buffer(bufnr, force) abort
|
||||
|
||||
let diff = ''
|
||||
try
|
||||
let diff = gitgutter#diff#run_diff(a:bufnr, 'index', 0)
|
||||
let diff = gitgutter#diff#run_diff(a:bufnr, g:gitgutter_diff_relative_to, 0)
|
||||
catch /gitgutter not tracked/
|
||||
call gitgutter#debug#log('Not tracked: '.gitgutter#utility#file(a:bufnr))
|
||||
catch /gitgutter diff failed/
|
||||
@ -119,37 +119,37 @@ function! gitgutter#setup_maps()
|
||||
return
|
||||
endif
|
||||
|
||||
if !hasmapto('<Plug>GitGutterPrevHunk') && maparg('[c', 'n') ==# ''
|
||||
nmap <buffer> [c <Plug>GitGutterPrevHunk
|
||||
if !hasmapto('<Plug>(GitGutterPrevHunk)') && maparg('[c', 'n') ==# ''
|
||||
nmap <buffer> [c <Plug>(GitGutterPrevHunk)
|
||||
endif
|
||||
if !hasmapto('<Plug>GitGutterNextHunk') && maparg(']c', 'n') ==# ''
|
||||
nmap <buffer> ]c <Plug>GitGutterNextHunk
|
||||
if !hasmapto('<Plug>(GitGutterNextHunk)') && maparg(']c', 'n') ==# ''
|
||||
nmap <buffer> ]c <Plug>(GitGutterNextHunk)
|
||||
endif
|
||||
|
||||
if !hasmapto('<Plug>GitGutterStageHunk', 'v') && maparg('<Leader>hs', 'x') ==# ''
|
||||
xmap <buffer> <Leader>hs <Plug>GitGutterStageHunk
|
||||
if !hasmapto('<Plug>(GitGutterStageHunk)', 'v') && maparg('<Leader>hs', 'x') ==# ''
|
||||
xmap <buffer> <Leader>hs <Plug>(GitGutterStageHunk)
|
||||
endif
|
||||
if !hasmapto('<Plug>GitGutterStageHunk', 'n') && maparg('<Leader>hs', 'n') ==# ''
|
||||
nmap <buffer> <Leader>hs <Plug>GitGutterStageHunk
|
||||
if !hasmapto('<Plug>(GitGutterStageHunk)', 'n') && maparg('<Leader>hs', 'n') ==# ''
|
||||
nmap <buffer> <Leader>hs <Plug>(GitGutterStageHunk)
|
||||
endif
|
||||
if !hasmapto('<Plug>GitGutterUndoHunk') && maparg('<Leader>hu', 'n') ==# ''
|
||||
nmap <buffer> <Leader>hu <Plug>GitGutterUndoHunk
|
||||
if !hasmapto('<Plug>(GitGutterUndoHunk)') && maparg('<Leader>hu', 'n') ==# ''
|
||||
nmap <buffer> <Leader>hu <Plug>(GitGutterUndoHunk)
|
||||
endif
|
||||
if !hasmapto('<Plug>GitGutterPreviewHunk') && maparg('<Leader>hp', 'n') ==# ''
|
||||
nmap <buffer> <Leader>hp <Plug>GitGutterPreviewHunk
|
||||
if !hasmapto('<Plug>(GitGutterPreviewHunk)') && maparg('<Leader>hp', 'n') ==# ''
|
||||
nmap <buffer> <Leader>hp <Plug>(GitGutterPreviewHunk)
|
||||
endif
|
||||
|
||||
if !hasmapto('<Plug>GitGutterTextObjectInnerPending') && maparg('ic', 'o') ==# ''
|
||||
omap <buffer> ic <Plug>GitGutterTextObjectInnerPending
|
||||
if !hasmapto('<Plug>(GitGutterTextObjectInnerPending)') && maparg('ic', 'o') ==# ''
|
||||
omap <buffer> ic <Plug>(GitGutterTextObjectInnerPending)
|
||||
endif
|
||||
if !hasmapto('<Plug>GitGutterTextObjectOuterPending') && maparg('ac', 'o') ==# ''
|
||||
omap <buffer> ac <Plug>GitGutterTextObjectOuterPending
|
||||
if !hasmapto('<Plug>(GitGutterTextObjectOuterPending)') && maparg('ac', 'o') ==# ''
|
||||
omap <buffer> ac <Plug>(GitGutterTextObjectOuterPending)
|
||||
endif
|
||||
if !hasmapto('<Plug>GitGutterTextObjectInnerVisual') && maparg('ic', 'x') ==# ''
|
||||
xmap <buffer> ic <Plug>GitGutterTextObjectInnerVisual
|
||||
if !hasmapto('<Plug>(GitGutterTextObjectInnerVisual)') && maparg('ic', 'x') ==# ''
|
||||
xmap <buffer> ic <Plug>(GitGutterTextObjectInnerVisual)
|
||||
endif
|
||||
if !hasmapto('<Plug>GitGutterTextObjectOuterVisual') && maparg('ac', 'x') ==# ''
|
||||
xmap <buffer> ac <Plug>GitGutterTextObjectOuterVisual
|
||||
if !hasmapto('<Plug>(GitGutterTextObjectOuterVisual)') && maparg('ac', 'x') ==# ''
|
||||
xmap <buffer> ac <Plug>(GitGutterTextObjectOuterVisual)
|
||||
endif
|
||||
|
||||
call gitgutter#utility#setbufvar(bufnr, 'mapped', 1)
|
||||
@ -179,3 +179,33 @@ function! s:clear(bufnr)
|
||||
call s:reset_tick(a:bufnr)
|
||||
call gitgutter#utility#setbufvar(a:bufnr, 'path', '')
|
||||
endfunction
|
||||
|
||||
|
||||
" Note:
|
||||
" - this runs synchronously
|
||||
" - it ignores unsaved changes in buffers
|
||||
" - it does not change to the repo root
|
||||
function! gitgutter#quickfix()
|
||||
let locations = []
|
||||
let cmd = g:gitgutter_git_executable.' '.g:gitgutter_git_args.' --no-pager '.g:gitgutter_git_args.
|
||||
\ ' diff --no-ext-diff --no-color -U0 '.g:gitgutter_diff_args
|
||||
let diff = systemlist(cmd)
|
||||
let lnum = 0
|
||||
for line in diff
|
||||
if line =~ '^diff --git [^"]'
|
||||
let paths = line[11:]
|
||||
let mid = (len(paths) - 1) / 2
|
||||
let [fnamel, fnamer] = [paths[:mid-1], paths[mid+1:]]
|
||||
let fname = fnamel ==# fnamer ? fnamel : fnamel[2:]
|
||||
elseif line =~ '^diff --git "'
|
||||
let [_, fnamel, _, fnamer] = split(line, '"')
|
||||
let fname = fnamel ==# fnamer ? fnamel : fnamel[2:]
|
||||
elseif line =~ '^@@'
|
||||
let lnum = matchlist(line, '+\(\d\+\)')[1]
|
||||
elseif lnum > 0
|
||||
call add(locations, {'filename': fname, 'lnum': lnum, 'text': line})
|
||||
let lnum = 0
|
||||
endif
|
||||
endfor
|
||||
call setqflist(locations)
|
||||
endfunction
|
||||
|
@ -187,7 +187,7 @@ function! gitgutter#diff#handler(bufnr, diff) abort
|
||||
call gitgutter#sign#clear_signs(a:bufnr)
|
||||
|
||||
else
|
||||
if g:gitgutter_signs || g:gitgutter_highlight_lines
|
||||
if g:gitgutter_signs || g:gitgutter_highlight_lines || g:gitgutter_highlight_linenrs
|
||||
call gitgutter#sign#update_signs(a:bufnr, modified_lines)
|
||||
endif
|
||||
endif
|
||||
@ -385,6 +385,10 @@ function! s:write_buffer(bufnr, file)
|
||||
call map(bufcontents, 'v:val."\r"')
|
||||
endif
|
||||
|
||||
if getbufvar(a:bufnr, '&endofline')
|
||||
call add(bufcontents, '')
|
||||
endif
|
||||
|
||||
let fenc = getbufvar(a:bufnr, '&fileencoding')
|
||||
if fenc !=# &encoding
|
||||
call map(bufcontents, 'iconv(v:val, &encoding, "'.fenc.'")')
|
||||
@ -394,7 +398,7 @@ function! s:write_buffer(bufnr, file)
|
||||
let bufcontents[0]=''.bufcontents[0]
|
||||
endif
|
||||
|
||||
call writefile(bufcontents, a:file)
|
||||
call writefile(bufcontents, a:file, 'b')
|
||||
endfunction
|
||||
|
||||
|
||||
|
@ -0,0 +1,225 @@
|
||||
" This is the minimum number of characters required between regions of change
|
||||
" in a line. It's somewhat arbitrary: higher values mean less visual busyness;
|
||||
" lower values mean more detail.
|
||||
let s:gap_between_regions = 5
|
||||
|
||||
|
||||
" Calculates the changed portions of lines.
|
||||
"
|
||||
" Based on:
|
||||
"
|
||||
" - diff-highlight (included with git)
|
||||
" https://github.com/git/git/blob/master/contrib/diff-highlight/DiffHighlight.pm
|
||||
"
|
||||
" - Diff Strategies, Neil Fraser
|
||||
" https://neil.fraser.name/writing/diff/
|
||||
|
||||
|
||||
" Returns a list of intra-line changed regions.
|
||||
" Each element is a list:
|
||||
"
|
||||
" [
|
||||
" line number (1-based),
|
||||
" type ('+' or '-'),
|
||||
" start column (1-based, inclusive),
|
||||
" stop column (1-based, inclusive),
|
||||
" ]
|
||||
"
|
||||
" Args:
|
||||
" hunk_body - list of lines
|
||||
function! gitgutter#diff_highlight#process(hunk_body)
|
||||
" Check whether we have the same number of lines added as removed.
|
||||
let [removed, added] = [0, 0]
|
||||
for line in a:hunk_body
|
||||
if line[0] == '-'
|
||||
let removed += 1
|
||||
elseif line[0] == '+'
|
||||
let added += 1
|
||||
endif
|
||||
endfor
|
||||
if removed != added
|
||||
return []
|
||||
endif
|
||||
|
||||
let regions = []
|
||||
|
||||
for i in range(removed)
|
||||
" pair lines by position
|
||||
let rline = a:hunk_body[i]
|
||||
let aline = a:hunk_body[i + removed]
|
||||
|
||||
call s:diff(rline, aline, i, i+removed, 0, 0, regions, 1)
|
||||
endfor
|
||||
|
||||
return regions
|
||||
endfunction
|
||||
|
||||
|
||||
function! s:diff(rline, aline, rlinenr, alinenr, rprefix, aprefix, regions, whole_line)
|
||||
" diff marker does not count as a difference in prefix
|
||||
let start = a:whole_line ? 1 : 0
|
||||
let prefix = s:common_prefix(a:rline[start:], a:aline[start:])
|
||||
if a:whole_line
|
||||
let prefix += 1
|
||||
endif
|
||||
let [rsuffix, asuffix] = s:common_suffix(a:rline, a:aline, prefix+1)
|
||||
|
||||
" region of change (common prefix and suffix removed)
|
||||
let rtext = a:rline[prefix+1:rsuffix-1]
|
||||
let atext = a:aline[prefix+1:asuffix-1]
|
||||
|
||||
" singular insertion
|
||||
if empty(rtext)
|
||||
if !a:whole_line || len(atext) != len(a:aline) " not whole line
|
||||
call add(a:regions, [a:alinenr+1, '+', a:aprefix+prefix+1+1, a:aprefix+asuffix+1-1])
|
||||
endif
|
||||
return
|
||||
endif
|
||||
|
||||
" singular deletion
|
||||
if empty(atext)
|
||||
if !a:whole_line || len(rtext) != len(a:rline) " not whole line
|
||||
call add(a:regions, [a:rlinenr+1, '-', a:rprefix+prefix+1+1, a:rprefix+rsuffix+1-1])
|
||||
endif
|
||||
return
|
||||
endif
|
||||
|
||||
" two insertions
|
||||
let j = stridx(atext, rtext)
|
||||
if j != -1
|
||||
call add(a:regions, [a:alinenr+1, '+', a:aprefix+prefix+1+1, a:aprefix+prefix+j+1])
|
||||
call add(a:regions, [a:alinenr+1, '+', a:aprefix+prefix+1+1+j+len(rtext), a:aprefix+asuffix+1-1])
|
||||
return
|
||||
endif
|
||||
|
||||
" two deletions
|
||||
let j = stridx(rtext, atext)
|
||||
if j != -1
|
||||
call add(a:regions, [a:rlinenr+1, '-', a:rprefix+prefix+1+1, a:rprefix+prefix+j+1])
|
||||
call add(a:regions, [a:rlinenr+1, '-', a:rprefix+prefix+1+1+j+len(atext), a:rprefix+rsuffix+1-1])
|
||||
return
|
||||
endif
|
||||
|
||||
" two edits
|
||||
let lcs = s:lcs(rtext, atext)
|
||||
" TODO do we need to ensure we don't get more than 2 elements when splitting?
|
||||
if len(lcs) > s:gap_between_regions
|
||||
let redits = s:split(rtext, lcs)
|
||||
let aedits = s:split(atext, lcs)
|
||||
call s:diff(redits[0], aedits[0], a:rlinenr, a:alinenr, a:rprefix+prefix+1, a:aprefix+prefix+1, a:regions, 0)
|
||||
call s:diff(redits[1], aedits[1], a:rlinenr, a:alinenr, a:rprefix+prefix+1+len(redits[0])+len(lcs), a:aprefix+prefix+1+len(aedits[0])+len(lcs), a:regions, 0)
|
||||
return
|
||||
endif
|
||||
|
||||
" fall back to highlighting entire changed area
|
||||
|
||||
" if a change (but not the whole line)
|
||||
if !a:whole_line || ((prefix != 0 || rsuffix != len(a:rline)) && prefix+1 < rsuffix)
|
||||
call add(a:regions, [a:rlinenr+1, '-', a:rprefix+prefix+1+1, a:rprefix+rsuffix+1-1])
|
||||
endif
|
||||
|
||||
" if a change (but not the whole line)
|
||||
if !a:whole_line || ((prefix != 0 || asuffix != len(a:aline)) && prefix+1 < asuffix)
|
||||
call add(a:regions, [a:alinenr+1, '+', a:aprefix+prefix+1+1, a:aprefix+asuffix+1-1])
|
||||
endif
|
||||
endfunction
|
||||
|
||||
|
||||
function! s:lcs(s1, s2)
|
||||
if empty(a:s1) || empty(a:s2)
|
||||
return ''
|
||||
endif
|
||||
|
||||
let matrix = map(repeat([repeat([0], len(a:s2)+1)], len(a:s1)+1), 'copy(v:val)')
|
||||
|
||||
let maxlength = 0
|
||||
let endindex = len(a:s1)
|
||||
|
||||
for i in range(1, len(a:s1))
|
||||
for j in range(1, len(a:s2))
|
||||
if a:s1[i-1] ==# a:s2[j-1]
|
||||
let matrix[i][j] = 1 + matrix[i-1][j-1]
|
||||
if matrix[i][j] > maxlength
|
||||
let maxlength = matrix[i][j]
|
||||
let endindex = i - 1
|
||||
endif
|
||||
endif
|
||||
endfor
|
||||
endfor
|
||||
|
||||
return a:s1[endindex - maxlength + 1 : endindex]
|
||||
endfunction
|
||||
|
||||
if $VIM_GITGUTTER_TEST
|
||||
function! gitgutter#diff_highlight#lcs(s1, s2)
|
||||
return s:lcs(a:s1, a:s2)
|
||||
endfunction
|
||||
endif
|
||||
|
||||
|
||||
" Returns 0-based index of last character of common prefix
|
||||
" If there is no common prefix, returns -1.
|
||||
"
|
||||
" a, b - strings
|
||||
"
|
||||
function! s:common_prefix(a, b)
|
||||
let len = min([len(a:a), len(a:b)])
|
||||
if len == 0
|
||||
return -1
|
||||
endif
|
||||
for i in range(len)
|
||||
if a:a[i:i] != a:b[i:i]
|
||||
return i - 1
|
||||
endif
|
||||
endfor
|
||||
return i
|
||||
endfunction
|
||||
|
||||
if $VIM_GITGUTTER_TEST
|
||||
function! gitgutter#diff_highlight#common_prefix(a, b)
|
||||
return s:common_prefix(a:a, a:b)
|
||||
endfunction
|
||||
endif
|
||||
|
||||
|
||||
" Returns 0-based indices of start of common suffix
|
||||
"
|
||||
" a, b - strings
|
||||
" start - 0-based index to start from
|
||||
function! s:common_suffix(a, b, start)
|
||||
let [sa, sb] = [len(a:a), len(a:b)]
|
||||
while sa >= a:start && sb >= a:start
|
||||
if a:a[sa] ==# a:b[sb]
|
||||
let sa -= 1
|
||||
let sb -= 1
|
||||
else
|
||||
break
|
||||
endif
|
||||
endwhile
|
||||
return [sa+1, sb+1]
|
||||
endfunction
|
||||
|
||||
if $VIM_GITGUTTER_TEST
|
||||
function! gitgutter#diff_highlight#common_suffix(a, b, start)
|
||||
return s:common_suffix(a:a, a:b, a:start)
|
||||
endfunction
|
||||
endif
|
||||
|
||||
|
||||
" Split a string on another string.
|
||||
" Assumes 1 occurrence of the delimiter.
|
||||
function! s:split(str, delimiter)
|
||||
let i = stridx(a:str, a:delimiter)
|
||||
|
||||
if i == 0
|
||||
return ['', a:str[len(a:delimiter):]]
|
||||
endif
|
||||
|
||||
return [a:str[:i-1], a:str[i+len(a:delimiter):]]
|
||||
endfunction
|
||||
|
||||
if $VIM_GITGUTTER_TEST
|
||||
function! gitgutter#diff_highlight#split(str, delimiter)
|
||||
return s:split(a:str, a:delimiter)
|
||||
endfunction
|
||||
endif
|
@ -31,6 +31,37 @@ function! gitgutter#fold#level(lnum)
|
||||
endfunction
|
||||
|
||||
|
||||
function! gitgutter#fold#foldtext()
|
||||
if !gitgutter#fold#is_changed()
|
||||
return foldtext()
|
||||
endif
|
||||
|
||||
return substitute(foldtext(), ':', ' (*):', '')
|
||||
endfunction
|
||||
|
||||
|
||||
" Returns 1 if any of the folded lines have been changed
|
||||
" (added, removed, or modified), 0 otherwise.
|
||||
function! gitgutter#fold#is_changed()
|
||||
for hunk in gitgutter#hunk#hunks(bufnr(''))
|
||||
let hunk_begin = hunk[2]
|
||||
let hunk_end = hunk[2] + (hunk[3] == 0 ? 1 : hunk[3])
|
||||
|
||||
if hunk_end < v:foldstart
|
||||
continue
|
||||
endif
|
||||
|
||||
if hunk_begin > v:foldend
|
||||
break
|
||||
endif
|
||||
|
||||
return 1
|
||||
endfor
|
||||
|
||||
return 0
|
||||
endfunction
|
||||
|
||||
|
||||
" A line in a hunk has a fold level of 0.
|
||||
" A line within 3 lines of a hunk has a fold level of 1.
|
||||
" All other lines have a fold level of 2.
|
||||
|
@ -30,6 +30,7 @@ function! gitgutter#highlight#line_toggle() abort
|
||||
endif
|
||||
endfunction
|
||||
|
||||
|
||||
function! gitgutter#highlight#linenr_disable() abort
|
||||
let g:gitgutter_highlight_linenrs = 0
|
||||
call s:define_sign_linenr_highlights()
|
||||
@ -42,12 +43,12 @@ function! gitgutter#highlight#linenr_disable() abort
|
||||
endfunction
|
||||
|
||||
function! gitgutter#highlight#linenr_enable() abort
|
||||
let old_highlight_lines = g:gitgutter_highlight_linenrs
|
||||
let old_highlight_linenrs = g:gitgutter_highlight_linenrs
|
||||
|
||||
let g:gitgutter_highlight_linenrs = 1
|
||||
call s:define_sign_linenr_highlights()
|
||||
|
||||
if !old_highlight_lines && !g:gitgutter_signs
|
||||
if !old_highlight_linenrs && !g:gitgutter_signs
|
||||
call gitgutter#all(1)
|
||||
endif
|
||||
|
||||
@ -102,6 +103,10 @@ function! gitgutter#highlight#define_highlights() abort
|
||||
highlight default link GitGutterChangeLineNr CursorLineNr
|
||||
highlight default link GitGutterDeleteLineNr CursorLineNr
|
||||
highlight default link GitGutterChangeDeleteLineNr CursorLineNr
|
||||
|
||||
" Highlights used intra line.
|
||||
highlight GitGutterAddIntraLine gui=reverse cterm=reverse
|
||||
highlight GitGutterDeleteIntraLine gui=reverse cterm=reverse
|
||||
endfunction
|
||||
|
||||
function! gitgutter#highlight#define_signs() abort
|
||||
@ -171,12 +176,12 @@ function! s:define_sign_linenr_highlights() abort
|
||||
if has('nvim-0.3.2')
|
||||
try
|
||||
if g:gitgutter_highlight_linenrs
|
||||
sign define GitGutterLineAdded numhl=GitGutterAddLineNr
|
||||
sign define GitGutterLineModified numhl=GitGutterChangeLineNr
|
||||
sign define GitGutterLineRemoved numhl=GitGutterDeleteLineNr
|
||||
sign define GitGutterLineRemovedFirstLine numhl=GitGutterDeleteLineNr
|
||||
sign define GitGutterLineRemovedAboveAndBelow numhl=GitGutterDeleteLineNr
|
||||
sign define GitGutterLineModifiedRemoved numhl=GitGutterChangeDeleteLineNr
|
||||
sign define GitGutterLineAdded numhl=GitGutterAddLineNr
|
||||
sign define GitGutterLineModified numhl=GitGutterChangeLineNr
|
||||
sign define GitGutterLineRemoved numhl=GitGutterDeleteLineNr
|
||||
sign define GitGutterLineRemovedFirstLine numhl=GitGutterDeleteLineNr
|
||||
sign define GitGutterLineRemovedAboveAndBelow numhl=GitGutterDeleteLineNr
|
||||
sign define GitGutterLineModifiedRemoved numhl=GitGutterChangeDeleteLineNr
|
||||
else
|
||||
sign define GitGutterLineAdded numhl=
|
||||
sign define GitGutterLineModified numhl=
|
||||
|
@ -1,3 +1,5 @@
|
||||
let s:winid = 0
|
||||
|
||||
function! gitgutter#hunk#set_hunks(bufnr, hunks) abort
|
||||
call gitgutter#utility#setbufvar(a:bufnr, 'hunks', a:hunks)
|
||||
call s:reset_summary(a:bufnr)
|
||||
@ -175,24 +177,24 @@ function! gitgutter#hunk#stage(...) abort
|
||||
else
|
||||
call s:hunk_op(function('s:stage'))
|
||||
endif
|
||||
silent! call repeat#set("\<Plug>GitGutterStageHunk", -1)
|
||||
silent! call repeat#set("\<Plug>(GitGutterStageHunk)", -1)
|
||||
endfunction
|
||||
|
||||
function! gitgutter#hunk#undo() abort
|
||||
call s:hunk_op(function('s:undo'))
|
||||
silent! call repeat#set("\<Plug>GitGutterUndoHunk", -1)
|
||||
silent! call repeat#set("\<Plug>(GitGutterUndoHunk)", -1)
|
||||
endfunction
|
||||
|
||||
function! gitgutter#hunk#preview() abort
|
||||
call s:hunk_op(function('s:preview'))
|
||||
silent! call repeat#set("\<Plug>GitGutterPreviewHunk", -1)
|
||||
silent! call repeat#set("\<Plug>(GitGutterPreviewHunk)", -1)
|
||||
endfunction
|
||||
|
||||
|
||||
function! s:hunk_op(op, ...)
|
||||
let bufnr = bufnr('')
|
||||
|
||||
if &previewwindow
|
||||
if s:in_hunk_preview_window()
|
||||
if string(a:op) =~ '_stage'
|
||||
" combine hunk-body in preview window with updated hunk-header
|
||||
let hunk_body = getline(1, '$')
|
||||
@ -214,8 +216,8 @@ function! s:hunk_op(op, ...)
|
||||
|
||||
let hunk_diff = join(hunk_header + hunk_body, "\n")."\n"
|
||||
|
||||
wincmd p
|
||||
pclose
|
||||
call s:goto_original_window()
|
||||
call s:close_hunk_preview_window()
|
||||
call s:stage(hunk_diff)
|
||||
endif
|
||||
|
||||
@ -225,7 +227,7 @@ function! s:hunk_op(op, ...)
|
||||
if gitgutter#utility#is_active(bufnr)
|
||||
" Get a (synchronous) diff.
|
||||
let [async, g:gitgutter_async] = [g:gitgutter_async, 0]
|
||||
let diff = gitgutter#diff#run_diff(bufnr, 'index', 1)
|
||||
let diff = gitgutter#diff#run_diff(bufnr, g:gitgutter_diff_relative_to, 1)
|
||||
let g:gitgutter_async = async
|
||||
|
||||
call gitgutter#hunk#set_hunks(bufnr, gitgutter#diff#parse_diff(diff))
|
||||
@ -276,7 +278,7 @@ endfunction
|
||||
function! s:undo(hunk_diff)
|
||||
" Apply reverse patch to buffer.
|
||||
let hunk = gitgutter#diff#parse_hunk(split(a:hunk_diff, '\n')[4])
|
||||
let lines = map(split(a:hunk_diff, '\n')[5:], 'v:val[1:]')
|
||||
let lines = map(split(a:hunk_diff, '\r\?\n')[5:], 'v:val[1:]')
|
||||
let lnum = hunk[2]
|
||||
let added_only = hunk[1] == 0 && hunk[3] > 0
|
||||
let removed_only = hunk[1] > 0 && hunk[3] == 0
|
||||
@ -293,33 +295,16 @@ endfunction
|
||||
|
||||
|
||||
function! s:preview(hunk_diff)
|
||||
let lines = split(a:hunk_diff, '\n')
|
||||
let lines = split(a:hunk_diff, '\r\?\n')
|
||||
let header = lines[0:4]
|
||||
let body = lines[5:]
|
||||
|
||||
let body_length = len(body)
|
||||
let previewheight = min([body_length, &previewheight])
|
||||
|
||||
silent! wincmd P
|
||||
if !&previewwindow
|
||||
noautocmd execute g:gitgutter_preview_win_location previewheight 'new'
|
||||
set previewwindow
|
||||
else
|
||||
execute 'resize' previewheight
|
||||
call s:open_hunk_preview_window()
|
||||
call s:populate_hunk_preview_window(header, body)
|
||||
call s:enable_staging_from_hunk_preview_window()
|
||||
if &previewwindow
|
||||
call s:goto_original_window()
|
||||
endif
|
||||
|
||||
let b:hunk_header = header
|
||||
|
||||
setlocal noreadonly modifiable filetype=diff buftype=nofile bufhidden=delete noswapfile
|
||||
execute "%delete_"
|
||||
call setline(1, body)
|
||||
normal! gg
|
||||
|
||||
cnoreabbrev <buffer> <expr> w getcmdtype() == ':' && getcmdline() == 'w' ? 'GitGutterStageHunk' : 'w'
|
||||
" Staging hunk from the preview window closes the window anyway.
|
||||
cnoreabbrev <buffer> <expr> wq getcmdtype() == ':' && getcmdline() == 'wq' ? 'GitGutterStageHunk' : 'wq'
|
||||
|
||||
noautocmd wincmd p
|
||||
endfunction
|
||||
|
||||
|
||||
@ -390,3 +375,150 @@ function! s:line_adjustment_for_current_hunk() abort
|
||||
return adj
|
||||
endfunction
|
||||
|
||||
|
||||
function! s:in_hunk_preview_window()
|
||||
if g:gitgutter_preview_win_floating
|
||||
return win_id2win(s:winid) == winnr()
|
||||
else
|
||||
return &previewwindow
|
||||
endif
|
||||
endfunction
|
||||
|
||||
|
||||
" Floating window: does not move cursor to floating window.
|
||||
" Preview window: moves cursor to preview window.
|
||||
function! s:open_hunk_preview_window()
|
||||
if g:gitgutter_preview_win_floating
|
||||
if exists('*nvim_open_win')
|
||||
call s:close_hunk_preview_window()
|
||||
|
||||
let buf = nvim_create_buf(v:false, v:false)
|
||||
" Set default width and height for now.
|
||||
let s:winid = nvim_open_win(buf, v:false, {
|
||||
\ 'relative': 'cursor',
|
||||
\ 'row': 1,
|
||||
\ 'col': 0,
|
||||
\ 'width': 42,
|
||||
\ 'height': &previewheight,
|
||||
\ 'style': 'minimal'
|
||||
\ })
|
||||
call nvim_buf_set_option(buf, 'filetype', 'diff')
|
||||
call nvim_buf_set_option(buf, 'buftype', 'acwrite')
|
||||
call nvim_buf_set_option(buf, 'bufhidden', 'delete')
|
||||
call nvim_buf_set_option(buf, 'swapfile', v:false)
|
||||
call nvim_buf_set_name(buf, 'gitgutter://hunk-preview')
|
||||
|
||||
" Assumes cursor is in original window.
|
||||
autocmd CursorMoved <buffer> ++once call s:close_hunk_preview_window()
|
||||
|
||||
return
|
||||
endif
|
||||
|
||||
if exists('*popup_create')
|
||||
let s:winid = popup_create('', {
|
||||
\ 'line': 'cursor+1',
|
||||
\ 'col': 'cursor',
|
||||
\ 'moved': 'any',
|
||||
\ })
|
||||
|
||||
call setbufvar(winbufnr(s:winid), '&filetype', 'diff')
|
||||
|
||||
return
|
||||
endif
|
||||
endif
|
||||
|
||||
silent! wincmd P
|
||||
if !&previewwindow
|
||||
noautocmd execute g:gitgutter_preview_win_location &previewheight 'new gitgutter://hunk-preview'
|
||||
let s:winid = win_getid()
|
||||
set previewwindow
|
||||
setlocal filetype=diff buftype=acwrite bufhidden=delete
|
||||
" Reset some defaults in case someone else has changed them.
|
||||
setlocal noreadonly modifiable noswapfile
|
||||
endif
|
||||
endfunction
|
||||
|
||||
|
||||
" Floating window: does not care where cursor is.
|
||||
" Preview window: assumes cursor is in preview window.
|
||||
function! s:populate_hunk_preview_window(header, body)
|
||||
let body_length = len(a:body)
|
||||
let height = min([body_length, &previewheight])
|
||||
|
||||
if g:gitgutter_preview_win_floating
|
||||
if exists('*nvim_open_win')
|
||||
" Assumes cursor is not in previewing window.
|
||||
call nvim_buf_set_var(winbufnr(s:winid), 'hunk_header', a:header)
|
||||
|
||||
let width = max(map(copy(a:body), 'strdisplaywidth(v:val)'))
|
||||
call nvim_win_set_width(s:winid, width)
|
||||
call nvim_win_set_height(s:winid, height)
|
||||
|
||||
call nvim_buf_set_lines(winbufnr(s:winid), 0, -1, v:false, [])
|
||||
call nvim_buf_set_lines(winbufnr(s:winid), 0, -1, v:false, a:body)
|
||||
call nvim_buf_set_option(winbufnr(s:winid), 'modified', v:false)
|
||||
|
||||
let ns_id = nvim_create_namespace('GitGutter')
|
||||
call nvim_buf_clear_namespace(winbufnr(s:winid), ns_id, 0, -1)
|
||||
for region in gitgutter#diff_highlight#process(a:body)
|
||||
let group = region[1] == '+' ? 'GitGutterAddIntraLine' : 'GitGutterDeleteIntraLine'
|
||||
call nvim_buf_add_highlight(winbufnr(s:winid), ns_id, group, region[0]-1, region[2]-1, region[3])
|
||||
endfor
|
||||
|
||||
call nvim_win_set_cursor(s:winid, [1,0])
|
||||
endif
|
||||
|
||||
if exists('*popup_create')
|
||||
call popup_settext(s:winid, a:body)
|
||||
|
||||
for region in gitgutter#diff_highlight#process(a:body)
|
||||
let group = region[1] == '+' ? 'GitGutterAddIntraLine' : 'GitGutterDeleteIntraLine'
|
||||
call win_execute(s:winid, "call matchaddpos('".group."', [[".region[0].", ".region[2].", ".(region[3]-region[2]+1)."]])")
|
||||
endfor
|
||||
endif
|
||||
|
||||
else
|
||||
let b:hunk_header = a:header
|
||||
execute 'resize' height
|
||||
|
||||
%delete _
|
||||
call setline(1, a:body)
|
||||
setlocal nomodified
|
||||
|
||||
call clearmatches()
|
||||
for region in gitgutter#diff_highlight#process(a:body)
|
||||
let group = region[1] == '+' ? 'GitGutterAddIntraLine' : 'GitGutterDeleteIntraLine'
|
||||
call matchaddpos(group, [[region[0], region[2], region[3]-region[2]+1]])
|
||||
endfor
|
||||
|
||||
1
|
||||
endif
|
||||
endfunction
|
||||
|
||||
|
||||
function! s:enable_staging_from_hunk_preview_window()
|
||||
augroup gitgutter_hunk_preview
|
||||
autocmd!
|
||||
execute 'autocmd BufWriteCmd <buffer='.winbufnr(s:winid).'> GitGutterStageHunk'
|
||||
augroup END
|
||||
endfunction
|
||||
|
||||
|
||||
function! s:goto_original_window()
|
||||
noautocmd wincmd p
|
||||
endfunction
|
||||
|
||||
|
||||
function! s:close_hunk_preview_window()
|
||||
call setbufvar(winbufnr(s:winid), '&modified', 0)
|
||||
|
||||
if g:gitgutter_preview_win_floating
|
||||
if win_id2win(s:winid) > 0
|
||||
execute win_id2win(s:winid).'wincmd c'
|
||||
endif
|
||||
else
|
||||
pclose
|
||||
endif
|
||||
|
||||
let s:winid = 0
|
||||
endfunction
|
||||
|
@ -11,7 +11,7 @@ function! gitgutter#sign#enable() abort
|
||||
let g:gitgutter_signs = 1
|
||||
call gitgutter#highlight#define_sign_text_highlights()
|
||||
|
||||
if !old_signs && !g:gitgutter_highlight_lines
|
||||
if !old_signs && !g:gitgutter_highlight_lines && !g:gitgutter_highlight_linenrs
|
||||
call gitgutter#all(1)
|
||||
endif
|
||||
endfunction
|
||||
@ -20,7 +20,7 @@ function! gitgutter#sign#disable() abort
|
||||
let g:gitgutter_signs = 0
|
||||
call gitgutter#highlight#define_sign_text_highlights()
|
||||
|
||||
if !g:gitgutter_highlight_lines
|
||||
if !g:gitgutter_highlight_lines && !g:gitgutter_highlight_linenrs
|
||||
call gitgutter#sign#clear_signs(bufnr(''))
|
||||
endif
|
||||
endfunction
|
||||
|
@ -13,6 +13,7 @@ CONTENTS *gitgutter*
|
||||
|
||||
Introduction ................. |gitgutter-introduction|
|
||||
Installation ................. |gitgutter-installation|
|
||||
Windows ................. |gitgutter-windows|
|
||||
Commands ..................... |gitgutter-commands|
|
||||
Mappings ..................... |gitgutter-mappings|
|
||||
Autocommand .................. |gitgutter-autocommand|
|
||||
@ -36,49 +37,26 @@ The signs are always up to date and the plugin never saves your buffer.
|
||||
===============================================================================
|
||||
INSTALLATION *gitgutter-installation*
|
||||
|
||||
Pathogen:~
|
||||
>
|
||||
cd ~/.vim/bundle
|
||||
git clone git://github.com/airblade/vim-gitgutter.git
|
||||
<
|
||||
Voom:~
|
||||
Use your favourite package manager, or use Vim's built-in package support.
|
||||
|
||||
Edit your plugin manifest (`voom edit`) and add:
|
||||
Vim:~
|
||||
>
|
||||
airblade/vim-gitgutter
|
||||
mkdir -p ~/.vim/pack/airblade/start
|
||||
cd ~/.vim/pack/airblade/start
|
||||
git clone https://github.com/airblade/vim-gitgutter.git
|
||||
vim -u NONE -c "helptags vim-gitgutter/doc" -c q
|
||||
<
|
||||
VimPlug:~
|
||||
|
||||
Place this in your .vimrc:
|
||||
Neovim:~
|
||||
>
|
||||
Plug 'airblade/vim-gitgutter'
|
||||
mkdir -p ~/.config/nvim/pack/airblade/start
|
||||
cd ~/.config/nvim/pack/airblade/start
|
||||
git clone https://github.com/airblade/vim-gitgutter.git
|
||||
nvim -u NONE -c "helptags vim-gitgutter/doc" -c q
|
||||
<
|
||||
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|.
|
||||
|
||||
|
||||
===============================================================================
|
||||
WINDOWS *gitgutter-windows*
|
||||
|
||||
I recommend configuring vim-gitgutter with the full path to your git executable.
|
||||
@ -160,6 +138,10 @@ Commands for jumping between hunks:~
|
||||
*gitgutter-:GitGutterPrevHunk*
|
||||
:GitGutterPrevHunk Jump to the previous [count] hunk.
|
||||
|
||||
*gitgutter-:GitGutterQuickFix*
|
||||
:GitGutterQuickFix Load all hunks into the |quickfix| list. Note this
|
||||
ignores any unsaved changes in your buffers.
|
||||
|
||||
|
||||
Commands for operating on a hunk:~
|
||||
|
||||
@ -228,9 +210,9 @@ These can be repeated with `.` if you have vim-repeat installed.
|
||||
|
||||
You can change these mappings like this:
|
||||
>
|
||||
nmap ghp <Plug>GitGutterPreviewHunk
|
||||
nmap ghs <Plug>GitGutterStageHunk
|
||||
nmap ghu <Plug>GitGutterUndoHunk
|
||||
nmap ghp <Plug>(GitGutterPreviewHunk)
|
||||
nmap ghs <Plug>(GitGutterStageHunk)
|
||||
nmap ghu <Plug>(GitGutterUndoHunk)
|
||||
<
|
||||
|
||||
Hunk jumping:~
|
||||
@ -243,8 +225,8 @@ Hunk jumping:~
|
||||
|
||||
You can change these mappings like this:
|
||||
>
|
||||
nmap [c <Plug>GitGutterPrevHunk
|
||||
nmap ]c <Plug>GitGutterNextHunk
|
||||
nmap [c <Plug>(GitGutterPrevHunk)
|
||||
nmap ]c <Plug>(GitGutterNextHunk)
|
||||
<
|
||||
|
||||
Hunk text object:~
|
||||
@ -253,10 +235,10 @@ Hunk text object:~
|
||||
"ic" operates on the current hunk's lines. "ac" does the same but also includes
|
||||
trailing empty lines.
|
||||
>
|
||||
omap ic <Plug>GitGutterTextObjectInnerPending
|
||||
omap ac <Plug>GitGutterTextObjectOuterPending
|
||||
xmap ic <Plug>GitGutterTextObjectInnerVisual
|
||||
xmap ac <Plug>GitGutterTextObjectOuterVisual
|
||||
omap ic <Plug>(GitGutterTextObjectInnerPending)
|
||||
omap ac <Plug>(GitGutterTextObjectOuterPending)
|
||||
xmap ic <Plug>(GitGutterTextObjectInnerVisual)
|
||||
xmap ac <Plug>(GitGutterTextObjectOuterVisual)
|
||||
<
|
||||
|
||||
|
||||
@ -276,6 +258,7 @@ Git:~
|
||||
|g:gitgutter_git_executable|
|
||||
|g:gitgutter_git_args|
|
||||
|g:gitgutter_diff_args|
|
||||
|g:gitgutter_diff_relative_to|
|
||||
|g:gitgutter_diff_base|
|
||||
|
||||
Grep:~
|
||||
@ -297,6 +280,10 @@ Signs:~
|
||||
|g:gitgutter_sign_modified_removed|
|
||||
|g:gitgutter_override_sign_column_highlight|
|
||||
|
||||
Hunk previews:~
|
||||
|
||||
|g:gitgutter_preview_win_floating|
|
||||
|
||||
Terminal:~
|
||||
|
||||
|g:gitgutter_terminal_reports_focus|
|
||||
@ -339,6 +326,15 @@ Use this option to pass any extra arguments to git-diff. For example:
|
||||
let g:gitgutter_diff_args = '-w'
|
||||
<
|
||||
|
||||
*g:gitgutter_diff_relative_to*
|
||||
Default: empty
|
||||
|
||||
By default buffers are diffed against the index. Use this option to diff against
|
||||
the working tree. For example:
|
||||
>
|
||||
let g:gitgutter_diff_relative_to = 'working_tree'
|
||||
<
|
||||
|
||||
*g:gitgutter_diff_base*
|
||||
Default: empty
|
||||
|
||||
@ -348,6 +344,9 @@ a revision instead. For example:
|
||||
let g:gitgutter_diff_base = '<some commit SHA>'
|
||||
<
|
||||
|
||||
This setting is ignore when the diff is relative to the working tree
|
||||
(|g:gitgutter_diff_relative_to|).
|
||||
|
||||
*g:gitgutter_grep*
|
||||
Default: 'grep'
|
||||
|
||||
@ -437,6 +436,15 @@ it in your |vimrc|:
|
||||
User-defined (graphical Vim) highlight SignColumn guibg={whatever}
|
||||
|
||||
|
||||
*g:gitgutter_preview_win_floating*
|
||||
Default: 0 (Vim)
|
||||
0 (NeoVim which does not support floating windows)
|
||||
1 (NeoVim which does support floating windows)
|
||||
|
||||
Whether to use floating/popup windows for hunk previews. Note that if you use
|
||||
popup windows on Vim you will not be able to stage partial hunks via the
|
||||
preview window.
|
||||
|
||||
*g:gitgutter_terminal_reports_focus*
|
||||
Default: 1
|
||||
|
||||
|
@ -23,6 +23,11 @@ function! s:set(var, default) abort
|
||||
endfunction
|
||||
|
||||
call s:set('g:gitgutter_preview_win_location', 'bo')
|
||||
if exists('*nvim_open_win')
|
||||
call s:set('g:gitgutter_preview_win_floating', 1)
|
||||
else
|
||||
call s:set('g:gitgutter_preview_win_floating', 0)
|
||||
endif
|
||||
call s:set('g:gitgutter_enabled', 1)
|
||||
call s:set('g:gitgutter_max_signs', 500)
|
||||
call s:set('g:gitgutter_signs', 1)
|
||||
@ -49,6 +54,7 @@ endif
|
||||
call s:set('g:gitgutter_sign_removed_above_and_below', '[')
|
||||
call s:set('g:gitgutter_sign_modified_removed', '~_')
|
||||
call s:set('g:gitgutter_git_args', '')
|
||||
call s:set('g:gitgutter_diff_relative_to', 'index')
|
||||
call s:set('g:gitgutter_diff_args', '')
|
||||
call s:set('g:gitgutter_diff_base', '')
|
||||
call s:set('g:gitgutter_map_keys', 1)
|
||||
@ -103,6 +109,8 @@ command! -bar GitGutterBufferDisable call gitgutter#buffer_disable()
|
||||
command! -bar GitGutterBufferEnable call gitgutter#buffer_enable()
|
||||
command! -bar GitGutterBufferToggle call gitgutter#buffer_toggle()
|
||||
|
||||
command! -bar GitGutterQuickFix call gitgutter#quickfix()
|
||||
|
||||
" }}}
|
||||
|
||||
" Line highlights {{{
|
||||
@ -137,10 +145,10 @@ command! -bar GitGutterUndoHunk call gitgutter#hunk#undo()
|
||||
command! -bar GitGutterPreviewHunk call gitgutter#hunk#preview()
|
||||
|
||||
" Hunk text object
|
||||
onoremap <silent> <Plug>GitGutterTextObjectInnerPending :<C-U>call gitgutter#hunk#text_object(1)<CR>
|
||||
onoremap <silent> <Plug>GitGutterTextObjectOuterPending :<C-U>call gitgutter#hunk#text_object(0)<CR>
|
||||
xnoremap <silent> <Plug>GitGutterTextObjectInnerVisual :<C-U>call gitgutter#hunk#text_object(1)<CR>
|
||||
xnoremap <silent> <Plug>GitGutterTextObjectOuterVisual :<C-U>call gitgutter#hunk#text_object(0)<CR>
|
||||
onoremap <silent> <Plug>(GitGutterTextObjectInnerPending) :<C-U>call gitgutter#hunk#text_object(1)<CR>
|
||||
onoremap <silent> <Plug>(GitGutterTextObjectOuterPending) :<C-U>call gitgutter#hunk#text_object(0)<CR>
|
||||
xnoremap <silent> <Plug>(GitGutterTextObjectInnerVisual) :<C-U>call gitgutter#hunk#text_object(1)<CR>
|
||||
xnoremap <silent> <Plug>(GitGutterTextObjectOuterVisual) :<C-U>call gitgutter#hunk#text_object(0)<CR>
|
||||
|
||||
|
||||
" Returns the git-diff hunks for the file or an empty list if there
|
||||
@ -184,13 +192,19 @@ command! -bar GitGutterDebug call gitgutter#debug#debug()
|
||||
|
||||
" Maps {{{
|
||||
|
||||
nnoremap <silent> <expr> <Plug>GitGutterNextHunk &diff ? ']c' : ":\<C-U>execute v:count1 . 'GitGutterNextHunk'\<CR>"
|
||||
nnoremap <silent> <expr> <Plug>GitGutterPrevHunk &diff ? '[c' : ":\<C-U>execute v:count1 . 'GitGutterPrevHunk'\<CR>"
|
||||
nnoremap <silent> <expr> <Plug>(GitGutterNextHunk) &diff ? ']c' : ":\<C-U>execute v:count1 . 'GitGutterNextHunk'\<CR>"
|
||||
nnoremap <silent> <expr> <Plug>GitGutterNextHunk &diff ? ']c' : ":\<C-U>call gitgutter#utility#warn('please change your map \<lt>Plug>GitGutterNextHunk to \<lt>Plug>(GitGutterNextHunk)')\<CR>"
|
||||
nnoremap <silent> <expr> <Plug>(GitGutterPrevHunk) &diff ? '[c' : ":\<C-U>execute v:count1 . 'GitGutterPrevHunk'\<CR>"
|
||||
nnoremap <silent> <expr> <Plug>GitGutterPrevHunk &diff ? '[c' : ":\<C-U>call gitgutter#utility#warn('please change your map \<lt>Plug>GitGutterPrevHunk to \<lt>Plug>(GitGutterPrevHunk)')\<CR>"
|
||||
|
||||
xnoremap <silent> <Plug>GitGutterStageHunk :GitGutterStageHunk<CR>
|
||||
nnoremap <silent> <Plug>GitGutterStageHunk :GitGutterStageHunk<CR>
|
||||
nnoremap <silent> <Plug>GitGutterUndoHunk :GitGutterUndoHunk<CR>
|
||||
nnoremap <silent> <Plug>GitGutterPreviewHunk :GitGutterPreviewHunk<CR>
|
||||
xnoremap <silent> <Plug>(GitGutterStageHunk) :GitGutterStageHunk<CR>
|
||||
xnoremap <silent> <Plug>GitGutterStageHunk :call gitgutter#utility#warn('please change your map <lt>Plug>GitGutterStageHunk to <lt>Plug>(GitGutterStageHunk)')<CR>
|
||||
nnoremap <silent> <Plug>(GitGutterStageHunk) :GitGutterStageHunk<CR>
|
||||
nnoremap <silent> <Plug>GitGutterStageHunk :call gitgutter#utility#warn('please change your map <lt>Plug>GitGutterStageHunk to <lt>Plug>(GitGutterStageHunk)')<CR>
|
||||
nnoremap <silent> <Plug>(GitGutterUndoHunk) :GitGutterUndoHunk<CR>
|
||||
nnoremap <silent> <Plug>GitGutterUndoHunk :call gitgutter#utility#warn('please change your map <lt>Plug>GitGutterUndoHunk to <lt>Plug>(GitGutterUndoHunk)')<CR>
|
||||
nnoremap <silent> <Plug>(GitGutterPreviewHunk) :GitGutterPreviewHunk<CR>
|
||||
nnoremap <silent> <Plug>GitGutterPreviewHunk :call gitgutter#utility#warn('please change your map <lt>Plug>GitGutterPreviewHunk to <lt>Plug>(GitGutterPreviewHunk)')<CR>
|
||||
|
||||
" }}}
|
||||
|
||||
@ -215,7 +229,11 @@ augroup gitgutter
|
||||
autocmd BufEnter * call s:on_bufenter()
|
||||
|
||||
autocmd CursorHold,CursorHoldI * call gitgutter#process_buffer(bufnr(''), 0)
|
||||
autocmd FileChangedShellPost * call gitgutter#process_buffer(bufnr(''), 1)
|
||||
if exists('*timer_start') && has('lambda')
|
||||
autocmd FileChangedShellPost * call timer_start(1, {-> gitgutter#process_buffer(bufnr(''), 1)})
|
||||
else
|
||||
autocmd FileChangedShellPost * call gitgutter#process_buffer(bufnr(''), 1)
|
||||
endif
|
||||
|
||||
" Ensure that all buffers are processed when opening vim with multiple files, e.g.:
|
||||
"
|
||||
|
Binary file not shown.
Before Width: | Height: | Size: 16 KiB After Width: | Height: | Size: 587 KiB |
11
sources_non_forked/vim-gitgutter/test/fixture_dos.txt
Normal file
11
sources_non_forked/vim-gitgutter/test/fixture_dos.txt
Normal file
@ -0,0 +1,11 @@
|
||||
a
|
||||
b
|
||||
c
|
||||
d
|
||||
e
|
||||
f
|
||||
g
|
||||
h
|
||||
i
|
||||
j
|
||||
|
@ -6,35 +6,40 @@ let s:bufnr = bufnr('')
|
||||
" Helpers
|
||||
"
|
||||
|
||||
" Ignores unexpected keys.
|
||||
"
|
||||
" expected - list of signs
|
||||
function s:assert_signs(expected, filename)
|
||||
" Ignores unexpected keys in actual.
|
||||
function s:assert_list_of_dicts(expected, actual)
|
||||
if empty(a:expected)
|
||||
call assert_equal(a:expected, [])
|
||||
call assert_equal([], a:actual)
|
||||
return
|
||||
endif
|
||||
|
||||
let expected_keys = keys(a:expected[0])
|
||||
let actual = sign_getplaced(a:filename, {'group': 'gitgutter'})[0].signs
|
||||
|
||||
for sign in actual
|
||||
for k in keys(sign)
|
||||
for dict in a:actual
|
||||
for k in keys(dict)
|
||||
if index(expected_keys, k) == -1
|
||||
call remove(sign, k)
|
||||
call remove(dict, k)
|
||||
endif
|
||||
endfor
|
||||
endfor
|
||||
|
||||
call assert_equal(a:expected, actual)
|
||||
call assert_equal(a:expected, a:actual)
|
||||
endfunction
|
||||
|
||||
function s:git_diff()
|
||||
return split(system('git diff -U0 fixture.txt'), '\n')
|
||||
" Ignores unexpected keys.
|
||||
"
|
||||
" expected - list of signs
|
||||
function s:assert_signs(expected, filename)
|
||||
let actual = sign_getplaced(a:filename, {'group': 'gitgutter'})[0].signs
|
||||
call s:assert_list_of_dicts(a:expected, actual)
|
||||
endfunction
|
||||
|
||||
function s:git_diff_staged()
|
||||
return split(system('git diff -U0 --staged fixture.txt'), '\n')
|
||||
function s:git_diff(...)
|
||||
return split(system('git diff -U0 '.(a:0 ? a:1 : 'fixture.txt')), '\n')
|
||||
endfunction
|
||||
|
||||
function s:git_diff_staged(...)
|
||||
return split(system('git diff -U0 --staged '.(a:0 ? a:1 : 'fixture.txt')), '\n')
|
||||
endfunction
|
||||
|
||||
function s:trigger_gitgutter()
|
||||
@ -50,11 +55,16 @@ function SetUp()
|
||||
call system("git init ".s:test_repo.
|
||||
\ " && cd ".s:test_repo.
|
||||
\ " && cp ../fixture.txt .".
|
||||
\ " && cp ../fixture_dos.txt .".
|
||||
\ " && git add . && git commit -m 'initial'".
|
||||
\ " && git config diff.mnemonicPrefix false")
|
||||
execute ':cd' s:test_repo
|
||||
edit! fixture.txt
|
||||
call gitgutter#sign#reset()
|
||||
|
||||
" FIXME why won't vim autoload the file?
|
||||
execute 'source' '../../autoload/gitgutter/diff_highlight.vim'
|
||||
execute 'source' '../../autoload/gitgutter/fold.vim'
|
||||
endfunction
|
||||
|
||||
function TearDown()
|
||||
@ -340,6 +350,34 @@ function Test_hunk_outside_noop()
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_preview()
|
||||
normal 5Gi*
|
||||
GitGutterPreviewHunk
|
||||
|
||||
wincmd P
|
||||
call assert_equal(2, line('$'))
|
||||
call assert_equal('-e', getline(1))
|
||||
call assert_equal('+*e', getline(2))
|
||||
wincmd p
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_preview_dos()
|
||||
edit! fixture_dos.txt
|
||||
|
||||
normal 5Gi*
|
||||
GitGutterPreviewHunk
|
||||
|
||||
wincmd P
|
||||
call assert_equal(2, line('$'))
|
||||
call assert_equal('-e', getline(1))
|
||||
call assert_equal('+*e', getline(2))
|
||||
wincmd p
|
||||
endfunction
|
||||
|
||||
|
||||
|
||||
|
||||
function Test_hunk_stage()
|
||||
let _shell = &shell
|
||||
set shell=foo
|
||||
@ -645,6 +683,20 @@ function Test_hunk_undo()
|
||||
call s:assert_signs([], 'fixture.txt')
|
||||
call assert_equal([], s:git_diff())
|
||||
call assert_equal([], s:git_diff_staged())
|
||||
call assert_equal('e', getline(5))
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_hunk_undo_dos()
|
||||
edit! fixture_dos.txt
|
||||
|
||||
normal 5Gi*
|
||||
GitGutterUndoHunk
|
||||
|
||||
call s:assert_signs([], 'fixture_dos.txt')
|
||||
call assert_equal([], s:git_diff('fixture_dos.txt'))
|
||||
call assert_equal([], s:git_diff_staged('fixture_dos.txt'))
|
||||
call assert_equal('e', getline(5))
|
||||
endfunction
|
||||
|
||||
|
||||
@ -889,3 +941,173 @@ function Test_empty_file()
|
||||
|
||||
set eol fixeol
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_quickfix()
|
||||
call setline(5, ['A', 'B'])
|
||||
call setline(9, ['C', 'D'])
|
||||
write
|
||||
|
||||
GitGutterQuickFix
|
||||
|
||||
let expected = [
|
||||
\ {'lnum': 5, 'bufnr': bufnr(''), 'text': '-e'},
|
||||
\ {'lnum': 9, 'bufnr': bufnr(''), 'text': '-i'}
|
||||
\ ]
|
||||
|
||||
call s:assert_list_of_dicts(expected, getqflist())
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_common_prefix()
|
||||
" zero length
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('', 'foo'))
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('foo', ''))
|
||||
" nothing in common
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('-abcde', '+pqrst'))
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('abcde', 'pqrst'))
|
||||
" something in common
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('-abcde', '+abcpq'))
|
||||
call assert_equal(2, gitgutter#diff_highlight#common_prefix('abcde', 'abcpq'))
|
||||
call assert_equal(0, gitgutter#diff_highlight#common_prefix('abc', 'apq'))
|
||||
" everything in common
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('-abcde', '+abcde'))
|
||||
call assert_equal(4, gitgutter#diff_highlight#common_prefix('abcde', 'abcde'))
|
||||
" different lengths
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('-abcde', '+abx'))
|
||||
call assert_equal(1, gitgutter#diff_highlight#common_prefix('abcde', 'abx'))
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('-abx', '+abcde'))
|
||||
call assert_equal(1, gitgutter#diff_highlight#common_prefix('abx', 'abcde'))
|
||||
call assert_equal(-1, gitgutter#diff_highlight#common_prefix('-abcde', '+abc'))
|
||||
call assert_equal(2, gitgutter#diff_highlight#common_prefix('abcde', 'abc'))
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_common_suffix()
|
||||
" nothing in common
|
||||
call assert_equal([6,6], gitgutter#diff_highlight#common_suffix('-abcde', '+pqrst', 0))
|
||||
" something in common
|
||||
call assert_equal([3,3], gitgutter#diff_highlight#common_suffix('-abcde', '+pqcde', 0))
|
||||
" everything in common
|
||||
call assert_equal([5,5], gitgutter#diff_highlight#common_suffix('-abcde', '+abcde', 5))
|
||||
" different lengths
|
||||
call assert_equal([4,2], gitgutter#diff_highlight#common_suffix('-abcde', '+xde', 0))
|
||||
call assert_equal([2,4], gitgutter#diff_highlight#common_suffix('-xde', '+abcde', 0))
|
||||
endfunction
|
||||
|
||||
|
||||
" Note the order of lists within the overall returned list does not matter.
|
||||
function Test_diff_highlight()
|
||||
" Ignores mismatched number of added and removed lines.
|
||||
call assert_equal([], gitgutter#diff_highlight#process(['-foo']))
|
||||
call assert_equal([], gitgutter#diff_highlight#process(['+foo']))
|
||||
call assert_equal([], gitgutter#diff_highlight#process(['-foo','-bar','+baz']))
|
||||
|
||||
" everything changed
|
||||
let hunk = ['-foo', '+cat']
|
||||
let expected = []
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" change in middle
|
||||
let hunk = ['-foo bar baz', '+foo zip baz']
|
||||
let expected = [[1, '-', 6, 8], [2, '+', 6, 8]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" change at start
|
||||
let hunk = ['-foo bar baz', '+zip bar baz']
|
||||
let expected = [[1, '-', 2, 4], [2, '+', 2, 4]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" change at end
|
||||
let hunk = ['-foo bar baz', '+foo bar zip']
|
||||
let expected = [[1, '-', 10, 12], [2, '+', 10, 12]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" removed in middle
|
||||
let hunk = ['-foo bar baz', '+foo baz']
|
||||
let expected = [[1, '-', 8, 11]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" added in middle
|
||||
let hunk = ['-foo baz', '+foo bar baz']
|
||||
let expected = [[2, '+', 8, 11]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" two insertions at start
|
||||
let hunk = ['-foo bar baz', '+(foo) bar baz']
|
||||
let expected = [[2, '+', 2, 2], [2, '+', 6, 6]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" two insertions in middle
|
||||
let hunk = ['-foo bar baz', '+foo (bar) baz']
|
||||
let expected = [[2, '+', 6, 6], [2, '+', 10, 10]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" two insertions at end
|
||||
let hunk = ['-foo bar baz', '+foo bar (baz)']
|
||||
let expected = [[2, '+', 10, 10], [2, '+', 14, 14]]
|
||||
call assert_equal(expected, gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" singular insertion
|
||||
let hunk = ['-The cat in the hat.', '+The furry cat in the hat.']
|
||||
call assert_equal([[2, '+', 6, 11]], gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" singular deletion
|
||||
let hunk = ['-The cat in the hat.', '+The cat.']
|
||||
call assert_equal([[1, '-', 9, 19]], gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" two insertions
|
||||
let hunk = ['-The cat in the hat.', '+The furry cat in the teal hat.']
|
||||
call assert_equal([[2, '+', 6, 11], [2, '+', 22, 26]], gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" two deletions
|
||||
let hunk = ['-The furry cat in the teal hat.', '+The cat in the hat.']
|
||||
call assert_equal([[1, '-', 6, 11], [1, '-', 22, 26]], gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" two edits
|
||||
let hunk = ['-The cat in the hat.', '+The ox in the box.']
|
||||
call assert_equal([[1, '-', 6, 8], [2, '+', 6, 7], [1, '-', 17, 19], [2, '+', 16, 18]], gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
" Requires s:gap_between_regions = 2 to pass.
|
||||
" let hunk = ['-foo: bar.zap', '+foo: quux(bar)']
|
||||
" call assert_equal([[2, '+', 7, 11], [1, '-', 10, 13], [2, '+', 15, 15]], gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
let hunk = ['-gross_value: transaction.unexplained_amount', '+gross_value: amount(transaction)']
|
||||
call assert_equal([[2, '+', 15, 21], [1, '-', 26, 44], [2, '+', 33, 33]], gitgutter#diff_highlight#process(hunk))
|
||||
|
||||
let hunk = ['-gem "contact_sport", "~> 1.0.2"', '+gem ("contact_sport"), "~> 1.2"']
|
||||
call assert_equal([[2, '+', 6, 6], [2, '+', 22, 22], [1, '-', 28, 29]], gitgutter#diff_highlight#process(hunk))
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_lcs()
|
||||
call assert_equal('', gitgutter#diff_highlight#lcs('', 'foo'))
|
||||
call assert_equal('', gitgutter#diff_highlight#lcs('foo', ''))
|
||||
call assert_equal('bar', gitgutter#diff_highlight#lcs('foobarbaz', 'bbart'))
|
||||
call assert_equal('transaction', gitgutter#diff_highlight#lcs('transaction.unexplained_amount', 'amount(transaction)'))
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_split()
|
||||
call assert_equal(['foo', 'baz'], gitgutter#diff_highlight#split('foobarbaz', 'bar'))
|
||||
call assert_equal(['', 'barbaz'], gitgutter#diff_highlight#split('foobarbaz', 'foo'))
|
||||
call assert_equal(['foobar', ''], gitgutter#diff_highlight#split('foobarbaz', 'baz'))
|
||||
call assert_equal(['1', '2'], gitgutter#diff_highlight#split('1~2', '~'))
|
||||
endfunction
|
||||
|
||||
|
||||
function Test_foldtext()
|
||||
8d
|
||||
call s:trigger_gitgutter()
|
||||
call assert_equal(0, gitgutter#fold#is_changed())
|
||||
|
||||
let v:foldstart = 5
|
||||
let v:foldend = 9
|
||||
call assert_equal(1, gitgutter#fold#is_changed())
|
||||
call assert_equal('+- 5 lines (*): e', gitgutter#fold#foldtext())
|
||||
|
||||
let v:foldstart = 1
|
||||
let v:foldend = 3
|
||||
call assert_equal(0, gitgutter#fold#is_changed())
|
||||
call assert_equal('+- 3 lines: a', gitgutter#fold#foldtext())
|
||||
endfunction
|
||||
|
Reference in New Issue
Block a user