How do you exit vimdiff mode in vim, specifically, for Fugitive?

╄→尐↘猪︶ㄣ 提交于 2019-12-04 07:37:48

问题


I am using vim with the fugitive extension. It has a :Gdiff command which brings you into vimdiff mode, but what is the right/quick way to close/quit vimdiff mode?

I.e., let's say I am editing the file FooBar.txt under Git repository. I fire up :Gdiff, review my changes in vimdiff, and then I want to get back and continue editing FooBar.txt or any other file :)

UPDATE1: I'm going to give these quick combos a try next working day :)

"vimdiff current vs git head (fugitive extension)
nnoremap <Leader>gd :Gdiff<cr> 
"switch back to current file and closes fugitive buffer
nnoremap <Leader>gD :diffoff!<cr><c-w>h:bd<cr>

UPDATE2: My current mappings (closes diff window only!)

"vimdiff current vs git head (fugitive extension)
nnoremap <Leader>gd :Gdiff<cr> 
"switch back to current file and closes fugitive buffer
nnoremap <Leader>gD <c-w>h<c-w>c

Also, please help me decide if the following should be an anwser: https://stackoverflow.com/a/15975201/275980


回答1:


You can execute windo set nodiff noscrollbind and then close the second window.

Update: there is a diffoff command. Use windo diffoff, not what I wrote in previous line.




回答2:


According to: https://github.com/tpope/vim-fugitive/issues/36

Close the other window. The easiest way to do this if you haven't shifted focus to it is <C-W><C-O>, which means "make this Window the Only window."




回答3:


I had no luck with diffoff, but I just learned that :Gedit with no argument will bring you back to the working-directory version of the file, as opposed to some earlier version you were reviewing.

And as q (no need for :q) will close the diff sidebar, you can do q followed by :Gedit to get rid of the sidebar and then go back to the current version of the file.




回答4:


This works fine for me, combining some of the existing ideas here:

function! MyCloseDiff()
  if (&diff == 0 || getbufvar('#', '&diff') == 0)
        \ && (bufname('%') !~ '^fugitive:' && bufname('#') !~ '^fugitive:')
    echom "Not in diff view."
    return
  endif

  " close current buffer if alternate is not fugitive but current one is
  if bufname('#') !~ '^fugitive:' && bufname('%') =~ '^fugitive:'
    if bufwinnr("#") == -1
      b #
      bd #
    else
      bd
    endif
  else
    bd #
  endif
endfunction
nnoremap <Leader>gD :call MyCloseDiff()<cr>



回答5:


I've found a simple solution for this. You can check it here: https://gist.github.com/radmen/5048080

" Simple way to turn off Gdiff splitscreen
" works only when diff buffer is focused
if !exists(":Gdiffoff")
  command Gdiffoff diffoff | q | Gedit
endif



回答6:


None of the above solutions worked for me. Ended up doing this instead:

nnoremap <Leader>D :Gedit<CR><C-w>h :q<CR><C-w>k




回答7:


An alternative to <C-W><C-O>, if you have multiple windows, would be move to the other diff window and do <C-W>c, which close only one window.

If you close the wrong diff window do a :Gedit

Be careful and don't confuse <C-W>c with <C-W><C-C>




回答8:


this is what I have to leave the vimdiff windows after using :Gdiff

nnoremap gD :q!<CR> :Gedit!<CR>



回答9:


noremap <leader>do :diffoff \| windo if &diff \| hide \| endif<cr>

Quite diff mode and close other diff windows. (Note: fugitive will auto delete its hidden buffers.)




回答10:


My function will work both from diff window and file window. But probably won't handle itself with multiple diffs opened. For that you'll need to use fugitive#buffer(n).path() to scan and match.

command! Gdiffoff call Gdiffoff()
function! Gdiffoff()
    let diffbufnr = bufnr('^fugitive:')
    if diffbufnr > -1 && &diff
        diffoff | q
        if bufnr('%') == diffbufnr | Gedit | endif
        setlocal nocursorbind
    else
        echo 'Error: Not in diff or file'
    endif
endfunction

Add a key binding:

nnoremap <silent> <leader>gD :Gdiffoff<CR>



回答11:


Yet another way. What I have in fugitive.vim - first save some info (s:gitbufname) when diff starts:

function! s:Diff(vert,...) abort
  call sy#toggle()
  let s:startcol = winwidth(0)
  let &columns=(winwidth(0) * 2 - 20)
...
    if getwinvar('#', '&diff')
      let s:gitbufname = bufname("%")
      wincmd p
      call feedkeys(winnr."\<C-W>w", 'n')
    endif
...
endfunction

and later when leaving the buffer switch window to the saved buffer and restore:

augroup fugitive_diff
autocmd!
autocmd BufWinLeave *
  \ if s:can_diffoff(+expand('<abuf>')) && s:diff_window_count() == 2 |
  \   if exists('s:gitbufname') && winnr() != bufwinnr(s:gitbufname) |
  \     let nr = bufnr("%") | exe bufwinnr(s:gitbufname).'wincmd w' | exe 'buf'.nr |
  \   endif |
  \   call s:diffoff_all(getbufvar(+expand('<abuf>'), 'git_dir')) |
  \   call sy#toggle() |
  \   call airline#load_theme() | call airline#update_statusline() |
  \   let &columns=s:startcol |
  \ endif
...



回答12:


Check the vimdiff toggling between diffthis and diffoff here at this page.

The code:

nnoremap <silent> <Leader>df :call DiffToggle()<CR>

function! DiffToggle()
    if &diff
        diffoff
    else
        diffthis
    endif
:endfunction



回答13:


Method 1:

  • open a compare by:

:windo diffthis

  • close it by:

:windo diffoff

Method 2:

I recommend just using the most simple command: :q<CR>

when you want to do it quickly, add the mapping:

" Set mapleader
let mapleader = ","
let g:mapleader = ","

and

" Quickly close the current window
nnoremap <leader>q :q<CR>

It works well for me. Exit vimdiff just by ,q, because normally your cursor in the old file.




回答14:


Was using the code below based on https://stackoverflow.com/a/15113951/10999673 :

    if !exists(":Gdiffoff")
        command Gdiffoff bw! fugitive://*
    endif

but it gave me an error "E93: more than one match for ..." in a 3 way diff, so i instead used the answer from https://stackoverflow.com/a/4867969/10999673 and finally have this:

function! GetBufferList()
    return filter(range(1,bufnr('$')), 'buflisted(v:val)')
endfunction

function! GetMatchingBuffers(pattern)
    return filter(GetBufferList(), 'bufname(v:val) =~ a:pattern')
endfunction

function! WipeMatchingBuffers(pattern)
    let l:matchList = GetMatchingBuffers(a:pattern)

    let l:count = len(l:matchList)
    if l:count < 1
        echo 'No buffers found matching pattern ' . a:pattern
        return
    endif

    if l:count == 1
        let l:suffix = ''
    else
        let l:suffix = 's'
    endif

    exec 'bw ' . join(l:matchList, ' ')

    echo 'Wiped ' . l:count . ' buffer' . l:suffix . '.'
endfunction

command! -nargs=1 Gdiffoff call WipeMatchingBuffers('fugitive://')

I just tweaked, copied and pasted the code into my .vimrc




回答15:


Running :Gwrite after merging to your satisfaction will close the other two diff panes in addition to updating the git cache to mark the file as merged.



来源:https://stackoverflow.com/questions/2703644/how-do-you-exit-vimdiff-mode-in-vim-specifically-for-fugitive

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!