12

How I paste now:

  1. Right-click/Copy or simply highlight.
  2. Right-click/Paste or Middle Click or CTRL+SHFT+V
  3. Indents appear at increasing intervals: 0, 2, 4, 6, +

Question at hand:

From prior research, I found that the quick and dirty solution is entering the following in my .vimrc file: set paste. However, those who suggested that command said that set paste affects other settings. (Off the top of my head, I forget.)

I would like to know what option I can set that simply pastes without extra indentation. If that ends up being 'paste', then I would like to know what exactly that command does.

I only see one difference. When in Vim, -- INSERT -- becomes -- INSERT (paste) --

Rich
  • 31,891
  • 3
  • 72
  • 139

7 Answers7

15

OK, here is a "yank & put" primer…

In Vim, the primary commands for yanking (copying) and putting (pasting) are y and p.

Yanking places the yanked text in a register. That register is the unnamed register, ", by default but one can use other registers:

"ay    " yank into register a
"by    " yank into register b
"+y    " yank into clipboard register
[…]

Similarly, putting inserts text from a register. That register is the unnamed register by default but one can use other registers:

"ap    " put from register a
"+p    " put from clipboard register
"3p    " put from the register 3
[…]

Those commands are prefered to "Right-click/Paste or Middle Click or CTRL+SHFT+V" because the text is "put" into the buffer without any special treatment. With "Right-click/Paste or Middle Click or CTRL+SHFT+V", the text is inserted in the buffer as if you typed it and is thus subjected to automatic indenting/formatting.

If you can't use "+p or "*p — working over SSH without X forwarding or Vim built without clipboard support — the paste option disables automatic indenting and a bunch of other very useful options so that your typed text is not alrered.

As noted in :help 'paste', the options has potentially very bad side effects so it is important to disable it right after you pasted your text:

:set paste
(paste)
:set nopaste

That dance is obviously a pain in the ass so there is another option that lets you define a special shortcut for toggling paste:

set pastetoggle=<F12>

That slightly reduces the pain:

<F12>
(paste)
<F12>

But it is still a pain.

If you can, it is recommended to install a proper Vim with clipboard support so you can use "*p or "+p (depending on how you copied your text) to paste text the right way.

  • On Mac OS X: install MacVim,
  • on Debian-based systems: install the vim-gnome or vim-gtk package,
  • on CentOS: install the vim-enhanced package.

Reference:

:help p
:help y
:help registers
:help 'paste'
:help 'pastetoggle'
filbranden
  • 28,785
  • 3
  • 26
  • 71
romainl
  • 40,486
  • 5
  • 85
  • 117
8

VIM has another setting pastetoggle that defines the mapping for toggling paste mode. That's what you'd want to do and then you can just enable paste mode and then paste.

Although I find that a little less intuitive and have often found ]p to be a better way to paste code instead of using just p

Dhruva Sagar
  • 5,510
  • 2
  • 22
  • 17
7

If you are using a fairly modern terminal emulator, you can install the vim-bracketed-paste plugin.

From the docs:

xterm, urxvt, iTerm2, gnome-terminal (and other terminals using libvte) are known to work.

After installing, you can simply paste as normal in insert mode, and it will take care of setting and unsetting paste for you.

Jay Thompson
  • 519
  • 3
  • 7
3

To paste text into vim without auto-indentation, you need to put Vim in Paste mode. This is useful if you want to cut or copy some text from one window and paste it in Vim. This will avoid unexpected effects. See: :help paste for more details.

To make a life easier, there is pastetoggle variable which specifies the key sequence that toggles the 'paste' option (:set invpaste).

In example if you'd like to use F2 to disable autoindenting if pasting into terminal in X, you may use the following code into your .vimrc file:

nnoremap <F2> :set invpaste paste?<CR>
set pastetoggle=<F2>
kenorb
  • 18,433
  • 18
  • 72
  • 134
1

When you are on a server or system where you can't or don't want to change the configuration, the quickest way is

:i!

This will enter insert mode with autoindent turned off, where you paste your text. When you are finished you need to type

.

on its own line to end the insert.

laktak
  • 2,933
  • 13
  • 27
  • This seems like it almost works. I opened a file in vim, :i!, pasted contents, newline, period, enter. It looks like the paste happened correctly. Then :wq results in: "E667: Fsync failed" WARNING: Original file may be lost or damaged don't quit the editor until the file is successfully written! – Wassadamo Jan 22 '22 at 00:13
  • @Wassadamo I don't think this error is related to :i! – laktak Jan 23 '22 at 18:52
  • Sorry it was indeed unrelated. There was something wrong on my system. No storage space available to save files. – Wassadamo Jan 23 '22 at 19:08
1

Unimpaired.vim solves this problem in the most efficient way I've seen. It provides some mappings to enter Insert mode with 'paste' enabled, then automatically disables it when you return to Normal mode. yo opens a new line below the cursor; yO above. (Just like o and O.)

The plugin also provides a suite of other useful mappings for navigating lists, changing common settings, and some nifty text conversions. The mappings are exemplary: they feel native to Vim without stepping on existing functionality.

I only provide the details in the previous paragraph because many would be reluctant to install a plugin to solve the problem at hand. However, I think they'd be happy with the other (unrelated) things Unimpaired.vim has to offer.

tommcdo
  • 7,710
  • 1
  • 32
  • 36
0

Alternatively you can have vim handle the situation automatically. With the following in your ~\.vimrc

let &t_SI .= "\<Esc>[?2004h"
let &t_EI .= "\<Esc>[?2004l"

inoremap <special> <expr> <Esc>[200~ XTermPasteBegin()

function! XTermPasteBegin() set pastetoggle=<Esc>[201~ set paste return "" endfunction

you can paste freely without worrying about the auto-indentions.

If you work in tmux, then you have to write instead the following

function! WrapForTmux(s)
  if !exists('$TMUX')
    return a:s
  endif

let tmux_start = "&lt;Esc>Ptmux;" let tmux_end = "&lt;Esc>\"

return tmux_start . substitute(a:s, "&lt;Esc>", "&lt;Esc>&lt;Esc>", 'g') . tmux_end endfunction

let &t_SI .= WrapForTmux("&lt;Esc>[?2004h") let &t_EI .= WrapForTmux("&lt;Esc>[?2004l")

function! XTermPasteBegin() set pastetoggle=<Esc>[201~ set paste return "" endfunction

inoremap <special> <expr> <Esc>[200~ XTermPasteBegin()

The source is Coderwall if you would like to read more.

zyy
  • 239
  • 2
  • 11