1

There must be a way to change the init.vim / .vimrc so I can quit Vim without saving first (:wq) nor force quitting (:q!). But I only want that behaviour when the Buffer has no name.

Why? Because a lot of times I use Vim just temporary for example:

  • As a calculator
  • Clipboard Text Editor
  • Get the Unicode Value of a Character
  • Dec to Hex Converter
  • Etc... The List is enormous colossal.

I am getting tired of typing in :q! instead of just :q. So any Ideas?


Thanks for your help :)

2
  • It's called the buftype option Commented Jul 14, 2023 at 12:00
  • @ChristianBrabandt Which one of these 9 Options? It doesn't seem to fit my need...
    – Bog
    Commented Jul 14, 2023 at 12:14

3 Answers 3

3

Here are a few variations on the :help 'buftype' theme suggested by Heptite. The idea is the opposite of that in Pixelbog's answer: instead of changing the behavior of :q, we change the nature of the first buffer, turning it into a sacrificial scratchpad.

Shell alias

$ vim +set\ buftype=nofile

starts Vim as usual, with an empty buffer, but makes it a scratch buffer by setting the buftype option to nofile.

You can make it an alias:

alias vims="vim +set\ buftype=nofile"

and do $ vims when you want a Vim scratchpad.

Short Vim command

You can create a Vim command with a short mnemonic name:

" in ~/.vimrc
command S set buftype=nofile

and call that command at startup with:

$ vim +S

when you need a scratchpad.

(I use that very method to edit my vimrc: $ vim +EV.)

Check arguments at startup

You can tell Vim to set the option above if it was called without arguments (filenames):

" in ~/.vimrc
if !exists('g:did_scratchpad') && argc(-1) == 0
    setlocal buftype=nofile
    let g:did_scratchpad = 1
endif

which allows you to simply do $ vim to get a scratchpad. The first empty buffer is the only one that is treated as a scratchpad so you don't have to worry about losing work in files you might decide to edit normally.

FWIW, I think this one is cool and I will probably keep a variation of it for a while.

See :help argc().

Bonus

Here is a "scratchpad" command from my vimrc, that I use very often:

command! SC vnew | setlocal bufhidden=wipe buftype=nofile nobuflisted noswapfile
5
  • Very detailed and informative answer, thanks. But does anything speak against doing it with :abbreviate? Are there any disadvantages you can think of to change the behavior of :q? I am gonna try both ways for like a week and then I am gonna pick the better one :)
    – Bog
    Commented Jul 17, 2023 at 11:48
  • No, it's just two different ways to approach the same problem. By focusing a bit too much on your "command" problem you sort of narrow down the field of possible solutions to "command" solutions. Which is not problematic in and of itself, but still a good way to miss better solutions. My answer provides a different perspective: instead of focusing on the "command" problem I focused on the actual need from which the problem arose (using $ vim like a scratchpad), which allowed me to think a bit more outside the box.
    – romainl
    Commented Jul 17, 2023 at 12:13
  • I am gonna use both of our solutions for like a month more. Both have some flaws: For example I don't like your solution, because I often get thrown into an empty buffer without starting vim from the cli. An example is: grep foo bar.txt | neovim -. My solution has the flaw, that it doesn't allow you to forcefully quit (:q!) in an empty buffer, because it will get expanded into this: :q!!. So yeah I am gonna choose in 1 Month which one to pick^^
    – Bog
    Commented Jul 19, 2023 at 13:07
  • Hmm, I don't follow. $ grep foo bar.txt | vim - works just as I would expect it to work: it opens Vim with the output of $ grep foo bar.txt in the first buffer… which is not super useful but I don't see how it conflicts with your stated goal. If you hit :q, then Vim quits just like you asked. If you open other buffers, then :q works normally for those buffers.
    – romainl
    Commented Jul 19, 2023 at 13:53
  • ehmmmmmm.... tbh I have no Idea what my thought behind it was while writing this... My brain is really tired right now^^ You are absolutely right, so far there are no flaws with your approach^^ My bad^^
    – Bog
    Commented Jul 19, 2023 at 14:12
3

If you set 'buftype' to nofile the buffer will be considered a "scratch buffer" and you won't have to force quit on the buffer, but you also won't be able to write it if you want to save it.

1
  • Yeah but whats the point of it? Isn't writing bt=nofile way longer than just putting the ! after :q?^^
    – Bog
    Commented Jul 17, 2023 at 6:33
1

Answer

cnoreabbrev <expr> q (bufname('%') == '' ? 'q!' : 'q')

Explanation

  • You can simply use :abbreviate for this. Even better: :cnoreabbrev.
  • Now you only need to check if the Buffer has a name or not. Do with a simple if-statement

Looks then like this:

function! QuitIfUnnamed()
    if bufname('%') == ''
        execute 'q!'
    else
        execute 'q'
    endif
endfunction

cnoreabbrev <expr> q QuitIfUnnamed()

And now if you want it to only have a one-liner, you can use a ternary operator and it would look like this:

cnoreabbrev <expr> q (bufname('%') == '' ? 'q!' : 'q')
1
  • 1
    Try :help empty()
    – D. Ben Knoble
    Commented Jul 14, 2023 at 15:22

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.