summaryrefslogtreecommitdiffstats
path: root/autoload/ShowTrailingWhitespace.vim
blob: cb7c5a888781ba81a32bd4b3b656fea318de1346 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
" ShowTrailingWhitespace.vim: Detect unwanted whitespace at the end of lines.
"
" DEPENDENCIES:
"
" Copyright: (C) 2012 Ingo Karkat
"   The VIM LICENSE applies to this script; see ':help copyright'.
"
" Maintainer:	Ingo Karkat <ingo@karkat.de>
"
" REVISION	DATE		REMARKS
"   1.00.004	06-Mar-2012	Toggle to value 2 when enabled but the buffer is
"				filtered from showing trailing whitespace.
"	003	05-Mar-2012	Introduce g:ShowTrailingWhitespace_FilterFunc to
"				disable highlighting for non-persisted and
"				nomodifiable buffers.
"	002	02-Mar-2012	Introduce b:ShowTrailingWhitespace_ExtraPattern
"				to be able to avoid some matches (e.g. a <Space>
"				in column 1 in a buffer with filetype=diff) and
"				ShowTrailingWhitespace#SetLocalExtraPattern() to
"				set it.
"	001	25-Feb-2012	file creation
let s:save_cpo = &cpo
set cpo&vim

function! ShowTrailingWhitespace#Pattern( isInsertMode )
    return (exists('b:ShowTrailingWhitespace_ExtraPattern') ? b:ShowTrailingWhitespace_ExtraPattern : '') .
    \	(a:isInsertMode ? '\s\+\%#\@<!$' : '\s\+$')
endfunction
let s:HlGroupName = 'ShowTrailingWhitespace'
function! s:UpdateMatch( isInsertMode )
    let l:pattern = ShowTrailingWhitespace#Pattern(a:isInsertMode)
    if exists('w:ShowTrailingWhitespace_Match')
	" Info: matchadd() does not consider the 'magic' (it's always on),
	" 'ignorecase' and 'smartcase' settings.
	silent! call matchdelete(w:ShowTrailingWhitespace_Match)
	call matchadd(s:HlGroupName, pattern, -1, w:ShowTrailingWhitespace_Match)
    else
	let w:ShowTrailingWhitespace_Match =  matchadd(s:HlGroupName, pattern)
    endif
endfunction
function! s:DeleteMatch()
    if exists('w:ShowTrailingWhitespace_Match')
	silent! call matchdelete(w:ShowTrailingWhitespace_Match)
	unlet w:ShowTrailingWhitespace_Match
    endif
endfunction

function! s:DetectAll()
    let l:currentWinNr = winnr()

    " By entering a window, its height is potentially increased from 0 to 1 (the
    " minimum for the current window). To avoid any modification, save the window
    " sizes and restore them after visiting all windows.
    let l:originalWindowLayout = winrestcmd()

    noautocmd windo call ShowTrailingWhitespace#Detect(0)
    execute l:currentWinNr . 'wincmd w'
    silent! execute l:originalWindowLayout
endfunction

function! ShowTrailingWhitespace#IsSet()
    return (exists('b:ShowTrailingWhitespace') ? b:ShowTrailingWhitespace : g:ShowTrailingWhitespace)
endfunction
function! ShowTrailingWhitespace#NotFiltered()
    let l:Filter = (exists('b:ShowTrailingWhitespace_FilterFunc') ? b:ShowTrailingWhitespace_FilterFunc : g:ShowTrailingWhitespace_FilterFunc)
    return (empty(l:Filter) ? 1 : call(l:Filter, []))
endfunction

function! ShowTrailingWhitespace#Detect( isInsertMode )
    if ShowTrailingWhitespace#IsSet() && ShowTrailingWhitespace#NotFiltered()
	call s:UpdateMatch(a:isInsertMode)
    else
	call s:DeleteMatch()
    endif
endfunction

" The showing of trailing whitespace be en-/disabled globally or only for a particular buffer.
function! ShowTrailingWhitespace#Set( isTurnOn, isGlobal )
    if a:isGlobal
	let g:ShowTrailingWhitespace = a:isTurnOn
	call s:DetectAll()
    else
	let b:ShowTrailingWhitespace = a:isTurnOn
	call ShowTrailingWhitespace#Detect(0)
    endif
endfunction
function! ShowTrailingWhitespace#Reset()
    unlet! b:ShowTrailingWhitespace
    call ShowTrailingWhitespace#Detect(0)
endfunction
function! ShowTrailingWhitespace#Toggle( isGlobal )
    if a:isGlobal
	let l:newState = ! g:ShowTrailingWhitespace
    else
	if ShowTrailingWhitespace#NotFiltered()
	    let l:newState = ! ShowTrailingWhitespace#IsSet()
	else
	    let l:newState = (ShowTrailingWhitespace#IsSet() > 1 ? 0 : 2)
	endif
    endif

    call ShowTrailingWhitespace#Set(l:newState, a:isGlobal)
endfunction

function! ShowTrailingWhitespace#SetLocalExtraPattern( pattern )
    let b:ShowTrailingWhitespace_ExtraPattern = a:pattern
    call s:DetectAll()
endfunction

" vim: set ts=8 sts=4 sw=4 noexpandtab ff=unix fdm=syntax :