Mercurial > vim
view runtime/indent/erlang.vim @ 4143:f5ef9b9c18cd v7.3.824
updated for version 7.3.824
Problem: Can redefine builtin functions. (ZyX)
Solution: Disallow adding a function to g:.
author | Bram Moolenaar <bram@vim.org> |
---|---|
date | Wed, 20 Feb 2013 15:19:43 +0100 |
parents | af1e8a1714c2 |
children | eb6ab7e78925 |
line wrap: on
line source
" Vim indent file " Language: Erlang " Author: Csaba Hoch <csaba.hoch@gmail.com> " Contributors: Edwin Fine <efine145_nospam01 at usa dot net> " Pawel 'kTT' Salata <rockplayer.pl@gmail.com> " Ricardo Catalinas Jiménez <jimenezrick@gmail.com> " License: Vim license " Version: 2011/09/06 " Only load this indent file when no other was loaded if exists("b:did_indent") finish else let b:did_indent = 1 endif setlocal indentexpr=ErlangIndent() setlocal indentkeys+==after,=end,=catch,=),=],=} " Only define the functions once if exists("*ErlangIndent") finish endif " The function goes through the whole line, analyses it and returns the " indentation level. " " line: the line to be examined " return: the indentation level of the examined line function s:ErlangIndentAfterLine(line) let linelen = strlen(a:line) " the length of the line let i = 0 " the index of the current character in the line let ind = 0 " how much should be the difference between the indentation of " the current line and the indentation of the next line? " e.g. +1: the indentation of the next line should be equal to " the indentation of the current line plus one shiftwidth let last_fun = 0 " the last token was a 'fun' let last_receive = 0 " the last token was a 'receive'; needed for 'after' let last_hash_sym = 0 " the last token was a '#' " Ignore comments if a:line =~# '^\s*%' return 0 endif " Partial function head where the guard is missing if a:line =~# "\\(^\\l[[:alnum:]_]*\\)\\|\\(^'[^']\\+'\\)(" && a:line !~# '->' return 2 endif " The missing guard from the split function head if a:line =~# '^\s*when\s\+.*->' return -1 endif while 0<=i && i<linelen " m: the next value of the i if a:line[i] == '"' let m = matchend(a:line,'"\%([^"\\]\|\\.\)*"',i) let last_receive = 0 elseif a:line[i] == "'" let m = matchend(a:line,"'[^']*'",i) let last_receive = 0 elseif a:line[i] =~# "[a-z]" let m = matchend(a:line,".[[:alnum:]_]*",i) if last_fun let ind = ind - 1 let last_fun = 0 let last_receive = 0 elseif a:line[(i):(m-1)] =~# '^\%(case\|if\|try\)$' let ind = ind + 1 elseif a:line[(i):(m-1)] =~# '^receive$' let ind = ind + 1 let last_receive = 1 elseif a:line[(i):(m-1)] =~# '^begin$' let ind = ind + 2 let last_receive = 0 elseif a:line[(i):(m-1)] =~# '^end$' let ind = ind - 2 let last_receive = 0 elseif a:line[(i):(m-1)] =~# '^after$' if last_receive == 0 let ind = ind - 1 else let ind = ind + 0 endif let last_receive = 0 elseif a:line[(i):(m-1)] =~# '^fun$' let ind = ind + 1 let last_fun = 1 let last_receive = 0 endif elseif a:line[i] =~# "[A-Z_]" let m = matchend(a:line,".[[:alnum:]_]*",i) let last_receive = 0 elseif a:line[i] == '$' let m = i+2 let last_receive = 0 elseif a:line[i] == "." && (i+1>=linelen || a:line[i+1]!~ "[0-9]") let m = i+1 if last_hash_sym let last_hash_sym = 0 else let ind = ind - 1 endif let last_receive = 0 elseif a:line[i] == '-' && (i+1<linelen && a:line[i+1]=='>') let m = i+2 let ind = ind + 1 let last_receive = 0 elseif a:line[i] == ';' && a:line[(i):(linelen)] !~# '.*->.*' let m = i+1 let ind = ind - 1 let last_receive = 0 elseif a:line[i] == '#' let m = i+1 let last_hash_sym = 1 elseif a:line[i] =~# '[({[]' let m = i+1 let ind = ind + 1 let last_fun = 0 let last_receive = 0 let last_hash_sym = 0 elseif a:line[i] =~# '[)}\]]' let m = i+1 let ind = ind - 1 let last_receive = 0 else let m = i+1 endif let i = m endwhile return ind endfunction function s:FindPrevNonBlankNonComment(lnum) let lnum = prevnonblank(a:lnum) let line = getline(lnum) " Continue to search above if the current line begins with a '%' while line =~# '^\s*%.*$' let lnum = prevnonblank(lnum - 1) if 0 == lnum return 0 endif let line = getline(lnum) endwhile return lnum endfunction " The function returns the indentation level of the line adjusted to a mutiple " of 'shiftwidth' option. " " lnum: line number " return: the indentation level of the line function s:GetLineIndent(lnum) return (indent(a:lnum) / &sw) * &sw endfunction function ErlangIndent() " 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 prevline = getline(lnum) let currline = getline(v:lnum) let ind_after = s:ErlangIndentAfterLine(prevline) if ind_after != 0 let ind = s:GetLineIndent(lnum) + ind_after * &sw else let ind = indent(lnum) + ind_after * &sw endif " Special cases: if prevline =~# '^\s*\%(after\|end\)\>' let ind = ind + 2*&sw endif if currline =~# '^\s*end\>' let ind = ind - 2*&sw endif if currline =~# '^\s*after\>' let plnum = s:FindPrevNonBlankNonComment(v:lnum-1) if getline(plnum) =~# '^[^%]*\<receive\>\s*\%(%.*\)\=$' " If the 'receive' is not in the same line as the 'after' let ind = ind - 1*&sw else let ind = ind - 2*&sw endif endif if prevline =~# '^\s*[)}\]]' let ind = ind + 1*&sw endif if currline =~# '^\s*[)}\]]' let ind = ind - 1*&sw endif if prevline =~# '^\s*\%(catch\)\s*\%(%\|$\)' let ind = ind + 1*&sw endif if currline =~# '^\s*\%(catch\)\s*\%(%\|$\)' let ind = ind - 1*&sw endif if ind<0 let ind = 0 endif return ind endfunction