开发者

Is there a way to expand a Vim fold automatically when your put your cursor on it?

开发者 https://www.devze.com 2023-03-27 07:06 出处:网络
Can you have Vim exp开发者_如何学Goand a fold automatically when the cursor touches it?See the foldopen option.It controls which groups of commands will lead to

Can you have Vim exp开发者_如何学Goand a fold automatically when the cursor touches it?


See the foldopen option. It controls which groups of commands will lead to opening a fold if the cursor is moved into a closed fold.

Note that vertical movements do not open a closed fold, though. Moreover, there is no setting in foldopen to enable this behavior. When hor item is set in foldopen option, to open a fold one can use h, l or other horizontal movement commands. In case if it is crucial to automatically open a fold on any cursor movement that touches it, one can approach this problem by remapping some subset of vertical movement commands like it is shown below.

nnoremap <silent> j :<c-u>call MoveUpDown('j', +1, 1)<cr>
nnoremap <silent> k :<c-u>call MoveUpDown('k', -1, 1)<cr>
nnoremap <silent> gj :<c-u>call MoveUpDown('gj', +1, 1)<cr>
nnoremap <silent> gk :<c-u>call MoveUpDown('gk', -1, 1)<cr>
nnoremap <silent> <c-d> :<c-u>call MoveUpDown("\<lt>c-d>", +1, '&l:scroll')<cr>
nnoremap <silent> <c-u> :<c-u>call MoveUpDown("\<lt>c-u>", -1, '&l:scroll')<cr>
nnoremap <silent> <c-f> :<c-u>call MoveUpDown("\<lt>c-f>", +1, 'winheight("%")')<cr>
nnoremap <silent> <c-b> :<c-u>call MoveUpDown("\<lt>c-b>", -1, 'winheight("%")')<cr>
function! MoveUpDown(cmd, dir, ndef)
    let n = v:count == 0 ? eval(a:ndef) : v:count
    let l = line('.') + a:dir * n
    silent! execute l . 'foldopen!'
    execute 'norm! ' . n . a:cmd
endfunction

An inferior, but a bit thriftier solution would be to open a fold on every cursor movement.

autocmd CursorMoved,CursorMovedI * silent! foldopen

Unfortunately, this solution is not general one. After the fold under the cursor is opened, the cursor is positioned on the first line of that fold. If this behavior is undesirable, one can follow the vertical direction of a movement, and place the cursor on the last line of the fold when the cursor is moving bottom-up.

autocmd CursorMoved,CursorMovedI * call OnCursorMove()
function! OnCursorMove()
    let l = line('.')
    silent! foldopen
    if exists('b:last_line') && l < b:last_line
        norm! ]z
    endif
    let b:last_line = l
endfunction

However, a fold will not be opened if the movement jumps over the fold. For example, 2j on the line just above a fold will put the cursor on the line just after that fold, not the second line in it.


set foldopen=all

seems to do what you want. You may also make an autocommand for cursor movement:

au CursorMoved * call AutoOpen()

calling a function like:

function! AutoOpen()
  if foldclosed(".") == line(".")
    call feedkeys("zo")
  endif
endfunction

If you want this to also work in insert mode, use:

au CursorMoved,CursorMovedI * call AutoOpen()


:help fdo and possibly :help fcl may help you. I have this line in my .vimrc:

set foldopen=block,hor,insert,jump,mark,percent,quickfix,search,tag,undo
0

精彩评论

暂无评论...
验证码 换一张
取 消