Super User is a question and answer site for computer enthusiasts and power users. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I like to start Emacs as part of a login script and leave it running for the duration of my login session (which is typically weeks).

I have scripts to call emacs-client which will allow me to use a file-manager or Windows Explorer to locate files and right-click to edit them in Emacs.

I often end up with a lot of emacs windows (frames) open and I like to just be able to close them by clicking on the MS-Windows or KDE X button at the top-right.

The trouble is, if the window is the last one, this will shut down emacs which will lose all kinds of interesting history information.

As a work-around I use C-x 5 0 which won't let me close the last frame but this is often not as convenient as using the mouse

Does anyone know how to configure Emacs so that it can intercept the Window-Close button of the last frame to either request confirmation or simply disallow it?

On MS-Windows, disallowing closing of the last window may cause logoff to hang if emacs is still running but I'm not too worried about that.

share|improve this question
up vote 4 down vote accepted

Two ways I can think of, but I'm sure there are more. The function that is called when you click the delete-frame button (upper-right corner [X] on Windows) is handle-delete-frame. You can advise that command or you can replace it as the function that handles that click by some other command.

To advise it:

    (defadvice handle-delete-frame (around my-handle-delete-frame-advice activate)
      "Ask for confirmation before deleting the last frame"
      (let ((frame   (posn-window (event-start event)))
            (numfrs  (length (visible-frame-list))))
        (when (or (> numfrs 1) (y-or-n-p "Really exit Emacs? "))

To replace it:

    (defun my-handle-delete-frame (event)
      "Ask for confirmation before deleting the last frame"
      (interactive "e")
      (let ((frame   (posn-window (event-start event)))
            (numfrs  (length (visible-frame-list))))
        (cond ((> numfrs 1) (delete-frame frame t))
              ((y-or-n-p "Really exit Emacs? ") (save-buffers-kill-emacs)))))

    (define-key special-event-map [delete-frame] 'my-handle-delete-frame)

Don't do both of these; just do one of them.

share|improve this answer
This seems to work well on Windows. I'll try it out for a few days and also in KDE before I accept your answer. – Adrian Pronk Aug 28 '11 at 22:40
Option 1 prompts when I close the last visible frame. I think I should use frame-list rather than visible-frame-list to prompt at the last frame. Or is there some tricky problem with using frame-list? – Adrian Pronk Aug 29 '11 at 9:58
Yes, you can use frame-list -- that makes more sense, actually. – Drew Sep 5 '11 at 23:15

You should use the emacs daemon: launch Emacs as

       emacs -d

Then Emacs will be launch in background, waiting for emacsclient to open a new windows. The Emacs daemon won't close when its last windows will be closed.

share|improve this answer
It looks like I'll be able to use emacs --daemon on Linux but NTEmacs doesn't seem to support that option. I'll keep at it... – Adrian Pronk Jul 11 '11 at 10:04

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .