Skip to content

Commit

Permalink
Improve fish#Indent().
Browse files Browse the repository at this point in the history
  • Loading branch information
Raimondi committed Jun 19, 2015
1 parent 825853f commit b771d51
Show file tree
Hide file tree
Showing 2 changed files with 82 additions and 12 deletions.
93 changes: 81 additions & 12 deletions autoload/fish.vim
Original file line number Diff line number Diff line change
@@ -1,22 +1,91 @@
function! s:IsString(lnum, col)
let l:stack = map(synstack(a:lnum, a:col), 'synIDattr(v:val, "name")')
return len(filter(l:stack, 'v:val ==# "fishString"'))
endfunction

function! s:IsContinuedLine(lnum)
return getline(a:lnum - 1) =~ '\v\\$'
endfunction

function! s:FindPrevLnum(lnum)
if a:lnum < 1
return 0
endif
let l:lnum = prevnonblank(a:lnum)
while l:lnum > 0 && ( s:IsContinuedLine(l:lnum) || s:IsString(l:lnum, 1) )
let l:lnum = prevnonblank(l:lnum - 1)
endwhile
return l:lnum
endfunction

function! s:IsEndOfSwitch(lnum)
let l:lnum = a:lnum
let l:line = getline(l:lnum)
let l:in_block = 0
let l:stop_pat = '\v^\s*%(if|else|while|for|begin)>'
let l:block_start_pat = '\v^\s*%(if|while|for|switch|begin)>'
while l:lnum > 0
let l:lnum = prevnonblank(l:lnum - 1)
let l:line = getline(l:lnum)
if l:line =~# '\v^\s*end>'
let l:in_block += 1
elseif l:in_block && l:line =~# l:block_start_pat
let l:in_block -= 1
elseif !l:in_block && l:line =~# l:stop_pat
return 0
elseif !l:in_block && l:line =~# '\v^\s*switch>'
return 1
endif
endwhile
return 0
endfunction

function! fish#Indent()
let l:prevlnum = prevnonblank(v:lnum - 1)
let l:line = getline(v:lnum)
if s:IsString(v:lnum, 1)
return indent(v:lnum)
endif
if exists('*shiftwidth')
let l:shiftwidth = shiftwidth()
else
let l:shiftwidth = &shiftwidth
endif
let l:prevlnum = s:FindPrevLnum(v:lnum - 1)
if l:prevlnum ==# 0
return 0
endif
let l:indent = 0
let l:shift = 0
let l:prevline = getline(l:prevlnum)
if l:prevline =~# '\v^\s*switch>'
let l:indent = &shiftwidth * 2
elseif l:prevline =~# '\v^\s*%(begin|if|else|while|for|function|case)>'
let l:indent = &shiftwidth
let l:previndent = indent(l:prevlnum)
if s:IsContinuedLine(v:lnum)
let l:previndent = indent(v:lnum - 1)
if s:IsContinuedLine(v:lnum - 1)
return l:previndent
elseif exists('g:fish_indent_cont')
return l:previndent + (g:fish_indent_cont * &sw)
elseif exists('g:indent_cont')
return l:previndent + (g:indent_cont * &sw)
else
return l:previndent + (3 * &sw)
endif
endif
let l:line = getline(v:lnum)
if l:line =~# '\v^\s*end>'
return indent(v:lnum) - (l:indent ==# 0 ? &shiftwidth : l:indent)
elseif l:line =~# '\v^\s*%(case|else)>'
return indent(v:lnum) - &shiftwidth
if l:prevline =~# '\v^\s*%(begin|if|else|while|for|function|case|switch)>'
let l:shift += 1
endif
if l:line =~# '\v^\s*%(end|case|else)>'
let l:shift -= 1
endif
if l:line =~# '\v^\s*<case>' && l:prevline =~# '\v<switch>'
let l:shift += 1
endif
if l:line =~# '\v\s*end>' && s:IsEndOfSwitch(v:lnum)
let l:shift -= 1
endif
if l:prevline =~# '\v^\s*%(if|while|for|else|switch|end)>.*<begin>'
let l:shift += 1
endif
return indent(l:prevlnum) + l:indent
let l:indent = l:previndent + l:shift * l:shiftwidth
return l:indent < 0 ? 0 : l:indent
endfunction

function! fish#Format()
Expand Down
1 change: 1 addition & 0 deletions indent/fish.vim
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
setlocal indentexpr=fish#Indent()
setlocal indentkeys=!^F,o,O
setlocal indentkeys+==end,=else,=case

0 comments on commit b771d51

Please sign in to comment.