vimrc 파일을 접는 가장 좋은 방법이 있습니까?


21

나는 최근에 내는 것을 깨달았다 vimrc보다 쉽게 탐색 할 수 있도록, 그것은 내가 정력에 접는의 개념을 조사하기로 결정 읽고 편집 (IMO 너무 많이 나는 그것을 줄이기 위해 노력하겠습니다 인) 지금은 400 개 이상의 선 길이 (이 나는 익숙하지 않았다) .

  • 접기 방법을 설정하려고 시도했지만 indent결과가 마음에 들지 않았습니다 (내 대부분 vimrc이 실제로 들여 쓰기되지 않았기 때문에 너무 지저분했습니다 ).
  • 또한 세트에 노력 foldmethod을 expr하고 syntax있지만 제대로 아무것도 접을 수 없습니다.
  • 여기서 diff접는 방법으로 사용 하는 것은 적합하지 않은 것 같습니다. (또는 그것이 사용 방법을 이해하지 못했다면)
  • 그래서 지금 은 파일에서 "잡음"을 찾은 및 마커 marker때문에 완전히 만족하지 않는 방법을 사용 하고 있습니다."{{{"}}}

따라서을 올바르게 접는 방법에 대한 모범 사례 또는 일반적인 지침이 있는지 알고 싶습니다vimrc .

참고 1 : 우리 모두가 알고 있듯이 SO는 포럼이 아니며 개인적인 의견을 수집하기 위해 만들어지지 않았으며 그것이 내가 찾고있는 것이 아닙니다. 물론 일부 사람들은 선호도가 있다고 생각하지만 왜 사용하는지 알고 싶습니다. 예를 들어 마커는 들여 쓰기를 사용하는 것보다 가독성을 향상시킵니다.

참고 2 : 또한 나의 주요 목표는 vimrc가능한 한 명확하게하는 것이므로 다른 모범 사례가 존재하면 멋진 vimrc것을 만들 수 있습니다.

편집 1 : 나는 vimrc이미 주요 부분을 섹션 (때로는 하위 섹션)으로 세분화 했다는 것을 알아야했습니다 .

  • 일반 옵션
  • 플러그인 (각 플러그인 및 해당 구성에 대한 하위 섹션 포함)
  • 매핑
  • 탐색 (하위 섹션도 포함)
  • 색깔
  • 기타...

폴딩을 생각한 것은 바로이 구조입니다. 특정 지점에서 관심있는 섹션 만 출력 할 수 있다는 것이 매우 편리하다고 생각합니다.

편집 2 :vimrc 여러 파일에서 세분화를 언급하는 답변 은 유효하지만 개인 취향으로는 내 도트 파일을 포함하는 git repo에서 하나의 파일 만 유지하는 것이 더 쉽다고 생각하기 때문에 접기를 사용하고 싶습니다. 그것은 개인적인 취향 일 뿐이며이 접근법을 사용할 수도 있지만 접는 것을 선호합니다.


내가 사용하고 생각 "{{{일을하는 방법이 가장 '와 같은 정력'의 솔라리 플러그인이 사용하고 그것은 당신에게 수동 주름 설정의 가장 표준적인 방법 제공 소음이 될 수도 있지만입니다
— icc97을

답변:


22

나는 표의vimrc 저자 인 godlygeek에서 복사 한 바닥에 다음과 같은 모델을 가지고 있습니다 .

"" vim:fdm=expr:fdl=0
"" vim:fde=getline(v\:lnum)=~'^""'?'>'.(matchend(getline(v\:lnum),'""*')-2)\:'='

이렇게하면 2 + "'sa로 시작하는 줄이 생깁니다. 더는 "'깊은 겹이야. 필요한 경우 섹션을 세분화 할 수 있습니다.


나는 지금 그것을 테스트 할 수 없지만 그것은 나에게 이상적인 솔루션 인 것 같습니다! 공유해 주셔서 감사합니다!
— statox

일부 Explain : getline (v : lnum)은 행 번호 (v : lnum)로 지정된 행의 문자열을 리턴합니다. = ~는 정규식 일치를 의미합니다. '^ ""'은 모든 행이 두 개의 "s로 시작 함을 의미합니다. matchend (getline (v : lnum), '" "*')-2는" "의 추가 수를 계산합니다. 즉," ""는 레벨 1, " "" "는 레벨 2와 같이 접 힙니다. getline (v : lnum) = ~ '^" "'은 v : lnum 행 시작에 따라" "가 아닌" "에 따라 true 또는 false를 반환합니다. true 인 경우, fde가 >extra number of "(이 라인에서 <다음의 숫자에 의해 시작되는 시작 레벨) 또는 '='(이전 라인 레벨 사용)으로 설정되면, 의미는fold-expr
— van abel

