VimでSCSSの括弧のインデントがおかしい。

VimでSCSSを整形したら、閉じ括弧が左端に寄ってしまう現象に見舞われました。

css.vimを入れても、scss-syntax.vimを入れても、vim-css3-syntax.vimを入れても治りません。

さて困った…とここで頼みの綱のstackoverflowです。

This is a quick hack, based on the built-in perl indentation code (in indent/perl.vim). Hopefully you can use it to get what you want to do. See the more detailed comments in either the perl indentation code or another one of the files in the indent directory for more details.

setlocal indentexpr=GetMyIndent()
function! GetMyIndent()
    let cline = getline(v:lnum)

    " 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 line = getline(lnum)
    let ind = indent(lnum)

    " Indent blocks enclosed by {}, (), or []
    " Find a real opening brace
    let bracepos = match(line, '[(){}\[\]]', matchend(line, '^\s*[)}\]]'))
    while bracepos != -1
        let brace = strpart(line, bracepos, 1)
        if brace == '(' || brace == '{' || brace == '['
            let ind = ind + &sw
        else
            let ind = ind - &sw
        endif
        let bracepos = match(line, '[(){}\[\]]', bracepos + 1)
    endwhile
    let bracepos = matchend(cline, '^\s*[)}\]]')
    if bracepos != -1
        let ind = ind - &sw
    endif

    return ind
endfunction
indentation - How do I define indents in vim based on curly braces? - Stack Overflow

ということで、.vim/after/indent/scss.vimがこんな感じになりました。

setlocal indentexpr=GetMyIndent()
function! GetMyIndent()
    let cline = getline(v:lnum)

    " 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 line = getline(lnum)
    let ind = indent(lnum)

    " Indent blocks enclosed by {}, (), or []
    " Find a real opening brace
    let bracepos = match(line, '[(){}\[\]]', matchend(line, '^\s*[)}\]]'))
    while bracepos != -1
        let brace = strpart(line, bracepos, 1)
        if brace == '(' || brace == '{' || brace == '['
            let ind = ind + &sw
        else
            let ind = ind - &sw
        endif
        let bracepos = match(line, '[(){}\[\]]', bracepos + 1)
    endwhile
    let bracepos = matchend(cline, '^\s*[)}\]]')
    if bracepos != -1
        let ind = ind - &sw
    endif

    return ind
endfunction

setlocal expandtab
setlocal tabstop=4
setlocal shiftwidth=4
setlocal softtabstop=0

if !exists('b:undo_indent')
    let b:undo_indent = ''
endif

let b:undo_indent = 'setlocal '.join([
	    \	'tabstop<',
	    \	'shiftwidth<',
	    \	'softtabstop<',
	    \ ])
dotfiles/.vim/after/indent/scss.vim at master · s-shin/dotfiles · GitHub