1" Vim indent file 2" Language: Pascal 3" Maintainer: Neil Carter <[email protected]> 4" Created: 2004 Jul 13 5" Last Change: 2017 Jun 13 6" 7" This is version 2.0, a complete rewrite. 8" 9" For further documentation, see http://psy.swansea.ac.uk/staff/carter/vim/ 10 11 12if exists("b:did_indent") 13 finish 14endif 15let b:did_indent = 1 16 17setlocal indentexpr=GetPascalIndent(v:lnum) 18setlocal indentkeys& 19setlocal indentkeys+==end;,==const,==type,==var,==begin,==repeat,==until,==for 20setlocal indentkeys+==program,==function,==procedure,==object,==private 21setlocal indentkeys+==record,==if,==else,==case 22 23if exists("*GetPascalIndent") 24 finish 25endif 26 27 28function! s:GetPrevNonCommentLineNum( line_num ) 29 30 " Skip lines starting with a comment 31 let SKIP_LINES = '^\s*\(\((\*\)\|\(\*\ \)\|\(\*)\)\|{\|}\)' 32 33 let nline = a:line_num 34 while nline > 0 35 let nline = prevnonblank(nline-1) 36 if getline(nline) !~? SKIP_LINES 37 break 38 endif 39 endwhile 40 41 return nline 42endfunction 43 44 45function! s:PurifyCode( line_num ) 46 " Strip any trailing comments and whitespace 47 let pureline = 'TODO' 48 return pureline 49endfunction 50 51 52function! GetPascalIndent( line_num ) 53 54 " Line 0 always goes at column 0 55 if a:line_num == 0 56 return 0 57 endif 58 59 let this_codeline = getline( a:line_num ) 60 61 62 " SAME INDENT 63 64 " Middle of a three-part comment 65 if this_codeline =~ '^\s*\*' 66 return indent( a:line_num - 1) 67 endif 68 69 70 " COLUMN 1 ALWAYS 71 72 " Last line of the program 73 if this_codeline =~ '^\s*end\.' 74 return 0 75 endif 76 77 " Compiler directives, allowing "(*" and "{" 78 "if this_codeline =~ '^\s*\({\|(\*\)$\(IFDEF\|IFNDEF\|ELSE\|ENDIF\)' 79 if this_codeline =~ '^\s*\({\|(\*\)\$' 80 return 0 81 endif 82 83 " section headers 84 if this_codeline =~ '^\s*\(program\|procedure\|function\|type\)\>' 85 return 0 86 endif 87 88 " Subroutine separators, lines ending with "const" or "var" 89 if this_codeline =~ '^\s*\((\*\ _\+\ \*)\|\(const\|var\)\)$' 90 return 0 91 endif 92 93 94 " OTHERWISE, WE NEED TO LOOK FURTHER BACK... 95 96 let prev_codeline_num = s:GetPrevNonCommentLineNum( a:line_num ) 97 let prev_codeline = getline( prev_codeline_num ) 98 let indnt = indent( prev_codeline_num ) 99 100 101 " INCREASE INDENT 102 103 " If the PREVIOUS LINE ended in these items, always indent 104 if prev_codeline =~ '\<\(type\|const\|var\)$' 105 return indnt + shiftwidth() 106 endif 107 108 if prev_codeline =~ '\<repeat$' 109 if this_codeline !~ '^\s*until\>' 110 return indnt + shiftwidth() 111 else 112 return indnt 113 endif 114 endif 115 116 if prev_codeline =~ '\<\(begin\|record\)$' 117 if this_codeline !~ '^\s*end\>' 118 return indnt + shiftwidth() 119 else 120 return indnt 121 endif 122 endif 123 124 " If the PREVIOUS LINE ended with these items, indent if not 125 " followed by "begin" 126 if prev_codeline =~ '\<\(\|else\|then\|do\)$' || prev_codeline =~ ':$' 127 if this_codeline !~ '^\s*begin\>' 128 return indnt + shiftwidth() 129 else 130 " If it does start with "begin" then keep the same indent 131 "return indnt + shiftwidth() 132 return indnt 133 endif 134 endif 135 136 " Inside a parameter list (i.e. a "(" without a ")"). ???? Considers 137 " only the line before the current one. TODO: Get it working for 138 " parameter lists longer than two lines. 139 if prev_codeline =~ '([^)]\+$' 140 return indnt + shiftwidth() 141 endif 142 143 144 " DECREASE INDENT 145 146 " Lines starting with "else", but not following line ending with 147 " "end". 148 if this_codeline =~ '^\s*else\>' && prev_codeline !~ '\<end$' 149 return indnt - shiftwidth() 150 endif 151 152 " Lines after a single-statement branch/loop. 153 " Two lines before ended in "then", "else", or "do" 154 " Previous line didn't end in "begin" 155 let prev2_codeline_num = s:GetPrevNonCommentLineNum( prev_codeline_num ) 156 let prev2_codeline = getline( prev2_codeline_num ) 157 if prev2_codeline =~ '\<\(then\|else\|do\)$' && prev_codeline !~ '\<begin$' 158 " If the next code line after a single statement branch/loop 159 " starts with "end", "except" or "finally", we need an 160 " additional unindentation. 161 if this_codeline =~ '^\s*\(end;\|except\|finally\|\)$' 162 " Note that we don't return from here. 163 return indnt - 2 * shiftwidth() 164 endif 165 return indnt - shiftwidth() 166 endif 167 168 " Lines starting with "until" or "end". This rule must be overridden 169 " by the one for "end" after a single-statement branch/loop. In 170 " other words that rule should come before this one. 171 if this_codeline =~ '^\s*\(end\|until\)\>' 172 return indnt - shiftwidth() 173 endif 174 175 176 " MISCELLANEOUS THINGS TO CATCH 177 178 " Most "begin"s will have been handled by now. Any remaining 179 " "begin"s on their own line should go in column 1. 180 if this_codeline =~ '^\s*begin$' 181 return 0 182 endif 183 184 185" ____________________________________________________________________ 186" Object/Borland Pascal/Delphi Extensions 187" 188" Note that extended-pascal is handled here, unless it is simpler to 189" handle them in the standard-pascal section above. 190 191 192 " COLUMN 1 ALWAYS 193 194 " section headers at start of line. 195 if this_codeline =~ '^\s*\(interface\|implementation\|uses\|unit\)\>' 196 return 0 197 endif 198 199 200 " INDENT ONCE 201 202 " If the PREVIOUS LINE ended in these items, always indent. 203 if prev_codeline =~ '^\s*\(unit\|uses\|try\|except\|finally\|private\|protected\|public\|published\)$' 204 return indnt + shiftwidth() 205 endif 206 207 " ???? Indent "procedure" and "functions" if they appear within an 208 " class/object definition. But that means overriding standard-pascal 209 " rule where these words always go in column 1. 210 211 212 " UNINDENT ONCE 213 214 if this_codeline =~ '^\s*\(except\|finally\)$' 215 return indnt - shiftwidth() 216 endif 217 218 if this_codeline =~ '^\s*\(private\|protected\|public\|published\)$' 219 return indnt - shiftwidth() 220 endif 221 222 223" ____________________________________________________________________ 224 225 " If nothing changed, return same indent. 226 return indnt 227endfunction 228 229