comparison runtime/indent/sh.vim @ 39:c16898406ff2

synchorinize version 7.3.081
author one@zeus.cr.ie.u-ryukyu.ac.jp
date Fri, 17 Dec 2010 17:43:06 +0900
parents 76efa0be13f1
children
comparison
equal deleted inserted replaced
38:e06a1cd7230d 39:c16898406ff2
1 " Vim indent file 1 " Vim indent file
2 " Language: Shell Script 2 " Language: Shell Script
3 " Maintainer: Nikolai Weibull <now@bitwi.se> 3 " Maintainer: Nikolai Weibull <now@bitwi.se>
4 " Latest Revision: 2006-04-19 4 " Latest Revision: 2010-01-06
5 5
6 if exists("b:did_indent") 6 if exists("b:did_indent")
7 finish 7 finish
8 endif 8 endif
9 let b:did_indent = 1 9 let b:did_indent = 1
10 10
11 setlocal indentexpr=GetShIndent() 11 setlocal indentexpr=GetShIndent()
12 setlocal indentkeys+==then,=do,=else,=elif,=esac,=fi,=fin,=fil,=done 12 setlocal indentkeys+=0=then,0=do,0=else,0=elif,0=fi,0=esac,0=done,),0=;;,0=;&
13 setlocal indentkeys+=0=fin,0=fil,0=fip,0=fir,0=fix
13 setlocal indentkeys-=:,0# 14 setlocal indentkeys-=:,0#
15 setlocal nosmartindent
14 16
15 if exists("*GetShIndent") 17 if exists("*GetShIndent")
16 finish 18 finish
17 endif 19 endif
18 20
19 let s:cpo_save = &cpo 21 let s:cpo_save = &cpo
20 set cpo&vim 22 set cpo&vim
21 23
22 function GetShIndent() 24 function s:buffer_shiftwidth()
25 return &shiftwidth
26 endfunction
27
28 let s:sh_indent_defaults = {
29 \ 'default': function('s:buffer_shiftwidth'),
30 \ 'continuation-line': function('s:buffer_shiftwidth'),
31 \ 'case-labels': function('s:buffer_shiftwidth'),
32 \ 'case-statements': function('s:buffer_shiftwidth'),
33 \ 'case-breaks': 0 }
34
35 function! s:indent_value(option)
36 let Value = exists('b:sh_indent_options')
37 \ && has_key(b:sh_indent_options, a:option) ?
38 \ b:sh_indent_options[a:option] :
39 \ s:sh_indent_defaults[a:option]
40 if type(Value) == type(function('type'))
41 return Value()
42 endif
43 return Value
44 endfunction
45
46 function! GetShIndent()
23 let lnum = prevnonblank(v:lnum - 1) 47 let lnum = prevnonblank(v:lnum - 1)
24 if lnum == 0 48 if lnum == 0
25 return 0 49 return 0
26 endif 50 endif
27 51
28 " Add a 'shiftwidth' after if, while, else, case, until, for, function() 52 let pnum = prevnonblank(lnum - 1)
29 " Skip if the line also contains the closure for the above 53
30 let ind = indent(lnum) 54 let ind = indent(lnum)
31 let line = getline(lnum) 55 let line = getline(lnum)
32 if line =~ '^\s*\(if\|then\|do\|else\|elif\|case\|while\|until\|for\)\>' 56 if line =~ '^\s*\%(if\|then\|do\|else\|elif\|case\|while\|until\|for\|select\)\>'
33 \ || line =~ '^\s*\<\k\+\>\s*()\s*{' 57 if line !~ '\<\%(fi\|esac\|done\)\>\s*\%(#.*\)\=$'
34 \ || line =~ '^\s*{' 58 let ind += s:indent_value('default')
35 if line !~ '\(esac\|fi\|done\)\>\s*$' && line !~ '}\s*$'
36 let ind = ind + &sw
37 endif 59 endif
60 elseif s:is_case_label(line, pnum)
61 if !s:is_case_ended(line)
62 let ind += s:indent_value('case-statements')
63 endif
64 elseif line =~ '^\s*\<\k\+\>\s*()\s*{' || line =~ '^\s*{'
65 if line !~ '}\s*\%(#.*\)\=$'
66 let ind += s:indent_value('default')
67 endif
68 elseif s:is_continuation_line(line)
69 if pnum == 0 || !s:is_continuation_line(getline(pnum))
70 let ind += s:indent_value('continuation-line')
71 endif
72 elseif pnum != 0 && s:is_continuation_line(getline(pnum))
73 let ind = indent(s:find_continued_lnum(pnum))
38 endif 74 endif
39 75
40 " Subtract a 'shiftwidth' on a then, do, else, esac, fi, done 76 let pine = line
41 " Retain the indentation level if line matches fin (for find)
42 let line = getline(v:lnum) 77 let line = getline(v:lnum)
43 if (line =~ '^\s*\(then\|do\|else\|elif\|esac\|fi\|done\)\>' || line =~ '^\s*}') 78 if line =~ '^\s*\%(then\|do\|else\|elif\|fi\|done\)\>' || line =~ '^\s*}'
44 \ && line !~ '^\s*fi[ln]\>' 79 let ind -= s:indent_value('default')
45 let ind = ind - &sw 80 elseif line =~ '^\s*esac\>'
81 let ind -= (s:is_case_label(pine, lnum) && s:is_case_ended(pine) ?
82 \ 0 : s:indent_value('case-statements')) +
83 \ s:indent_value('case-labels')
84 if s:is_case_break(pine)
85 let ind += s:indent_value('case-breaks')
86 endif
87 elseif s:is_case_label(line, lnum)
88 if s:is_case(pine)
89 let ind = indent(lnum) + s:indent_value('case-labels')
90 else
91 let ind -= s:indent_value('case-statements') - s:indent_value('case-breaks')
92 endif
93 elseif s:is_case_break(line)
94 let ind -= s:indent_value('case-breaks')
46 endif 95 endif
47 96
48 return ind 97 return ind
49 endfunction 98 endfunction
50 99
100 function! s:is_continuation_line(line)
101 return a:line =~ '\%(\%(^\|[^\\]\)\\\|&&\|||\)$'
102 endfunction
103
104 function! s:find_continued_lnum(lnum)
105 let i = a:lnum
106 while i > 1 && s:is_continuation_line(getline(i - 1))
107 let i -= 1
108 endwhile
109 return i
110 endfunction
111
112 function! s:is_case_label(line, pnum)
113 if a:line !~ '^\s*(\=.*)'
114 return 0
115 endif
116
117 if a:pnum > 0
118 let pine = getline(a:pnum)
119 if !(s:is_case(pine) || s:is_case_ended(pine))
120 return 0
121 endif
122 endif
123
124 let suffix = substitute(a:line, '^\s*(\=', "", "")
125 let nesting = 0
126 let i = 0
127 let n = strlen(suffix)
128 while i < n
129 let c = suffix[i]
130 let i += 1
131 if c == '\\'
132 let i += 1
133 elseif c == '('
134 let nesting += 1
135 elseif c == ')'
136 if nesting == 0
137 return 1
138 endif
139 let nesting -= 1
140 endif
141 endwhile
142 return 0
143 endfunction
144
145 function! s:is_case(line)
146 return a:line =~ '^\s*case\>'
147 endfunction
148
149 function! s:is_case_break(line)
150 return a:line =~ '^\s*;[;&]'
151 endfunction
152
153 function! s:is_case_ended(line)
154 return s:is_case_break(a:line) || a:line =~ ';[;&]\s*\%(#.*\)\=$'
155 endfunction
156
51 let &cpo = s:cpo_save 157 let &cpo = s:cpo_save
52 unlet s:cpo_save 158 unlet s:cpo_save