diff --git a/README b/README index 6ab9429..aac3c81 100644 --- a/README +++ b/README @@ -1,5 +1,18 @@ +**UPDATE** For a general solution take a look at: +https://github.com/dirkwallenstein/vim-match-control + bad-whitespace - Highlights whitespace at the end of lines +Features +-------- +There are configuration options that allow you to adjust filetype-specific +behavior of the highlighting. You can turn the highlighting initially off, use an +alternative (e.g. faint) color, or suppress highlighting in the +/- columns of +patches in unified diff format. + +Original Note +------------- + http://www.vim.org/scripts/script.php?script_id=3735 Author: Bit Connor @@ -32,3 +45,6 @@ This plugin is better than competing plugins because it doesn't show highlighting in buffers that are not modifiable, which is usually what you want. This makes it compatible with UI buffers that happen to contain bad whitespace, such as the quickfix window, or the fugitive plugin. + +This plugin can optionally suppress highlighting in the +/- columns of a +patch in unified diff format. diff --git a/doc/bad-whitespace.txt b/doc/bad-whitespace.txt index 652e9a0..f74018b 100644 --- a/doc/bad-whitespace.txt +++ b/doc/bad-whitespace.txt @@ -51,4 +51,55 @@ Disables bad whitespace highlighting for the current buffer. Toggles bad whitespace highlighting for the current buffer. + *SetSearchPatternToBadWhitespace * + +Write the bad-whitespace pattern for the current buffer to the last search +pattern register. This way you can jump to an error by creating a mapping +like this: > + nnoremap W :SetSearchPatternToBadWhitespacen +< + +Configuration~ *g:bad_whitespace_patch_filetypes* + +You can suppress highlighting of the +/- columns in patch filetypes, by setting +the variable 'g:bad_whitespace_patch_filetypes'. The column width is derived +from the number fo '@' characters introducing the hunk header. The given value +in this example is the default: > + let g:bad_whitespace_patch_filetypes = ['diff', 'git'] +< + + *g:bad_whitespace_alternative_color_filetypes* + +Use the alternative color for the given filetypes. The default is empty. +Example: > + let g:bad_whitespace_alternative_color_filetypes = ['text', 'gitcommit'] +< + + *g:bad_whitespace_off_filetypes* + +Initially turn off bad-whitespace highlighting for the filetypes in this list. +Example: > + let g:bad_whitespace_off_filetypes = ['text', 'markdown'] +< + + *g:bad_whitespace_color_default* + +Specify the name of a color to be used for bad whitespace highlighting. The +default uses a red background. Example: > + let g:bad_whitespace_color_default = 'Error' +< + + *g:bad_whitespace_color_alt_default* + +Specify the name of a color to be used for the alternative bad whitespace +highlighting. The default uses a gray background. Example: > + let g:bad_whitespace_color_alt_default = 'Special' +< + + + *g:bad_whitespace_patch_column_width_fallback* + +If the +/- column width could not be derived from the hunk header, this value +will be used. The default is 0. + vim:tw=78:et:ft=help: diff --git a/plugin/bad-whitespace.vim b/plugin/bad-whitespace.vim index eece123..34a92a9 100644 --- a/plugin/bad-whitespace.vim +++ b/plugin/bad-whitespace.vim @@ -2,59 +2,209 @@ " Maintainer: Bit Connor " Version: 0.3 -function! s:ShowBadWhitespace(force) - if a:force - let b:bad_whitespace_show = 1 +if exists('loaded_bad_whitespace') + finish +endif +let loaded_bad_whitespace = 1 + +if ! exists( "g:bad_whitespace_patch_filetypes" ) + let g:bad_whitespace_patch_filetypes = ['diff', 'git'] +endif + +if ! exists( "g:bad_whitespace_off_filetypes" ) + let g:bad_whitespace_off_filetypes = [] +endif + +if ! exists( "g:bad_whitespace_patch_column_width_fallback" ) + " If the column width could not be derived from the hunk header, use this + " value as a fallback. + let g:bad_whitespace_patch_column_width_fallback = 0 +endif + +if ! exists( "g:bad_whitespace_alternative_color_filetypes" ) + let g:bad_whitespace_alternative_color_filetypes = [] +endif + +if ! exists( "g:bad_whitespace_color_default" ) + highlight default BadWhitespaceDefaultState ctermbg=red guibg=red + let g:bad_whitespace_color_default = 'BadWhitespaceDefaultState' +endif + +if ! exists( "g:bad_whitespace_color_alt_default" ) + highlight default BadWhitespaceAltDefaultState ctermbg=gray guibg=gray + let g:bad_whitespace_color_alt_default = 'BadWhitespaceAltDefaultState' +endif + +if ! exists( "g:bad_whitespace_match_priority" ) + " The priority used for the bad-whitespace match in matchadd() + let g:bad_whitespace_match_priority = -20 +endif + +" The IDs 1-3 are reserved and therefore never used by matchadd. +let s:InvalidMatchId = 1 + +execute 'highlight link BadWhitespace ' . g:bad_whitespace_color_default +execute 'highlight link BadWhitespaceAlternative ' + \ . g:bad_whitespace_color_alt_default +autocmd BufWinEnter,WinEnter * call EnableShowBadWhitespace() +autocmd FileType * call ReInitBuffer() + +function! s:IsAlternativeColorFiletype() + let l:alt_filtypes = filter( + \ copy(g:bad_whitespace_alternative_color_filetypes), + \ 'v:val == &ft') + if empty(l:alt_filtypes) + return 0 + else + return 1 endif - highlight default BadWhitespace ctermbg=red guibg=red - autocmd ColorScheme highlight default BadWhitespace ctermbg=red guibg=red - match BadWhitespace /\s\+$/ - autocmd InsertLeave match BadWhitespace /\s\+$/ - autocmd InsertEnter match BadWhitespace /\s\+\%#\@ execute 'highlight link BadWhitespace ' + \ . g:bad_whitespace_color_default + autocmd ColorScheme + \ execute 'highlight link BadWhitespaceAlternative ' + \ . g:bad_whitespace_color_alt_default + let l:whitespace_pattern_global = s:GetBadWhitespacePattern(0) + let l:whitespace_pattern_editing = s:GetBadWhitespacePattern(1) + if s:IsAlternativeColorFiletype() + let l:active_highlight = 'BadWhitespaceAlternative' + else + let l:active_highlight = 'BadWhitespace' endif - match none BadWhitespace + call s:SetBadWhitespaceMatch(l:active_highlight, l:whitespace_pattern_global) + augroup BadWhitespace + autocmd! * + execute 'autocmd InsertLeave call SetBadWhitespaceMatch( "' + \ . l:active_highlight . '", ''' + \ . l:whitespace_pattern_global . ''')' + execute 'autocmd InsertEnter call SetBadWhitespaceMatch( "' + \ . l:active_highlight . '", ''' + \ . l:whitespace_pattern_editing . ''')' + augroup END endfunction -function! s:EnableShowBadWhitespace() - if exists("b:bad_whitespace_show") - return +function! s:GetBadWhitespacePattern(want_editing_pattern) + " Return the bad-whitespace pattern for the current buffer. If + " want_editing_pattern is nonzero return the pattern for insert mode. + if exists('b:bad_whitespace_buffer_specific_patterns') + let l:pattern_prefixes = b:bad_whitespace_buffer_specific_patterns + else + let l:pattern_prefixes = [ + \ '\_s\+\%$\|\s\+$', + \ '\_s\+\%#\@ShowBadWhitespace(0) + if a:want_editing_pattern + return l:pattern_prefixes[1] else - call HideBadWhitespace(0) + return l:pattern_prefixes[0] endif endfunction -function! s:ToggleBadWhitespace() - if !exists("b:bad_whitespace_show") - let b:bad_whitespace_show = 0 - if &modifiable - let b:bad_whitespace_show = 1 +function! s:GetPatternsForPatches() + let l:save_cursor = getpos(".") + if search('^@\+', 'we') + let l:start_colum = col('.') + else + let l:start_colum = g:bad_whitespace_patch_column_width_fallback + 1 + if g:bad_whitespace_patch_column_width_fallback != 0 + echomsg "bad-whitespace: No @ char match. " + \ . "Will use fallback +/- column width " + \ . g:bad_whitespace_patch_column_width_fallback + endif + endif + call setpos('.', l:save_cursor) + let l:patch_pattern = '\%' . l:start_colum . 'c.\{-\}\zs\s\+\ze' + return [l:patch_pattern . '$', l:patch_pattern . '\%#\@ + augroup END +endfunction + +function! s:EnableShowBadWhitespace() + call s:SetBufferSpecificPatterns() + if !exists("b:bad_whitespace_show") + if &modifiable + let b:bad_whitespace_show = s:GetDisplayOnOffDefaultForFiletype() + else + let b:bad_whitespace_show = 0 + endif endif if b:bad_whitespace_show - call HideBadWhitespace(1) + call ShowBadWhitespace() else - call ShowBadWhitespace(1) + call HideBadWhitespace() endif endfunction -autocmd BufWinEnter,WinEnter,FileType * call EnableShowBadWhitespace() +function! s:ToggleBadWhitespace() + if b:bad_whitespace_show + call HideBadWhitespace() + else + call ShowBadWhitespace() + endif +endfunction function! s:EraseBadWhitespace(line1,line2) let l:save_cursor = getpos(".") - silent! execute ':' . a:line1 . ',' . a:line2 . 's/\s\+$//' + silent! execute ':' . a:line1 . ',' . a:line2 + \ . 's/' . s:GetBadWhitespacePattern(0) . '//' call setpos('.', l:save_cursor) endfunction " Run :EraseBadWhitespace to remove end of line white space. -command! -range=% EraseBadWhitespace call EraseBadWhitespace(,) -command! ShowBadWhitespace call ShowBadWhitespace(1) -command! HideBadWhitespace call HideBadWhitespace(1) +command! -range=% EraseBadWhitespace + \ call EraseBadWhitespace(,) +command! ShowBadWhitespace call ShowBadWhitespace() +command! HideBadWhitespace call HideBadWhitespace() command! ToggleBadWhitespace call ToggleBadWhitespace() +command! SetSearchPatternToBadWhitespace + \ let @/ = GetBadWhitespacePattern(0)