diff options
| author | Ben Beltran <ben@freshout.us> | 2012-10-08 11:44:10 -0500 |
|---|---|---|
| committer | Ben Beltran <ben@freshout.us> | 2012-10-08 11:44:10 -0500 |
| commit | 0d23b6e515a01a5782532351821ebfa11f3d6cf2 (patch) | |
| tree | aa395b7e50ccb533d6b48b809016ac06f2d5bc8c /vim/indent | |
| parent | a91731eac872b7837c2821341db5888702125cef (diff) | |
Add vim again :)
Diffstat (limited to 'vim/indent')
| -rw-r--r-- | vim/indent/coffee.vim | 322 | ||||
| -rw-r--r-- | vim/indent/cucumber.vim | 74 | ||||
| -rw-r--r-- | vim/indent/gitconfig.vim | 36 | ||||
| -rw-r--r-- | vim/indent/haml.vim | 73 | ||||
| -rw-r--r-- | vim/indent/javascript.vim | 328 | ||||
| -rw-r--r-- | vim/indent/puppet.vim | 76 | ||||
| -rw-r--r-- | vim/indent/sass.vim | 40 | ||||
| -rw-r--r-- | vim/indent/scala.vim | 83 | ||||
| -rw-r--r-- | vim/indent/scss.vim | 12 |
9 files changed, 1044 insertions, 0 deletions
diff --git a/vim/indent/coffee.vim b/vim/indent/coffee.vim new file mode 100644 index 0000000..f60cfdd --- /dev/null +++ b/vim/indent/coffee.vim @@ -0,0 +1,322 @@ +" Language: CoffeeScript +" Maintainer: Mick Koch <kchmck@gmail.com> +" URL: http://github.com/kchmck/vim-coffee-script +" License: WTFPL + +if exists("b:did_indent") + finish +endif + +let b:did_indent = 1 + +setlocal autoindent +setlocal indentexpr=GetCoffeeIndent(v:lnum) +" Make sure GetCoffeeIndent is run when these are typed so they can be +" indented or outdented. +setlocal indentkeys+=0],0),0.,=else,=when,=catch,=finally + +" Only define the function once. +if exists("*GetCoffeeIndent") + finish +endif + +" Keywords to indent after +let s:INDENT_AFTER_KEYWORD = '^\%(if\|unless\|else\|for\|while\|until\|' +\ . 'loop\|switch\|when\|try\|catch\|finally\|' +\ . 'class\)\>' + +" Operators to indent after +let s:INDENT_AFTER_OPERATOR = '\%([([{:=]\|[-=]>\)$' + +" Keywords and operators that continue a line +let s:CONTINUATION = '\<\%(is\|isnt\|and\|or\)\>$' +\ . '\|' +\ . '\%(-\@<!-\|+\@<!+\|<\|[-=]\@<!>\|\*\|/\@<!/\|%\||\|' +\ . '&\|,\|\.\@<!\.\)$' + +" Operators that block continuation indenting +let s:CONTINUATION_BLOCK = '[([{:=]$' + +" A continuation dot access +let s:DOT_ACCESS = '^\.' + +" Keywords to outdent after +let s:OUTDENT_AFTER = '^\%(return\|break\|continue\|throw\)\>' + +" A compound assignment like `... = if ...` +let s:COMPOUND_ASSIGNMENT = '[:=]\s*\%(if\|unless\|for\|while\|until\|' +\ . 'switch\|try\|class\)\>' + +" A postfix condition like `return ... if ...`. +let s:POSTFIX_CONDITION = '\S\s\+\zs\<\%(if\|unless\)\>' + +" A single-line else statement like `else ...` but not `else if ... +let s:SINGLE_LINE_ELSE = '^else\s\+\%(\<\%(if\|unless\)\>\)\@!' + +" Max lines to look back for a match +let s:MAX_LOOKBACK = 50 + +" Syntax names for strings +let s:SYNTAX_STRING = 'coffee\%(String\|AssignString\|Embed\|Regex\|Heregex\|' +\ . 'Heredoc\)' + +" Syntax names for comments +let s:SYNTAX_COMMENT = 'coffee\%(Comment\|BlockComment\|HeregexComment\)' + +" Syntax names for strings and comments +let s:SYNTAX_STRING_COMMENT = s:SYNTAX_STRING . '\|' . s:SYNTAX_COMMENT + +" Get the linked syntax name of a character. +function! s:SyntaxName(linenum, col) + return synIDattr(synID(a:linenum, a:col, 1), 'name') +endfunction + +" Check if a character is in a comment. +function! s:IsComment(linenum, col) + return s:SyntaxName(a:linenum, a:col) =~ s:SYNTAX_COMMENT +endfunction + +" Check if a character is in a string. +function! s:IsString(linenum, col) + return s:SyntaxName(a:linenum, a:col) =~ s:SYNTAX_STRING +endfunction + +" Check if a character is in a comment or string. +function! s:IsCommentOrString(linenum, col) + return s:SyntaxName(a:linenum, a:col) =~ s:SYNTAX_STRING_COMMENT +endfunction + +" Check if a whole line is a comment. +function! s:IsCommentLine(linenum) + " Check the first non-whitespace character. + return s:IsComment(a:linenum, indent(a:linenum) + 1) +endfunction + +" Repeatedly search a line for a regex until one is found outside a string or +" comment. +function! s:SmartSearch(linenum, regex) + " Start at the first column. + let col = 0 + + " Search until there are no more matches, unless a good match is found. + while 1 + call cursor(a:linenum, col + 1) + let [_, col] = searchpos(a:regex, 'cn', a:linenum) + + " No more matches. + if !col + break + endif + + if !s:IsCommentOrString(a:linenum, col) + return 1 + endif + endwhile + + " No good match found. + return 0 +endfunction + +" Skip a match if it's in a comment or string, is a single-line statement that +" isn't adjacent, or is a postfix condition. +function! s:ShouldSkip(startlinenum, linenum, col) + if s:IsCommentOrString(a:linenum, a:col) + return 1 + endif + + " Check for a single-line statement that isn't adjacent. + if s:SmartSearch(a:linenum, '\<then\>') && a:startlinenum - a:linenum > 1 + return 1 + endif + + if s:SmartSearch(a:linenum, s:POSTFIX_CONDITION) && + \ !s:SmartSearch(a:linenum, s:COMPOUND_ASSIGNMENT) + return 1 + endif + + return 0 +endfunction + +" Find the farthest line to look back to, capped to line 1 (zero and negative +" numbers cause bad things). +function! s:MaxLookback(startlinenum) + return max([1, a:startlinenum - s:MAX_LOOKBACK]) +endfunction + +" Get the skip expression for searchpair(). +function! s:SkipExpr(startlinenum) + return "s:ShouldSkip(" . a:startlinenum . ", line('.'), col('.'))" +endfunction + +" Search for pairs of text. +function! s:SearchPair(start, end) + " The cursor must be in the first column for regexes to match. + call cursor(0, 1) + + let startlinenum = line('.') + + " Don't need the W flag since MaxLookback caps the search to line 1. + return searchpair(a:start, '', a:end, 'bcn', + \ s:SkipExpr(startlinenum), + \ s:MaxLookback(startlinenum)) +endfunction + +" Try to find a previous matching line. +function! s:GetMatch(curline) + let firstchar = a:curline[0] + + if firstchar == '}' + return s:SearchPair('{', '}') + elseif firstchar == ')' + return s:SearchPair('(', ')') + elseif firstchar == ']' + return s:SearchPair('\[', '\]') + elseif a:curline =~ '^else\>' + return s:SearchPair('\<\%(if\|unless\|when\)\>', '\<else\>') + elseif a:curline =~ '^catch\>' + return s:SearchPair('\<try\>', '\<catch\>') + elseif a:curline =~ '^finally\>' + return s:SearchPair('\<try\>', '\<finally\>') + endif + + return 0 +endfunction + +" Get the nearest previous line that isn't a comment. +function! s:GetPrevNormalLine(startlinenum) + let curlinenum = a:startlinenum + + while curlinenum > 0 + let curlinenum = prevnonblank(curlinenum - 1) + + if !s:IsCommentLine(curlinenum) + return curlinenum + endif + endwhile + + return 0 +endfunction + +" Try to find a comment in a line. +function! s:FindComment(linenum) + let col = 0 + + while 1 + call cursor(a:linenum, col + 1) + let [_, col] = searchpos('#', 'cn', a:linenum) + + if !col + break + endif + + if s:IsComment(a:linenum, col) + return col + endif + endwhile + + return 0 +endfunction + +" Get a line without comments or surrounding whitespace. +function! s:GetTrimmedLine(linenum) + let comment = s:FindComment(a:linenum) + let line = getline(a:linenum) + + if comment + " Subtract 1 to get to the column before the comment and another 1 for + " zero-based indexing. + let line = line[:comment - 2] + endif + + return substitute(substitute(line, '^\s\+', '', ''), + \ '\s\+$', '', '') +endfunction + +function! s:GetCoffeeIndent(curlinenum) + let prevlinenum = s:GetPrevNormalLine(a:curlinenum) + + " Don't do anything if there's no previous line. + if !prevlinenum + return -1 + endif + + let curline = s:GetTrimmedLine(a:curlinenum) + + " Try to find a previous matching statement. This handles outdenting. + let matchlinenum = s:GetMatch(curline) + + if matchlinenum + return indent(matchlinenum) + endif + + " Try to find a matching `when`. + if curline =~ '^when\>' && !s:SmartSearch(prevlinenum, '\<switch\>') + let linenum = a:curlinenum + + while linenum > 0 + let linenum = s:GetPrevNormalLine(linenum) + + if getline(linenum) =~ '^\s*when\>' + return indent(linenum) + endif + endwhile + + return -1 + endif + + let prevline = s:GetTrimmedLine(prevlinenum) + let previndent = indent(prevlinenum) + + " Always indent after these operators. + if prevline =~ s:INDENT_AFTER_OPERATOR + return previndent + &shiftwidth + endif + + " Indent after a continuation if it's the first. + if prevline =~ s:CONTINUATION + let prevprevlinenum = s:GetPrevNormalLine(prevlinenum) + let prevprevline = s:GetTrimmedLine(prevprevlinenum) + + if prevprevline !~ s:CONTINUATION && prevprevline !~ s:CONTINUATION_BLOCK + return previndent + &shiftwidth + endif + + return -1 + endif + + " Indent after these keywords and compound assignments if they aren't a + " single-line statement. + if prevline =~ s:INDENT_AFTER_KEYWORD || prevline =~ s:COMPOUND_ASSIGNMENT + if !s:SmartSearch(prevlinenum, '\<then\>') && prevline !~ s:SINGLE_LINE_ELSE + return previndent + &shiftwidth + endif + + return -1 + endif + + " Indent a dot access if it's the first. + if curline =~ s:DOT_ACCESS && prevline !~ s:DOT_ACCESS + return previndent + &shiftwidth + endif + + " Outdent after these keywords if they don't have a postfix condition or are + " a single-line statement. + if prevline =~ s:OUTDENT_AFTER + if !s:SmartSearch(prevlinenum, s:POSTFIX_CONDITION) || + \ s:SmartSearch(prevlinenum, '\<then\>') + return previndent - &shiftwidth + endif + endif + + " No indenting or outdenting is needed. + return -1 +endfunction + +" Wrap s:GetCoffeeIndent to keep the cursor position. +function! GetCoffeeIndent(curlinenum) + let oldcursor = getpos('.') + let indent = s:GetCoffeeIndent(a:curlinenum) + call setpos('.', oldcursor) + + return indent +endfunction diff --git a/vim/indent/cucumber.vim b/vim/indent/cucumber.vim new file mode 100644 index 0000000..802d224 --- /dev/null +++ b/vim/indent/cucumber.vim @@ -0,0 +1,74 @@ +" Vim indent file +" Language: Cucumber +" Maintainer: Tim Pope <vimNOSPAM@tpope.org> +" Last Change: 2010 May 21 + +if exists("b:did_indent") + finish +endif +let b:did_indent = 1 + +setlocal autoindent +setlocal indentexpr=GetCucumberIndent() +setlocal indentkeys=o,O,*<Return>,<:>,0<Bar>,0#,=,!^F + +let b:undo_indent = 'setl ai< inde< indk<' + +" Only define the function once. +if exists("*GetCucumberIndent") + finish +endif + +function! s:syn(lnum) + return synIDattr(synID(a:lnum,1+indent(a:lnum),1),'name') +endfunction + +function! GetCucumberIndent() + let line = getline(prevnonblank(v:lnum-1)) + let cline = getline(v:lnum) + let nline = getline(nextnonblank(v:lnum+1)) + let syn = s:syn(prevnonblank(v:lnum-1)) + let csyn = s:syn(v:lnum) + let nsyn = s:syn(nextnonblank(v:lnum+1)) + if csyn ==# 'cucumberFeature' || cline =~# '^\s*Feature:' + " feature heading + return 0 + elseif csyn ==# 'cucumberExamples' || cline =~# '^\s*\%(Examples\|Scenarios\):' + " examples heading + return 2 * &sw + elseif csyn =~# '^cucumber\%(Background\|Scenario\|ScenarioOutline\)$' || cline =~# '^\s*\%(Background\|Scenario\|Scenario Outline\):' + " background, scenario or outline heading + return &sw + elseif syn ==# 'cucumberFeature' || line =~# '^\s*Feature:' + " line after feature heading + return &sw + elseif syn ==# 'cucumberExamples' || line =~# '^\s*\%(Examples\|Scenarios\):' + " line after examples heading + return 3 * &sw + elseif syn =~# '^cucumber\%(Background\|Scenario\|ScenarioOutline\)$' || line =~# '^\s*\%(Background\|Scenario\|Scenario Outline\):' + " line after background, scenario or outline heading + return 2 * &sw + elseif cline =~# '^\s*[@#]' && (nsyn == 'cucumberFeature' || nline =~# '^\s*Feature:' || indent(prevnonblank(v:lnum-1)) <= 0) + " tag or comment before a feature heading + return 0 + elseif cline =~# '^\s*@' + " other tags + return &sw + elseif cline =~# '^\s*[#|]' && line =~# '^\s*|' + " mid-table + " preserve indent + return indent(prevnonblank(v:lnum-1)) + elseif cline =~# '^\s*|' && line =~# '^\s*[^|]' + " first line of a table, relative indent + return indent(prevnonblank(v:lnum-1)) + &sw + elseif cline =~# '^\s*[^|]' && line =~# '^\s*|' + " line after a table, relative unindent + return indent(prevnonblank(v:lnum-1)) - &sw + elseif cline =~# '^\s*#' && getline(v:lnum-1) =~ '^\s*$' && (nsyn =~# '^cucumber\%(Background\|Scenario\|ScenarioOutline\)$' || nline =~# '^\s*\%(Background\|Scenario\|Scenario Outline\):') + " comments on scenarios + return &sw + endif + return indent(prevnonblank(v:lnum-1)) +endfunction + +" vim:set sts=2 sw=2: diff --git a/vim/indent/gitconfig.vim b/vim/indent/gitconfig.vim new file mode 100644 index 0000000..e190fc3 --- /dev/null +++ b/vim/indent/gitconfig.vim @@ -0,0 +1,36 @@ +" Vim indent file +" Language: git config file +" Maintainer: Tim Pope <vimNOSPAM@tpope.org> + +if exists("b:did_indent") + finish +endif +let b:did_indent = 1 + +setlocal autoindent +setlocal indentexpr=GetGitconfigIndent() +setlocal indentkeys=o,O,*<Return>,0[,],0;,0#,=,!^F + +let b:undo_indent = 'setl ai< inde< indk<' + +" Only define the function once. +if exists("*GetGitconfigIndent") + finish +endif + +function! GetGitconfigIndent() + let line = getline(prevnonblank(v:lnum-1)) + let cline = getline(v:lnum) + if line =~ '\\\@<!\%(\\\\\)*\\$' + " odd number of slashes, in a line continuation + return 2 * &sw + elseif cline =~ '^\s*\[' + return 0 + elseif cline =~ '^\s*\a' + return &sw + elseif cline == '' && line =~ '^\[' + return &sw + else + return -1 + endif +endfunction diff --git a/vim/indent/haml.vim b/vim/indent/haml.vim new file mode 100644 index 0000000..58c0307 --- /dev/null +++ b/vim/indent/haml.vim @@ -0,0 +1,73 @@ +" Vim indent file +" Language: Haml +" Maintainer: Tim Pope <vimNOSPAM@tpope.org> +" Last Change: 2010 May 21 + +if exists("b:did_indent") + finish +endif +runtime! indent/ruby.vim +unlet! b:did_indent +let b:did_indent = 1 + +setlocal autoindent sw=2 et +setlocal indentexpr=GetHamlIndent() +setlocal indentkeys=o,O,*<Return>,},],0),!^F,=end,=else,=elsif,=rescue,=ensure,=when + +" Only define the function once. +if exists("*GetHamlIndent") + finish +endif + +let s:attributes = '\%({.\{-\}}\|\[.\{-\}\]\)' +let s:tag = '\%([%.#][[:alnum:]_-]\+\|'.s:attributes.'\)*[<>]*' + +if !exists('g:haml_self_closing_tags') + let g:haml_self_closing_tags = 'meta|link|img|hr|br' +endif + +function! GetHamlIndent() + let lnum = prevnonblank(v:lnum-1) + if lnum == 0 + return 0 + endif + let line = substitute(getline(lnum),'\s\+$','','') + let cline = substitute(substitute(getline(v:lnum),'\s\+$','',''),'^\s\+','','') + let lastcol = strlen(line) + let line = substitute(line,'^\s\+','','') + let indent = indent(lnum) + let cindent = indent(v:lnum) + if cline =~# '\v^-\s*%(elsif|else|when)>' + let indent = cindent < indent ? cindent : indent - &sw + endif + let increase = indent + &sw + if indent == indent(lnum) + let indent = cindent <= indent ? -1 : increase + endif + + let group = synIDattr(synID(lnum,lastcol,1),'name') + + if line =~ '^!!!' + return indent + elseif line =~ '^/\%(\[[^]]*\]\)\=$' + return increase + elseif group == 'hamlFilter' + return increase + elseif line =~ '^'.s:tag.'[&!]\=[=~-]\s*\%(\%(if\|else\|elsif\|unless\|case\|when\|while\|until\|for\|begin\|module\|class\|def\)\>\%(.*\<end\>\)\@!\|.*do\%(\s*|[^|]*|\)\=\s*$\)' + return increase + elseif line =~ '^'.s:tag.'[&!]\=[=~-].*,\s*$' + return increase + elseif line == '-#' + return increase + elseif group =~? '\v^(hamlSelfCloser)$' || line =~? '^%\v%('.g:haml_self_closing_tags.')>' + return indent + elseif group =~? '\v^%(hamlTag|hamlAttributesDelimiter|hamlObjectDelimiter|hamlClass|hamlId|htmlTagName|htmlSpecialTagName)$' + return increase + elseif synIDattr(synID(v:lnum,1,1),'name') ==? 'hamlRubyFilter' + return GetRubyIndent() + else + return indent + endif +endfunction + +" vim:set sw=2: diff --git a/vim/indent/javascript.vim b/vim/indent/javascript.vim new file mode 100644 index 0000000..b34deee --- /dev/null +++ b/vim/indent/javascript.vim @@ -0,0 +1,328 @@ +" Vim indent file +" Language: Javascript +" Maintainer: Darrick Wiebe <darrick at innatesoftware.com> +" URL: http://github.com/pangloss/vim-javascript +" Version: 1.0.0 +" Last Change: August 31, 2009 +" Acknowledgement: Based off of vim-ruby maintained by Nikolai Weibull http://vim-ruby.rubyforge.org + +" 0. Initialization {{{1 +" ================= + +" Only load this indent file when no other was loaded. +if exists("b:did_indent") + finish +endif +let b:did_indent = 1 + +setlocal nosmartindent + +" Now, set up our indentation expression and keys that trigger it. +setlocal indentexpr=GetJavascriptIndent() +setlocal indentkeys=0{,0},0),0],!^F,o,O,e + +" Only define the function once. +if exists("*GetJavascriptIndent") + finish +endif + +let s:cpo_save = &cpo +set cpo&vim + +" 1. Variables {{{1 +" ============ + +" Regex of syntax group names that are or delimit string or are comments. +let s:syng_strcom = 'javaScript\%(String\|RegexpString\|CommentTodo\|LineComment\|Comment\|DocComment\)' + +" Regex of syntax group names that are strings. +let s:syng_string = 'javaScript\%(RegexpString\)' + +" Regex of syntax group names that are strings or documentation. +let s:syng_stringdoc = 'javaScriptDocComment\|javaScriptComment' + +" Expression used to check whether we should skip a match with searchpair(). +let s:skip_expr = "synIDattr(synID(line('.'),col('.'),1),'name') =~ '".s:syng_strcom."'" + +let s:line_term = '\s*\%(\%(\/\/\).*\)\=$' + +" Regex that defines continuation lines, not including (, {, or [. +let s:continuation_regex = '\%([\\*+/.:]\|\%(<%\)\@<![=-]\|\W[|&?]\|||\|&&\)' . s:line_term + +" Regex that defines continuation lines. +" TODO: this needs to deal with if ...: and so on +let s:msl_regex = '\%([\\*+/.:([]\|\%(<%\)\@<![=-]\|\W[|&?]\|||\|&&\)' . s:line_term + +let s:one_line_scope_regex = '\<\%(if\|else\|for\|while\)\>[^{;]*' . s:line_term + +" Regex that defines blocks. +let s:block_regex = '\%({\)\s*\%(|\%([*@]\=\h\w*,\=\s*\)\%(,\s*[*@]\=\h\w*\)*|\)\=' . s:line_term + +" 2. Auxiliary Functions {{{1 +" ====================== + +" Check if the character at lnum:col is inside a string, comment, or is ascii. +function s:IsInStringOrComment(lnum, col) + return synIDattr(synID(a:lnum, a:col, 1), 'name') =~ s:syng_strcom +endfunction + +" Check if the character at lnum:col is inside a string. +function s:IsInString(lnum, col) + return synIDattr(synID(a:lnum, a:col, 1), 'name') =~ s:syng_string +endfunction + +" Check if the character at lnum:col is inside a string or documentation. +function s:IsInStringOrDocumentation(lnum, col) + return synIDattr(synID(a:lnum, a:col, 1), 'name') =~ s:syng_stringdoc +endfunction + +" Find line above 'lnum' that isn't empty, in a comment, or in a string. +function s:PrevNonBlankNonString(lnum) + let in_block = 0 + let lnum = prevnonblank(a:lnum) + while lnum > 0 + " Go in and out of blocks comments as necessary. + " If the line isn't empty (with opt. comment) or in a string, end search. + let line = getline(lnum) + if line =~ '/\*' + if in_block + let in_block = 0 + else + break + endif + elseif !in_block && line =~ '\*/' + let in_block = 1 + elseif !in_block && line !~ '^\s*\%(//\).*$' && !(s:IsInStringOrComment(lnum, 1) && s:IsInStringOrComment(lnum, strlen(line))) + break + endif + let lnum = prevnonblank(lnum - 1) + endwhile + return lnum +endfunction + +" Find line above 'lnum' that started the continuation 'lnum' may be part of. +function s:GetMSL(lnum, in_one_line_scope) + " Start on the line we're at and use its indent. + let msl = a:lnum + let lnum = s:PrevNonBlankNonString(a:lnum - 1) + while lnum > 0 + " If we have a continuation line, or we're in a string, use line as MSL. + " Otherwise, terminate search as we have found our MSL already. + let line = getline(lnum) + let col = match(line, s:msl_regex) + 1 + if (col > 0 && !s:IsInStringOrComment(lnum, col)) || s:IsInString(lnum, strlen(line)) + let msl = lnum + else + " Don't use lines that are part of a one line scope as msl unless the + " flag in_one_line_scope is set to 1 + " + if a:in_one_line_scope + break + end + let msl_one_line = s:Match(lnum, s:one_line_scope_regex) + if msl_one_line == 0 + break + endif + endif + let lnum = s:PrevNonBlankNonString(lnum - 1) + endwhile + return msl +endfunction + +" Check if line 'lnum' has more opening brackets than closing ones. +function s:LineHasOpeningBrackets(lnum) + let open_0 = 0 + let open_2 = 0 + let open_4 = 0 + let line = getline(a:lnum) + let pos = match(line, '[][(){}]', 0) + while pos != -1 + if !s:IsInStringOrComment(a:lnum, pos + 1) + let idx = stridx('(){}[]', line[pos]) + if idx % 2 == 0 + let open_{idx} = open_{idx} + 1 + else + let open_{idx - 1} = open_{idx - 1} - 1 + endif + endif + let pos = match(line, '[][(){}]', pos + 1) + endwhile + return (open_0 > 0) . (open_2 > 0) . (open_4 > 0) +endfunction + +function s:Match(lnum, regex) + let col = match(getline(a:lnum), a:regex) + 1 + return col > 0 && !s:IsInStringOrComment(a:lnum, col) ? col : 0 +endfunction + +function s:IndentWithContinuation(lnum, ind, width) + " Set up variables to use and search for MSL to the previous line. + let p_lnum = a:lnum + let lnum = s:GetMSL(a:lnum, 1) + let line = getline(line) + + " If the previous line wasn't a MSL and is continuation return its indent. + " TODO: the || s:IsInString() thing worries me a bit. + if p_lnum != lnum + if s:Match(p_lnum,s:continuation_regex)||s:IsInString(p_lnum,strlen(line)) + return a:ind + endif + endif + + " Set up more variables now that we know we aren't continuation bound. + let msl_ind = indent(lnum) + + " If the previous line ended with [*+/.-=], start a continuation that + " indents an extra level. + if s:Match(lnum, s:continuation_regex) + if lnum == p_lnum + return msl_ind + a:width + else + return msl_ind + endif + endif + + return a:ind +endfunction + +function s:InOneLineScope(lnum) + let msl = s:GetMSL(a:lnum, 1) + if msl > 0 && s:Match(msl, s:one_line_scope_regex) + return msl + endif + return 0 +endfunction + +function s:ExitingOneLineScope(lnum) + let msl = s:GetMSL(a:lnum, 1) + if msl > 0 + " if the current line is in a one line scope .. + if s:Match(msl, s:one_line_scope_regex) + return 0 + else + let prev_msl = s:GetMSL(msl - 1, 1) + if s:Match(prev_msl, s:one_line_scope_regex) + return prev_msl + endif + endif + endif + return 0 +endfunction + +" 3. GetJavascriptIndent Function {{{1 +" ========================= + +function GetJavascriptIndent() + " 3.1. Setup {{{2 + " ---------- + + " Set up variables for restoring position in file. Could use v:lnum here. + let vcol = col('.') + + " 3.2. Work on the current line {{{2 + " ----------------------------- + + " Get the current line. + let line = getline(v:lnum) + let ind = -1 + + + " If we got a closing bracket on an empty line, find its match and indent + " according to it. For parentheses we indent to its column - 1, for the + " others we indent to the containing line's MSL's level. Return -1 if fail. + let col = matchend(line, '^\s*[]})]') + if col > 0 && !s:IsInStringOrComment(v:lnum, col) + call cursor(v:lnum, col) + let bs = strpart('(){}[]', stridx(')}]', line[col - 1]) * 2, 2) + if searchpair(escape(bs[0], '\['), '', bs[1], 'bW', s:skip_expr) > 0 + if line[col-1]==')' && col('.') != col('$') - 1 + let ind = virtcol('.')-1 + else + let ind = indent(s:GetMSL(line('.'), 0)) + endif + endif + return ind + endif + + " If we have a /* or */ set indent to first column. + if match(line, '^\s*\%(/\*\|\*/\)$') != -1 + return 0 + endif + + " If we are in a multi-line string or line-comment, don't do anything to it. + if s:IsInStringOrDocumentation(v:lnum, matchend(line, '^\s*') + 1) + return indent('.') + endif + + " 3.3. Work on the previous line. {{{2 + " ------------------------------- + + " Find a non-blank, non-multi-line string line above the current line. + let lnum = s:PrevNonBlankNonString(v:lnum - 1) + + " If the line is empty and inside a string, use the previous line. + if line =~ '^\s*$' && lnum != prevnonblank(v:lnum - 1) + return indent(prevnonblank(v:lnum)) + endif + + " At the start of the file use zero indent. + if lnum == 0 + return 0 + endif + + " Set up variables for current line. + let line = getline(lnum) + let ind = indent(lnum) + + " If the previous line ended with a block opening, add a level of indent. + if s:Match(lnum, s:block_regex) + return indent(s:GetMSL(lnum, 0)) + &sw + endif + + " If the previous line contained an opening bracket, and we are still in it, + " add indent depending on the bracket type. + if line =~ '[[({]' + let counts = s:LineHasOpeningBrackets(lnum) + if counts[0] == '1' && searchpair('(', '', ')', 'bW', s:skip_expr) > 0 + if col('.') + 1 == col('$') + return ind + &sw + else + return virtcol('.') + endif + elseif counts[1] == '1' || counts[2] == '1' + return ind + &sw + else + call cursor(v:lnum, vcol) + end + endif + + " 3.4. Work on the MSL line. {{{2 + " -------------------------- + + let ind_con = ind + let ind = s:IndentWithContinuation(lnum, ind_con, &sw) + + " }}}2 + " + " + let ols = s:InOneLineScope(lnum) + if ols > 0 + let ind = ind + &sw + else + let ols = s:ExitingOneLineScope(lnum) + while ols > 0 && ind > 0 + let ind = ind - &sw + let ols = s:InOneLineScope(ols - 1) + endwhile + endif + + return ind +endfunction + +" }}}1 + +let &cpo = s:cpo_save +unlet s:cpo_save + +" vim:set sw=2 sts=2 ts=8 noet: + diff --git a/vim/indent/puppet.vim b/vim/indent/puppet.vim new file mode 100644 index 0000000..689e068 --- /dev/null +++ b/vim/indent/puppet.vim @@ -0,0 +1,76 @@ +" Vim indent file +" Language: Puppet +" Maintainer: Todd Zullinger <tmz@pobox.com> +" Last Change: 2009 Aug 19 +" vim: set sw=4 sts=4: + +if exists("b:did_indent") + finish +endif +let b:did_indent = 1 + +setlocal autoindent smartindent +setlocal indentexpr=GetPuppetIndent() +setlocal indentkeys+=0],0) + +if exists("*GetPuppetIndent") + finish +endif + +" Check if a line is part of an include 'block', e.g.: +" include foo, +" bar, +" baz +function! s:PartOfInclude(lnum) + let lnum = a:lnum + while lnum + let lnum = lnum - 1 + let line = getline(lnum) + if line !~ ',$' + break + endif + if line =~ '^\s*include\s\+[^,]\+,$' + return 1 + endif + endwhile + return 0 +endfunction + +function! s:OpenBrace(lnum) + call cursor(a:lnum, 1) + return searchpair('{\|\[\|(', '', '}\|\]\|)', 'nbW') +endfunction + +function! GetPuppetIndent() + let pnum = prevnonblank(v:lnum - 1) + if pnum == 0 + return 0 + endif + + let line = getline(v:lnum) + let pline = getline(pnum) + let ind = indent(pnum) + + if pline =~ '^\s*#' + return ind + endif + + if pline =~ '\({\|\[\|(\|:\)$' + let ind += &sw + elseif pline =~ ';$' && pline !~ '[^:]\+:.*[=+]>.*' + let ind -= &sw + elseif pline =~ '^\s*include\s\+.*,$' + let ind += &sw + endif + + if pline !~ ',$' && s:PartOfInclude(pnum) + let ind -= &sw + endif + + " Match } }, }; ] ]: ) + if line =~ '^\s*\(}\(,\|;\)\?$\|]:\?$\|)\)' + let ind = indent(s:OpenBrace(v:lnum)) + endif + + return ind +endfunction diff --git a/vim/indent/sass.vim b/vim/indent/sass.vim new file mode 100644 index 0000000..1da8319 --- /dev/null +++ b/vim/indent/sass.vim @@ -0,0 +1,40 @@ +" Vim indent file +" Language: Sass +" Maintainer: Tim Pope <vimNOSPAM@tpope.org> +" Last Change: 2010 May 21 + +if exists("b:did_indent") + finish +endif +let b:did_indent = 1 + +setlocal autoindent sw=2 et +setlocal indentexpr=GetSassIndent() +setlocal indentkeys=o,O,*<Return>,<:>,!^F + +" Only define the function once. +if exists("*GetSassIndent") + finish +endif + +let s:property = '^\s*:\|^\s*[[:alnum:]#{}-]\+\%(:\|\s*=\)' +let s:extend = '^\s*\%(@extend\|@include\|+\)' + +function! GetSassIndent() + let lnum = prevnonblank(v:lnum-1) + let line = substitute(getline(lnum),'\s\+$','','') + let cline = substitute(substitute(getline(v:lnum),'\s\+$','',''),'^\s\+','','') + let lastcol = strlen(line) + let line = substitute(line,'^\s\+','','') + let indent = indent(lnum) + let cindent = indent(v:lnum) + if line !~ s:property && line !~ s:extend && cline =~ s:property + return indent + &sw + "elseif line =~ s:property && cline !~ s:property + "return indent - &sw + else + return -1 + endif +endfunction + +" vim:set sw=2: diff --git a/vim/indent/scala.vim b/vim/indent/scala.vim new file mode 100644 index 0000000..45266a0 --- /dev/null +++ b/vim/indent/scala.vim @@ -0,0 +1,83 @@ +" Vim indent file +" Language : Scala (http://scala-lang.org/) +" Maintainer : Stefan Matthias Aust +" Last Change: 2006 Apr 13 + +if exists("b:did_indent") + finish +endif +let b:did_indent = 1 + +setlocal indentexpr=GetScalaIndent() + +setlocal indentkeys=0{,0},0),!^F,<>>,<CR> + +setlocal autoindent sw=2 et + +if exists("*GetScalaIndent") + finish +endif + +function! CountParens(line) + let line = substitute(a:line, '"\(.\|\\"\)*"', '', 'g') + let open = substitute(line, '[^(]', '', 'g') + let close = substitute(line, '[^)]', '', 'g') + return strlen(open) - strlen(close) +endfunction + +function! GetScalaIndent() + " Find a non-blank line above the current line. + let lnum = prevnonblank(v:lnum - 1) + + " Hit the start of the file, use zero indent. + if lnum == 0 + return 0 + endif + + let ind = indent(lnum) + let prevline = getline(lnum) + + "Indent html literals + if prevline !~ '/>\s*$' && prevline =~ '^\s*<[a-zA-Z][^>]*>\s*$' + return ind + &shiftwidth + endif + + " Add a 'shiftwidth' after lines that start a block + " If if, for or while end with ), this is a one-line block + " If val, var, def end with =, this is a one-line block + if prevline =~ '^\s*\<\(\(else\s\+\)\?if\|for\|while\|va[lr]\|def\)\>.*[)=]\s*$' + \ || prevline =~ '^\s*\<else\>\s*$' + \ || prevline =~ '{\s*$' + let ind = ind + &shiftwidth + endif + + " If parenthesis are unbalanced, indent or dedent + let c = CountParens(prevline) + echo c + if c > 0 + let ind = ind + &shiftwidth + elseif c < 0 + let ind = ind - &shiftwidth + endif + + " Dedent after if, for, while and val, var, def without block + let pprevline = getline(prevnonblank(lnum - 1)) + if pprevline =~ '^\s*\<\(\(else\s\+\)\?if\|for\|while\|va[lr]\|def\)\>.*[)=]\s*$' + \ || pprevline =~ '^\s*\<else\>\s*$' + let ind = ind - &shiftwidth + endif + + " Align 'for' clauses nicely + if prevline =~ '^\s*\<for\> (.*;\s*$' + let ind = ind - &shiftwidth + 5 + endif + + " Subtract a 'shiftwidth' on '}' or html + let thisline = getline(v:lnum) + if thisline =~ '^\s*[})]' + \ || thisline =~ '^\s*</[a-zA-Z][^>]*>' + let ind = ind - &shiftwidth + endif + + return ind +endfunction diff --git a/vim/indent/scss.vim b/vim/indent/scss.vim new file mode 100644 index 0000000..82bba49 --- /dev/null +++ b/vim/indent/scss.vim @@ -0,0 +1,12 @@ +" Vim indent file +" Language: SCSS +" Maintainer: Tim Pope <vimNOSPAM@tpope.org> +" Last Change: 2010 Jul 26 + +if exists("b:did_indent") + finish +endif + +runtime! indent/css.vim + +" vim:set sw=2: |