13

I frequently extract a rectangle of text from a buffer, but then find I want to yank the text as if it was not a rectangle. Is there a way to add the current killed rectangle to the kill ring?

The GNU Emacs Manual has this to say:

“Killing” a rectangle is not killing in the usual sense; the rectangle is not stored in the kill ring, but in a special place that only records the most recent rectangle killed. This is because yanking a rectangle is so different from yanking linear text that different yank commands have to be used. Yank-popping is not defined for rectangles.

However, I can basically get the behavior I want with

  • M-> go to end of buffer
  • C-x r y yank rectangle
  • C-x C-x exchange point and mark (selects newly-yanked lines)
  • C-w kill the selection to the kill ring

Is there a better way to turn a killed rectangle into a kill-ring entry?

1

3 Answers 3

8

If I understood your question, your are looking to something like this:

(defun youngfrog/copy-rectangle-to-kill-ring (start end)
  "Saves a rectangle to the normal kill ring. Not suitable for yank-rectangle."
  (interactive "r")
  (let ((lines (extract-rectangle start end)))
    (with-temp-buffer
      (while lines ;; insert-rectangle, but without the unneeded stuff
        ;; (most importantly no push-mark)
        (insert-for-yank (car lines))
        (insert "\n")
        (setq lines (cdr lines)))
      (kill-ring-save (point-min) (point-max)))))

Courtesy of ErgoEmacs

3

Not sure what is special about having the rectangle in the kill-ring, but if you upgrade to Emacs-24.4, then you can do: C-x SPC .... M-w to select a rectangle and place it on the kill-ring. After that C-y will yank that rectangle (in the same was that C-x r y does, tho).

2
  • There are two things about the kill ring that are "special." The most important (to me) is the way that items from the kill ring are yanked. Simply put, the yank shifts existing text down instead of shifting it to the right. Using the kill ring also has the side benefit of maintaining a history of killed text. It sounds like 24.4 might provide the second benefit but not the first.
    – nispio
    Commented Nov 10, 2014 at 20:43
  • Ah, indeed, in that case the new behavior of 24.4 improves the part about which you don't care.
    – Stefan
    Commented Nov 10, 2014 at 21:17
2

I was initially annoyed by the lack of a built-in solution to this problem, then realized that there was a built-in solution: kill-rectangle.

Say you have text like

AAA BBBBBBBBB
AAA BBB
AAA BBBBBBB

But want the 'B' part of the text somewhere else, like between these C and D lines:

CCCCC
CCC
DDDD
DD

If you copy the B rectangle (C-x r M-w) and then place point at the first 'D', then yank the rectangle back (C-x r y), you end up with

CCCCC
CCC
BBBBBBBBBDDDD
BBB      DD
BBBBBBB  

where you really wanted

CCCCC
CCC
BBBBBBBBB
BBB
BBBBBBB
DDDD
DD

It might seem natural to copy the rectangle of 'B's and yank them to the new location, but a better solution is to simply copy the lines 'A and 'B' lines and and yank them in their entirety between the 'C' and 'D' lines.

Then, mark the rectangle containing the 'A's and use kill-rectangle (C-x r k) to end with the desired result.

1
  • Well, that's correct, but it has the downside of disturbing the locality of the operation. Imagine you were operating on a collection of very long lines and only wanted to snip off a tiny rectangle from the end of that collection. In order to mark the right set of lines you'd need to jump between the beginning and end of a long line, likely losing sight of the area in its entirety. Moreover, having pasted the lines as text you'd then need to perform a similarly unwieldy action to mark and kill the unwanted "prefix" rectangle. In short, it works, but it's not pretty. Commented Nov 13, 2020 at 16:26

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.