최근 vim 업데이트 8.1.1517 이후) :이 구성으로 ""모델을 처리하는 동안 오류가 발견되었습니다 "
— apollo

9

먼저 .vimrc하위 목록 및 하위 하위 목록이있는 목록과 같이 자신의 범주를 정의 하고 모든 플러그인 / 설정 / 기능을 해당 범주에 추가하는 것이 좋습니다. 맞춤형 폴딩과 결합하면 다음과 같이 효과적입니다.

예

위의 예는 my을 구성하는 데 도움이되는 가능한 범주를 보여줍니다 .vimrc. 다음과 같은 사용자 정의 접기 설정을 사용합니다.

""""""""""""""""""""""""
"  THIS IS A CATEGORY  "
""""""""""""""""""""""""
"" Autofolding .vimrc
" see http://vimcasts.org/episodes/writing-a-custom-fold-expression/
""" defines a foldlevel for each line of code
function! VimFolds(lnum)
  let s:thisline = getline(a:lnum)
  if match(s:thisline, '^"" ') >= 0
    return '>2'
  endif
  if match(s:thisline, '^""" ') >= 0
    return '>3'
  endif
  let s:two_following_lines = 0
  if line(a:lnum) + 2 <= line('$')
    let s:line_1_after = getline(a:lnum+1)
    let s:line_2_after = getline(a:lnum+2)
    let s:two_following_lines = 1
  endif
  if !s:two_following_lines
      return '='
    endif
  else
    if (match(s:thisline, '^"""""') >= 0) &&
       \ (match(s:line_1_after, '^"  ') >= 0) &&
       \ (match(s:line_2_after, '^""""') >= 0)
      return '>1'
    else
      return '='
    endif
  endif
endfunction

""" defines a foldtext
function! VimFoldText()
  " handle special case of normal comment first
  let s:info = '('.string(v:foldend-v:foldstart).' l)'
  if v:foldlevel == 1
    let s:line = ' ◇ '.getline(v:foldstart+1)[3:-2]
  elseif v:foldlevel == 2
    let s:line = '   ●  '.getline(v:foldstart)[3:]
  elseif v:foldlevel == 3
    let s:line = '     ▪ '.getline(v:foldstart)[4:]
  endif
  if strwidth(s:line) > 80 - len(s:info) - 3
    return s:line[:79-len(s:info)-3+len(s:line)-strwidth(s:line)].'...'.s:info
  else
    return s:line.repeat(' ', 80 - strwidth(s:line) - len(s:info)).s:info
  endif
endfunction

""" set foldsettings automatically for vim files
augroup fold_vimrc
  autocmd!
  autocmd FileType vim 
                   \ setlocal foldmethod=expr |
                   \ setlocal foldexpr=VimFolds(v:lnum) |
                   \ setlocal foldtext=VimFoldText() |
     "              \ set foldcolumn=2 foldminlines=2
augroup END

자신의 범주와 하위 범주를 정의하려면 다음 구문을 사용하십시오.

