Copy and paste from external source - vim

I use vim (Actually gvim on windows) as my main text editor. In my work flow I have to copy sentences to/from various external sources, therefore I use clipboard=unnamed to save me key strokes (p instead of "*p).
I copy text from an outer source and I want to paste it over two different places in vim. I mark the first one (v) and then use p to paste over it. The problem is that at this point I lose the original buffer and can't paste it in the second place. It does not exist in the unnamed buffer, the * buffer or the numbered buffers. My guess is that pasting over selection is putting the "pasted over" text in the unnamed buffer.
How can I paste my original string in two locations? i.e. prevent it from getting lost from the buffers.
Thanks.

Try this:
:vmap p "_xP
vmap means to make a mapping that only applies in visual mode.
p is the key to create the mapping for.
"_ is the black hole register. This is used in any situation where you want to delete text without affecting any registers.
xP means delete the selected text, then paste before the resulting cursor position.

You could set up a mapping to ease your pain:
:vmap <F5> "zxP
This will delete the visually selected text, but put it in a different register, so the clipboard isn't affected. Change <F5> to whatever is easiest for you.

I don't know if I misunderstand you but I tried what you are doing and I have no problem in doing that with the + drop-register.
My workflow:
copy a sentence in an external application (ie. browser)
visual select a sentence in vim and replaced it with "+p or p (with clipboard=unnamed set)
visually select another sentence and replace it with "+p
Sadly when pasting the second time you have to explicitly paste from the + register. Therefore I would recommend a mapping for p/P instead of using clipboard=unnamed
nmap p "+p
Try using
:registers
to see the contents of the different registers.

I don't know how to do that on Windows. With KDE, the clipboard has a history that you can select from, so you could do the paste, select the previous selection from the clipboard, and paste in the new location.
That said, it sounds like it might make more sense for you to have it in only one location, then write a script to take that input and create the output you need. Can you elaborate more on what it is you are trying to accomplish?

Check the value of the 'guioptions' options. Make sure the 'a' flag is not set. Also, check that the 'clipboard' option and verify that neither the 'unnamed' or 'autoselect' flags are set.
:set go-=a
:set clipboard-=unnamed

Related

Why does Vim always manage to clip off at least a couple of characters when copying and pasting?

Vim always manages to clip off at least of couple of characters when I copy something from a text file, such as a public rsa key for example.
Generally, I open a text file in my computer, highlight the text, copy it to my clipboard. I go into my terminal (with Vim already open) and then:
i (for insert)
ctrl+shift+v
Am I doing something wrong?
I've double checked, and triple checked, this, and I am absolutely sure that I highlighted all of the text that I needed to copy. Other times it works fine. There does not seem to be any consistency in regards to when it happens.
Anyone experience this?
This usually happens because something in the pasted text triggers a key mapping unexpectedly. This is what paste mode is for.
Do this before pasting:
:set paste
And turn it off after:
:set nopaste
This can be annoying to type frequently, so there is a way to map it to a key combination. I use ,p for this, and have this in my .vimrc:
set pastetoggle=,p
(Yes, I use an actual comma here, not <Leader>. That's because <Leader> won't work here, as this isn't technically a mapping.)
This is a toggle, so you can use it to turn the mode on and off. It works in both normal mode and insert mode.
You do want to turn it off after the paste. Since paste mode disables your insert mappings, you don't want to leave it on all the time.
You can read more about the paste option with :help 'paste.
The annoyance of toggling to and form paste mode can be avoided by using "+p or "*p. (You're putting the quoteplus register).
More often than not, I prefer "+P, since this leaves my cursor at the end of properly formatted put. see :help quoteplus for details. So the whole workflow is:
outside of vim: copy to clipboard
inside of vim: "+P

Why it is so difficult for vim to copy into system clipboard?

According to official vim wiki copying any text into system clipboard is a something I've never expected to see in a text editor created by humans.
gg"+yG – copy the entire buffer into + (normal mode)
Copy/Pasting between the browser and a text file with 6 keystrokes is something I refuse to accept as normality.
Are there any sane alternatives?
It's not difficult, it's powerful. As the yank command takes a {motion}, you can copy arbitrary (and precisely selected) text areas, all with the same command. Likewise, "+ is just one destination of many, and Vim's named registers are very useful.
You may have noticed that most people (sometimes heavily) customize their Vim setup. On top of the powerful editing abstractions, that puts it on yet another level (at the expense of now being dependent on your Vim configuration).
So, if you need to copy the entire buffer to the system clipboard often, create your own shortcut, and persist it in your ~/.vimrc. For example:
:nnoremap <F2> :%yank +<CR>
There you have it: copying with a single keystroke (cp. :help key-notation for how keys are specified; as function keys are sparse, I would prefer <Leader>y instead).
If you often yank (various areas) to the system clipboard, making that the default register might also be worthwhile:
:set clipboard^=unnamedplus
To break it down:
gg
Move the cursor to the beginning of the buffer
"+
Set the target for copy to the system clipboard register
yG
Copy ("yank") everything from the cursor position to the end of the buffer (i.e. the whole file).
To give another example. If you want to copy just the current word to the clipboard you might perform:
"+yw
Since "w" is the command to move the cursor to the end of the current word.
If you want to shorten a regularly repeated action you could record a macro, or map a keyboard shortcut.
When I want to copy a whole file I just do :%y+
: Enter ex command
y[ank]
+ To clipboard register

Undo a paste without undoing previous typing

In vim I frequently end up undoing more than I want to after a messed up paste from the system clipboard. Is there a better way?
To reproduce:
Open iTerm # or terminal
vi # open vim
i # enter insert mode
type some stuff
Cmd-V # paste the contents of the OS X clipboard
The paste is a mess because I haven't :set paste. So
Esc # enter command mode
u # undo
but that undoes my typing as well as my paste.
Is there a different undo I can use? Apart from remembering to :set paste before pasting is there a better way to do this in general?
This is not the answer you're looking for, but you really should stop using vim as a non-modal editor. If you want to paste then return to normal mode and use vim's paste commands.
Assuming that you have a vim version with clipboard access this should do the trick "+p. You can also facilitate this by setting your unnamed register to be the + (or *) register, such that pasting from clipboard becomes a simple p.
The following question has a great answer that includes all this information How to make vim paste from (and copy to) system's clipboard?.
I'm not sure there's anything you can do after the fact, but one solution is to hit Ctrl-G u in insert mode just before you paste. This breaks the undo block into two separate blocks - so the paste will be remembered as a separate undoable action.
Granted if you have to remember to do this, you might as well just use :set paste instead - but on the upside it's fewer keystrokes and you don't have to go to command mode first.
Take a look at this plugin, it can auto run :set paste! when you use Cmd-V(or Ctrl-V) to paste some text. And leave paste mode when you finished.
The following mappings create an additional undo point (via :help i_CTRL-G_u) before pasting in insert mode. This way, you can undo the paste separately.
inoremap <C-r> <C-g>u<C-r>
inoremap <C-v> <C-g>u<C-v>
Actually the solution is you have to go to command mode(e.g. Esc) first and re-enter the insert mode, but it only works if I type manually but it seems "randomly" stop working if I test it in ~/.vimrc. Google doesn't help at all.
I spends a lot of time try to fix this issue and I just figure out the reason in my case:
Don't map the paste key same with the terminal existing paste key
e.g. Ctrl+Shift+V will paste in my Konsole terminal, but if I assign this key <C-S-v> in ~/.vimrc, the "undo for only single paste instead of multiple pastes" will not working.
In my case, I have to use <C-v> instead of <C-S-v>:
inoremap <C-v> <Esc>"+pi<Esc>i<Right><Right>
Your case may difference, but the point is same: don't assign the same paste key conflicts with existing terminal emulator key.
I've 100% proved this conclusion by set my terminal paste key to Ctrl+V and now <C-v> stop working but <C-S-v> working.
Note also that the vim is too sensitive and strange. I figure out I have to use i and then 2 Right keys manually to make it works in the correct cursor position, that's means I have to put i and 2 Right keys in the ~/.vimrc too. Your case might difference, but the point is same, ensure the keys+order in ~/.vimrc 100% match with what you type manually.

Quickest way to paste block of text into the vi editor from an external source

For instance, copying a configuration section from a web page and then pasting it into a .conf file that you have open in vi.
Enter insert mode (Type i)
Type: Ctrl + Shift + v
Or if you use the system register, you can paste without being in insert mode:
"*p
This will paste the system's clipboard at the point of the cursor. No insert mode needed.
The real answer:
:set paste
Enter Insert Mode: hit i
Paste: Command + v or Control + v
ESC
:set nopaste
One thing to bear in mind: Sometimes Vim auto-indents text. This is mostly fine, but sometimes it messes up text that you paste into a document.
If your indentations are awry, remove the pasted text, type :set paste, paste the text in again, and when you're done, type :set nopaste.
The easiest way is just to copy the text and just right click where you want to paste it in Vim in INSERT mode.
If you are using gVim, hit Ctrl + R and then either * or + in insert mode. It will paste the last copied text.
Ctrl-V/ Apple-V? Just make sure you're in insert mode in vi (i)
Use your systems paste shortcut key while in Insert mode, or if your source is in another file, you can type :r <fileName>, and it will be pasted at the current location of your cursor.
The easiest way on *nix is by selecting it with the mouse and pasting it in Vim with a middle click, after having put vi in insert mode.
The middle click could be a both left-right key if you're using a touchpad.
The quickest way is to paste it using whatever paste key your system uses (e.g. ⌘-v for Macs, Ctrl-V for Windows, etc.) in insert mode.
Some terminals require you to use Shift-Ctrl-V. However you are able to paste onto the command-line is how you should paste into Vim. However, this can cause some problems with indentation, which is where :set paste comes in. The fastest way to get in and out of this is to set a pastetoggle (see :help pastetoggle). For example, I use
set pastetoggle=<leader>p
The reason to use a pastetoggle instead of a mapping is because if you set a mapping insert mode, it will read it literally when in paste mode. Thus if you :set paste, go into insert mode, and type in any imap the mapping will not be completed, but instead the literal characters will be inserted. With pastetoggle you can get around that since it's a built-in feature.
As others have said, if you're in insert mode, you can also use <C-r>*, but why? Your normal pasting flow is most likely better. Understanding the * register and <C-r> is an important skill however. You can read more about them at :help registers and :help i_CTRL-R. You could also use "*p, but if you're faster at typing that than your normal paste I'm impressed.
Of course you could map that to something else, but again... why? You should get used to quickly getting into insert mode with i, I, a, A, o, O, s, S, c, and C so that you can be precise.

Vim: Replace selection with default buffer without overwriting the buffer

Here is my problem:
I am in visual mode.
I select text and copy it to the buffer. ((y)ank)
I select another text which I want to replace and paste the buffer. ((p)aste)
Now the second selection has been replaced in the buffer, however I want the first one to still sit in there.
Any ideas?
Often, this behavior is useful. When you don't want it, you can instead do the usual yank, then paste (officially, 'put') with "0p. You can do this however many times you like.
See :help v_p for more.
If you want to avoid the overwrite, you need to delete first. You can use "_ to select the blackhole buffer, then delete d, then paste before P and you'll avoid the buffer being set.
While this does not technically answer the question (not using default buffer) it does solve the symptom of the problem so I thought I would still share. I get around this issue with a solution to a different problem.
I have mapped "Copy, paste" (yank, put) from the system clipboard to "Ctrl-Shift-C, Ctrl-Shift-V" (Ctrl-C, Ctrl-V if caps lock is on). This can be used in place of y with the same effect.
If I use the system buffer for copy it does not get overwritten when I paste.
I added this to my .vimrc
vnoremap <C-V> "*p
vnoremap <C-C> "*y
As a bonus it will give you easy access to the system clipboard.

Resources