3

I have some long text on Yank var e.g. "Hello all how are you ?"

I have a rectangular selection between abc and ABC /a llC-vjj

a A
b B
C C

And I want to past my long text without having to type it

To get this:

a Hello all how are you ? A
b Hello all how are you ? B
c Hello all how are you ? C

From @christian-Brabandt I select (| is where my cursor is) not the line but characters like this:

|Hello how are you ?
vllllllllllllllllllly

then I put the cursor on 'a'

a A
b B
C C

and press 'p'

I got

aHello how are you ? A
b B
C C

So with this method I have to add a space with i <ESC>, go on b type pi <ESC> go on c` ...

Not optimal because not using the block selection ;(

2
  • 2
    I would say: "Just hit p." But I guess that is not what you want. Could you please provide a example of the result you want to achieve?
    – Ralf
    Apr 14, 2019 at 22:18
  • Depending on the register content, you might have to first set the register to blockwise or characterwise before pasting, e.g. like this (assuming your yanked text is in register a: call setreg("a", getreg("a"), 'v') Apr 15, 2019 at 8:19

2 Answers 2

3

It is not very clear from the question, what the goal is (e.g. what the final result should look like). So let me describe what you can do.

First, store your text in register a:

:let @a='Hello all how are you ?'

A register does not only store text, it also remembers whether it has been used in line wise, character wise or block wise mode. You can influence this using the 3rd argument of the setreg() function.

Now with a sample like this:

a A
b B
c C

enter image description here

  1. Pasting in character wise mode

After 1), the register content will be in character wise mode, as :echo getregtype('a') confirms. So block selecting the empty space after the capital letters (1gg$<c-v>2j) and hitting "ap will result in: enter image description here

  1. Pasting in line wise mode

Change the register a to be linewise: call setreg('a', getreg('a'), 'l') Now, block select the empty space after the capital letters (1gg$<c-v>2j) and hitting "ap will result in: enter image description here

  1. Pasting in block wise mode

Change the register a to be linewise: call setreg('a', getreg('a'), 'b') Now, block select the empty space after the capital letters (1gg$<c-v>2j) and hitting "ap will result in: enter image description here

So you need to define, how register should be handled and you might need to change the register type if needed.

Note, there also exist plugins to make handling this easier. Ingo Karkat maintains a plugin UnconditionalPaste, that can be used to force pasting a register with a different type.

2
  • Thank you for all the details, this is very helpful. +1. Sadly, this means I first followed your suggestion correctly: with gvim 7.4, the version I was using to test, the paste is only on the first line, even with the register in character mode. I now tested with gvim 8.1.1 and it works as you describe, pasting on each line as desired. I think it's time I update my gvim on all machines.
    – joanis
    Apr 16, 2019 at 20:17
  • Just did some research, and it looks like you implemented Patch 7.4.199 making all this work. If I'm reading the doc correctly, this patch has been available since vim 8.0.
    – joanis
    Apr 16, 2019 at 20:32
2

TL;DR

You can accomplish this by using q to record a sequence of operations and @ to replay it.

Assumptions

I think you want this output:

a Hello all how are you ? A
b Hello all how are you ? B
c Hello all how are you ? C

A paste like you describe would be quite a useful feature, I agree, but I did some tests and I don't see how to do it in my vim 7.4 installation.

Recording as a solution

The solution I found uses q to record pasting the line once, and then replaying the recorded commands twice:

Set the cursor on A and record doing the insertion once:

q1P6bjq

Explanation:

  • q1: start recording into register 1
  • P: insert the text - you could type it out, as well
  • 6bj: place the cursor on B to be ready to paste on the next line
  • q: stop recording

Then replay register 1 twice, or however many times are needed:

2@1

Before replaying, make sure the cursor is still on B, and things should work.

I agree, this is not nearly as nice as a block-duplicated paste as you describe in the question, but it works.

vim 8

PS: with Vim 8 or more recent, a simple paste over a block selection is likely to work. See @ChristianBrabandt's answer for more details.

9
  • I would add that you can execute a macro on lines matching a text. So say you have your Hello all how are you ? yanked in the " register, and you have a macro as the one described in this answer, you can do: :g/\w /norm! @1 Which will execute the macro on every lines matching the regex ^\w . This would avoid the 2@1 in case you have way more than 2 line to cover, and to not have to count them.
    – padawin
    Apr 15, 2019 at 13:50
  • In my case, the macro I did to do it was 0a <c-o>P<esc>
    – padawin
    Apr 15, 2019 at 13:52
  • Why are you saying there is no solution to achieve that. I can just make a visual-block between the small and capital letters and press p assuming that the line Hello all how are you ? is already on the unnamed register.
    – 3N4N
    Apr 15, 2019 at 14:01
  • @klaus When I tried that, it pasted on the first line, not on all the lines. The rest of the visually selected block was deleted but not replaced. The problem is that I have one line in the buffer, not an actual block.
    – joanis
    Apr 15, 2019 at 14:34
  • As mentioned in my comment, this happens because your register is not of type charwise. Apr 15, 2019 at 15:12

Your Answer

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

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