¿Cómo puedo hacer que Vim guarde automáticamente los archivos cuando pierde el foco?

I'm used to my editors autosaving files when they lose focus. I recently switched to MacVim, and I can't recreate that behavior. I tried this:

autocmd BufLeave,FocusLost * wall

but if a buffer is unnamed when the window or MacVim loses focus, I get an error like the following:

Error detected while processing BufLeave Auto commands for "*":
E141: No file name for buffer 1

I'm confused, because :wallla documentación dice:

Write all changed buffers.  Buffers without a file
name or which are readonly are not written.

so I'd expect it to skip unnamed buffers. Is there a better way to do this?

Editar:

I'm pretty sure that the better way to do what I intended by using BufLeave -- saving buffers when I switch between them, so I don't get "No write since last change" -- is to set 'autowriteall'. The question still stands for when MacVim loses focus to other applications (FocusLost).

preguntado el 09 de enero de 11 a las 03:01

Just throwing this out there in regards to autosaving in VIM: aren't swap files enough? -

I'm not trying to back up my work; I need the file to be on disk for whatever tool I've switched focus to, such as a test suite. -

4 Respuestas

You don’t care about errors in those circumstances since there is nothing you can reasonably do about them anyway – especially when losing focus. So just swallow them:

autocmd BufLeave,FocusLost * silent! wall

Much simpler than an elaborate dance to figure out where there se be an error in order to avoid it.

Respondido 29 ago 12, 12:08

It needs a *, like autocmd BufLeave,FocusLost * silent! wall , at least for me, it does. - pvinis

vim noob here.. where does this line go? inside .vimrc? - thefonso

Does it matter where in .vimrc it's added? This line does not make the warning go away for me. :( - También

Uhm, hard to answer. It can matter, though in most cases won’t. What warning do you get? Is your vimrc posted anywhere? - Aristóteles Pagaltzis

I suspect when docs for wall say "without a file name" they may be referring to buffers with buftype=nofile . One way to get what you want would be to have the autocmd have bufdo call a simple function. E.g., some untested code to give the idea:

autocmd BufLeave,FocusLost * bufdo! call WriteFile()

function WriteFile()
   if (&buftype=="") && (expand("%:r") > "") && (&readonly==0)
      write
   endif
endfunction

I think the standard way of getting something like this automatic saving of buffers would be to set the autosave option in Vim.

Respondido el 09 de enero de 11 a las 07:01

bufdo will switch buffers in the current window. You should probably write let s:curbuf=bufnr('%') | try | execute 'bufdo! call WriteFile()' | finally | execute "buffer ".s:curbuf | endtry. It still has problems: for some reason after this code list option in help buffer was reset and cursor got positioned in the center. Adding wincmd v antes try y wincmd q Si lo envía después endtry funciona mejor. - ZyX

Llanura wincmd v | execute 'bufdo! call WriteFile()' | wincmd q is probably the best option. - ZyX

@ZyX -- Thanks for the correction; I wasn't thinking when I suggested bufdo. Sounds like your second solution would work fine, opening new window, cycling through buffers, then closing window. I still think just going with autosave is best solution, or possibly writing a more complex function to be called by the autocmd that uses a windo command within a tabdo so that buffer switching within a window is never required. - Herbert Sitz

autocmd BufLeave,FocusLost * bufdo! call WriteFile()

function WriteFile()
   if (&buftype=="") && (expand("%:r") > "") && (&readonly==0)
      write
   endif
endfunction

This method has a side-effect that, you can only open one unamed buffer. If you open the second one, it would automatically be synced to the content of the first unamed buffer.

respondido 06 nov., 12:19

This is a copy of Herbert Sitz's answer above with different commentary. Was this intended as a comment on his answer? - Peeja

just put this in .vimrc

set updatetime=1000
autocmd CursorHoldI * silent w

Respondido el 20 de Septiembre de 13 a las 15:09

That has several issues: first, it takes a full second to save, by which time I'd want to have the file on disk already; second, it only works if you stay in insert mode; third, :write doesn't cut it. @Aristotle Pagaltzis answer covers it for me. - Peeja

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.