Is there a function I could use to quickly copy the message in the echo area (if any) into my working buffer? Should I define the shortcut for that function with define-key or global-set-key or some other way?

  • Are you sure the minibuffer is what you want to copy? Which buffers to you want to act on exactly: from the minibuffer associated with the current window to the current buffer? Sep 6 '14 at 22:36
  • @Gilles correct; my use case is that I want to do a C-c+z (which I've bound to show-file-name) and then copy that content (i.e. the current file name) to my current buffer. Or that I can type in the buffer an expression like (/ 30.0 7.0), hit C-x C-e and copy the result to my buffer without having to copy the digits with the mouse. Sep 6 '14 at 22:49
  • 1
    So what you want then isn't the minibuffer contents. The minibuffer is where you type stuff, e.g. a file name when opening a file with C-x C-f. Messages from Emacs also appear in the echo area but they're called messages. Sep 6 '14 at 23:07
  • @Gilles I guess you're right. I was confused because of it being the same spot. Thanks for updating the question. Sep 6 '14 at 23:14

The function current-message returns the message that is currently displayed in the echo area, if any. You can insert it with (insert (current-message)). However, anything that causes something else to occupy the echo area will cause current-message to return nil.

Messages from Emacs are archived in the *Messages* buffer. It would be more useful to grab the last line from there. This isn't perfectly reliable since it's possible to have a multi-line message, but that's rare: the message function is meant for short messages that fit in one line.

The following function inserts the last message (more precisely, the last line from the *Messages* buffer. With a prefix argument, it returns older messages: 1 for the latest message, 2 for the next-to-last one, etc. The argument 0 inserts (current-message) if any.

(defun last-message (&optional num)
  (or num (setq num 1))
  (if (= num 0)
      (set-buffer "*Messages*")
    (forward-line (- 1 num))
    (let ((end (point)))
      (forward-line 0)
      (buffer-substring-no-properties (point) end))))))
(defun insert-last-message (&optional num)
  (interactive "*p")
  (insert (last-message num)))

Bind it to a key in the normal way. For example, if you want the command available on C-c m at all times:

(global-set-key "\C-cm" 'insert-last-message)

There may be easier ways than invoking two custom commands to insert the file name, see the Emacs wiki.

To insert the output from evaluating a Lisp snippet with C-x C-e, pass a prefix argument: C-u C-x C-e.

  • 1
    Good but would be nice if it handled multi-line messages. Aug 6 '18 at 14:50
  • I multi-line messages would be great, but I think that it would be even cooler to be able to cycle among the previous messages!
    – Nisba
    Aug 30 '18 at 15:02

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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