Toggling
첫번째 장에서 vim에서 옵션을 세팅하는 방법을 다뤘었다. set someoption!
으로 해당 옵션을 "toggle"할 수 있다. 이는 우리가 매핑을 만들때 더욱 잘 쓰인다.
다음 명령어를 실행시켜보자.
:nnoremap <leader>N :setlocal number!<cr>
이제 <leader>N
으로 number
옵션을 키고 끌 수 있다.
relativenumber
옵션이 활성화 된 경우에는number
가 꺼져도 relative number가 출력되므로 이를 끄고 테스트해보자.setlocal norelativenumber
토글 매핑을 만드는 것은 우리가 별개의 두 키를 매핑시키지 않아도 되기 때문에 아주 편리하다.
Toggling Options
토글 옵션을 하나 만들어보자. 다음을 ~/.vimrc
에 추가해보자. (~/.vim/plugin/
에 분리된 파일을 만들어도 무방)
nnoremap <leader>f :call FoldColumnToggle()<cr>
function! FoldColumnToggle()
echom &foldcolumn
endfunction
<leader>f
를 누르면 현재 foldcolumn
옵션의 값을 출력해줄것이다. 해당 옵션에 익숙하지 않다면 :help foldcolumn
을 읽어보자.
실제 토글 기능을 넣어보자. 다음 코드를 수정
nnoremap <leader>f :call FoldColumnToggle()<cr>
function! FoldColumnToggle()
if &foldcolumn
setlocal foldcolumn=0
else
setlocal foldcolumn=4
endif
endfunction
실제로 실행시켜보면 <leader>f
키를 누를 때마다 fold column을 감추고 보여준다.
특정 텍스트를 fold 해 본 다음에 테스트 하면 더 직관적이다. fold 하고 싶은 텍스트를 선택한 다음
:fold
로 접을 수 있다.
Toggling Other Things
옵션 뿐 아니라 quickfix window 등도 토글하기에 좋다. 이전에 만든 뼈대와 비슷하게 만들어보자.
nnoremap <leader>q :call QuickfixToggle()<cr>
function! QuickfixToggle()
return
endfunction
이 매핑은 지금은 아무것도 하지 않는다. 이를 조금 더 유용한 형태로 변경시켜보자.
nnoremap <leader>q :call QuickfixToggle()<cr>
function! QuickfixToggle()
copen
endfunction
이제 quickfix window가 열리는 것을 볼 수 있다.
이를 "toggling" 하기 위해서 일단 빠르고 dirty한 해결책을 사용해보자. "global variable"이다.
nnoremap <leader>q :call QuickfixToggle()<cr>
let g:quickfix_is_open = 0
function! QuickfixToggle()
if g:quickfix_is_open
cclose
let g:quickfix_is_open = 0
else
copen
let g:quickfix_is_open = 1
endif
endfunction
이제 <leader>f
로 quickfix window를 토글할 수 있게 되었다.
Improvements
위에서 만든 토글은 잘 작동하지만, 몇몇 문제점을 가지고 있다.
우선 사용자가 :copen
이나 :cclose
를 사용해도 우리의 전역변수 (quickfix_is_open
)는 업데이트 되지 않는다.
이는 vimscript 코드 작성의 중요한 포인트를 보여준다: 만약 모든 케이스를 다루려고 한다면 늪에 빠지게 될것이고, 결 코 작업을 마무리하지 못할 것이다.
실제로 작동하게 한 후에 다시 돌아와서 이를 수정하는 것이 100% 완벽하게 하기 위해 시간을 소모하는 것보다 낫다. 많은 사람들이 사용하는 플러그인을 만들 때에는 예외이다. 이런 경우 버그등을 줄이기 위해 많은 시간이 소요된다.
Restoring Windows/Buffers
우리의 함수가 가지고 있는 문제는 이미 quickfix window가 열린 경우에 해당 매핑을 사용하는 경우이다.
이를 해결하기 위해 많은 플러그인에서 사용되는 방식을 차용해보자.
nnoremap <leader>q :call QuickfixToggle()<cr>
let g:quickfix_is_open = 0
function! QuickfixToggle()
if g:quickfix_is_open
cclose
let g:quickfix_is_open = 0
execute g:quickfix_return_to_window . "wincmd w"
else
let g:quickfix_return_to_window = winnr()
copen
let g:quickfix_is_open = 1
endif
endfunction
두 줄을 추가하였다. 하나는 현재 사용중인 윈도우의 번호를 새로운 변수로 정의한 것이다. (else
절)
두 번 째는 wincmd w
를 수행하여 vim이 해당 윈도우로 이동할 수 있게 한 것이다. (if
절)
여전히 우리의 해결책은 사용자가 quickfix window를 열어두었을 때 매핑으로 토글이 되지는 않지만, 그래도 많은 문제를 해결해준다. quickfix window를 사용하면서 작업중인 기존 윈도우로 커서를 이동해주는 역할을 한다.
Exercises
Read
:help foldcolumn
.Read
:help winnr()
Read
:help ctrl-w_w
.Read
:help wincmd
.Namespace the functions by adding
s:
and<SID>
where necessary.
nnoremap <leader>q :call <SID>QuickfixToggle()<cr>
let g:quickfix_is_open = 0
function! s:QuickfixToggle()
if g:quickfix_is_open
cclose
let g:quickfix_is_open = 0
execute g:quickfix_return_to_window . "wincmd w"
else
let g:quickfix_return_to_window = winnr()
copen
let g:quickfix_is_open = 1
endif
endfunction
'tools > vim' 카테고리의 다른 글
Learn Vimscript The Hard Way - 40. Paths (0) | 2020.04.20 |
---|---|
Learn Vimscript The Hard Way - 39. Functional Programming (0) | 2020.04.19 |
Learn Vimscript The Hard Way - 37. Dictionaries (0) | 2020.04.17 |
Learn Vimscript The Hard Way - 36. Looping (0) | 2020.04.16 |
Learn Vimscript The Hard Way - 35. List (0) | 2020.04.15 |