""""""""""""""
"  Category  "
""""""""""""""
"" Subcategory
""" Subsubcategory
" Just a comment, gets ignored no matter where

vim- 스 니펫 을 사용하는 경우 최상위 카테고리를 쉽게 만들 수 있습니다 (예 : UltiSnips 사용 ) : vim- 스 니펫에서 제공 하는 box또는 bbox스 니펫을 확장하기 만하면 됩니다 ( 확장 트리거 작성 box또는 bbox누르기).

공간을 두 번 눌러 접기를 더 빠르게 열고 닫으려면 :

let mapleader = "\<space>"
" Toggle folds
nnoremap <silent> <leader><Space> @=(foldlevel('.')?'za':"\<Space>")<CR>
vnoremap <leader><space> zf

그렇게하면 .vimrc쉽게 탐색 할 수 있는 잘 구조화 되어 있습니다.


멋진 애니메이션 gif의 경우 +1 :) 궁금한 점은 입력 한 키를 표시하는 데 사용한 것이 무엇입니까?
— mMontu

@ mMontu : screenkey를 사용하여 키를 표시하고 gtk-recordmydesktop을 사용하여 기록했습니다 (둘 다 데비안 저장소에서). 5fps에서 45 초 클립은 MiB보다 작습니다. 그런 다음 온라인으로 gif로 변환했습니다 (즉, 화질이 완벽하기 전에 왜곡이 발생한 곳).
— cbaumhardt

7

기본 vimrc을 여러 다른 분류 된 파일에 대한 링크로 사용 하여 한 파일의 Vim 옵션, 다른 파일의 플러그인 설정과 같이 각각의 파일을 소싱합니다.

"--- Vim Options
source ~/.vim/config/vim_options.vim

"--- Here Be Functions!
" (need to be sourced before stuff that uses 'em)
runtime! functions/*.vim

"--- Key Mapping
source ~/.vim/config/key_mapping.vim

"--- Folding
source ~/.vim/config/folding.vim

"--- Autocmds
source ~/.vim/config/autocmds.vim

"--- We Are Plugged In!
source ~/.vim/config/plugins.vim

" vim: ft=vim fdm=marker

OP 질문에 대한 더 직접적인 대답으로, 마커 방법을 사용하지만 간격과 오른쪽에 개별적으로보다 많은 범주가 있습니다. 그래도 각 플러그인을 별도로 수행합니다.


나는 내 질문에 정확하게 잊어 버렸습니다 : vimrc(IMO) 복잡성을 증가시키고 유지하기가 더 어려워지기 때문에 다른 파일에서 "분리"하는 팬이 아닙니다 . 접기에 대해 "간격을두고 오른쪽으로"라는 것은 무엇을 의미합니까?
— statox

내 말은 " {{{당신의 등이 많은 공간으로 함께 textwidth그래서 마커 우측 가장자리 근처에 있습니다. collapse.vim 파일에 개인화 된 FoldText 함수도 있습니다. 나는 git repo가 ​​커밋 당 하나의 특정 유형의 mod 만 있도록 별도의 파일을 선호합니다.
— Cometsong

7

"모범 사례"는 분명히 의견의 문제라고 말할 수 있습니다. :) (1) 명백한 이해, (2) Vim뿐만 아니라 모든 구성 파일에 적용 할 수있는 두 가지 접근 방식이 있습니다 : 논리 섹션으로 접기 그리고 하위 섹션 (또는 용감하다고 느끼면 더 깊어짐)을 구성하고 여러 개의 작은 파일로 구성을 나누고 :source-ing합니다.

개인적으로 접을 수 있기 때문에 접근하기가 더 쉬우면서도 몇 가지 계층 구조를 선택할 수 있습니다. autocmd가장 자연스러운 레벨의 접는 함수와 s도 "자연적인"논리 단위를 만들기 때문에 좋은 생각입니다. marker논리적 계층 구조는 들여 쓰기 수준이나 구문 강조에 반드시 반영 될 필요는 없기 때문에 접기는이 모든 것에서 가장 의미가 있습니다. 또한 증가 foldcolumn하여 현재 위치에 대한 시각적 힌트를 제공합니다.

# vim: filetype=vim foldmethod=marker foldlevel=0 foldcolumn=3

참고 로이 foldtext기능 (IIRC의 Drew Neil의 비슷한 기능 수정)은 기본값보다 나에게 더 의미가 있습니다.

function! MyFoldText()
    let line = getline(v:foldstart)

    let nucolwidth = &foldcolumn + &number * &numberwidth
    let windowwidth = winwidth(0) - nucolwidth - 3
    let foldedlinecount = v:foldend - v:foldstart

    " expand tabs into spaces
    let chunks = split(line, "\t", 1)
    let line = join(map(chunks[:-2], 'v:val . repeat(" ", &tabstop - strwidth(v:val) % &tabstop)'), '') . chunks[-1]

    let line = strpart(line, 0, windowwidth - 2 - len(foldedlinecount))
    let fillcharcount = windowwidth - len(line) - len(foldedlinecount) - 1
    return line . '...' . repeat(' ', fillcharcount) . foldedlinecount . ' '
endfunction
set foldtext=MyFoldText()

다른 접근 방식, 파일 분할, 주요 문제는 물건을 찾고 한 파일에서 다른 파일로 전환하는 것입니다. 둘 다 해결하는 가장 좋은 방법은 CtrlSF , CtrlP 또는 이와 유사한 플러그인을 사용하는 것 입니다. 그러나 어쨌든 이미 그 중 하나를 사용하고있을 것입니다.


그래서 당신은 함께갑니다 marker. 실제로 커스터마이징 foldcolumn은 좋은 일이며, 어떤 값이 내 요구에 가장 잘 맞는지 볼 것입니다. 또한 분할 파일에 대한 귀하의 견해를 공유하지만에 CtrlSF매우 만족하더라도 그것을 살펴볼 것입니다 CtrlP.
— statox

또한 맞춤형 폴딩 방법을 사용하는 방법을 설명해 주시겠습니까? 내가 설정하는 노력 fdm을 foldtext하고 MyFoldText()있지만 그것을 사용하는 올바른 방법이 아니다처럼 보인다.
— statox

@statox 는 기본적으로 특수화 된 버전 인 ag 또는 ackCtrlSF 와 함께 가장 잘 작동합니다 . 사용자 정의 접기 방법이 아니라 접힌 텍스트의 모양을 변경하는 기능입니다. 내 스 니펫의 마지막 줄은 사용 방법을 보여줍니다 . grepfoldtextset foldtext=MyFoldText()
— lcd047

2

기본 모범 사례 :

  • 섹션으로 나누십시오.

    • 플러그인
    • 설정
    • 리 바인드
  • 각 섹션 / 리 바인드 코멘트

  • ( .vimrc또는 _vimrcGithub에서 백업 )

저의 개인적인 취향입니다. 어쩌면별로 도움이되지 않을 수도 있습니다.


나는 개인적으로 접기를 사용하지 않으며, 필요하지 않습니다. vimrc를 정리하면 좋을 것입니다.
— 구스타프 블롬 크 비스트

내 vimrc는 이미 섹션 (일반 옵션, 플러그인, 매핑, 탐색, 색상 등)으로 구성되어 있습니다. 섹션 (또는 서브 섹션)을 접을 수 있다는 사실은 실제로 편집 / 찾고있는 것에 집중하는 것이 좋습니다.
— statox

괜찮아. 잘못된 답변으로 죄송합니다.
— 구스타프 블롬 크 비스트

그것은 나쁜 대답이 아니며, 또한 충분한 질문을하지 않고 유감스럽게 생각합니다. 죄송합니다. ;-)
— statox

2

@PeterRincker의 답변 에서 영감을 얻어 ATX 스타일 헤더를 사용하도록 다음을 만들었습니다. 당신의 끝에 추가.vimrc

"# Folding

" Fold with ATX style headers - "# is H1, "## is H2, and so on
" vim:fdm=expr:fdl=0
" vim:fde=getline(v\:lnum)=~'^"#'?'>'.(matchend(getline(v\:lnum),'"#*')-1)\:'='

1

나와 같은 큰 기능이 있다면 이것을 사용하여 기능을 접을 수 있습니다.

fun! MyFoldLevel(linenum)
    if ! exists('w:nextline')
        let w:nextline = 0
        let w:insideafun = 0
    endif

    if w:nextline == 1
        let w:nextline = 0
        let w:insideafun = 0
    endif

    let l:line = getline(a:linenum)

    if l:line =~# '^[[:space:]]*fun'
        let w:insideafun = 1
        return '>1'
    elseif l:line =~# '^[[:space:]]*endf'
        let w:nextline = 1
        return '<1'
    endif

    if w:insideafun == 1
        return 1
    else
        return 0
    endif
endfun

그리고이 모델을 vimrc에 추가하십시오 :

" vim:fde=MyFoldLevel(v\:lnum):fdm=expr:

0

@Peter Rincker 및 @ go2null의 아이디어 확장. Vim modeline에서 접기 옵션을 설정하지 않으려는 경우. 다음 autocmd를 사용하여 접기 방법과 접기 식을 설정할 수 있습니다.

augroup vim_folding
    autocmd!
    autocmd FileType vim set foldmethod=expr foldlevel=0
    " note that double quote in foldexpr has to be escaped with backslash
    autocmd FileType vim set foldexpr=getline(v:lnum)=~'^\"#'?'>'.(matchend(getline(v:lnum),'\"#*')-1):'='
augroup END

정식 vim 명령으로 작동하도록 원래 답변을 약간 수정했습니다 (콜론을 벗어날 필요는 없지만 큰 따옴표는 이스케이프해야합니다).

긴 foldexpr문자열 이 마음에 들지 않으면 해당 함수를 정의 할 수 있습니다.

function! VimFolds(lnum)
    let s:cur_line = getline(a:lnum)

    if s:cur_line =~ '^"#'
        return '>' . (matchend(s:cur_line, '"#*')-1)
    else
        return '='
    endif

endfunction

그런 다음 autocmd 줄 foldexpr을

autocmd FileType vim set foldexpr=VimFolds(v:lnum)
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.