Fix `exwm-manage--kill-buffer-query-function'

* exwm-manage.el (exwm-manage--kill-buffer-query-function): Check
buffer-local variables for destroyed X windows; Avoid force killing
clients that support WM_DELETE_WINDOW but not _NET_WM_PING; Use
`y-or-n-p' instead for querying.
This commit is contained in:
Chris Feng 2016-09-25 19:54:13 +08:00
parent 6be75083c2
commit 7fbd5220f2

View file

@ -449,14 +449,19 @@ manager is shutting down."
(defun exwm-manage--kill-buffer-query-function () (defun exwm-manage--kill-buffer-query-function ()
"Run in `kill-buffer-query-functions'." "Run in `kill-buffer-query-functions'."
(catch 'return (catch 'return
(when (xcb:+request-checked+request-check exwm--connection (when (or (not exwm--id)
(make-instance 'xcb:MapWindow :window exwm--id)) (not exwm--container)
(xcb:+request-checked+request-check exwm--connection
(make-instance 'xcb:MapWindow
:window exwm--id)))
;; The X window is no longer alive so just close the buffer. ;; The X window is no longer alive so just close the buffer.
;; Destroy the container. ;; Destroy the container.
;; Hide the container to prevent flickering. ;; Hide the container to prevent flickering.
(xcb:+request exwm--connection (when exwm--container
(make-instance 'xcb:UnmapWindow :window exwm--container)) (xcb:+request exwm--connection
(xcb:flush exwm--connection) (make-instance 'xcb:UnmapWindow
:window exwm--container))
(xcb:flush exwm--connection))
(when exwm--floating-frame (when exwm--floating-frame
(let ((window (frame-parameter exwm--floating-frame 'exwm-outer-id))) (let ((window (frame-parameter exwm--floating-frame 'exwm-outer-id)))
(xcb:+request exwm--connection (xcb:+request exwm--connection
@ -466,8 +471,10 @@ manager is shutting down."
:window window :window window
:parent exwm--root :parent exwm--root
:x 0 :y 0)))) :x 0 :y 0))))
(xcb:+request exwm--connection (when exwm--container
(make-instance 'xcb:DestroyWindow :window exwm--container)) (xcb:+request exwm--connection
(make-instance 'xcb:DestroyWindow
:window exwm--container)))
(xcb:flush exwm--connection) (xcb:flush exwm--connection)
(throw 'return t)) (throw 'return t))
(unless (memq xcb:Atom:WM_DELETE_WINDOW exwm--protocols) (unless (memq xcb:Atom:WM_DELETE_WINDOW exwm--protocols)
@ -492,15 +499,8 @@ manager is shutting down."
(xcb:flush exwm--connection) (xcb:flush exwm--connection)
;; ;;
(unless (memq xcb:Atom:_NET_WM_PING exwm--protocols) (unless (memq xcb:Atom:_NET_WM_PING exwm--protocols)
;; The window does not support _NET_WM_PING. To make sure it'll die, ;; For X windows without _NET_WM_PING support, we'd better just
;; kill it after the time runs out. ;; wait for DestroyNotify events.
;; Hide the container to prevent flickering.
(xcb:+request exwm--connection
(make-instance 'xcb:UnmapWindow :window exwm--container))
(xcb:flush exwm--connection)
(run-with-timer exwm-manage-ping-timeout nil #'exwm-manage--kill-client
id)
;; Wait for DestroyNotify event.
(throw 'return nil)) (throw 'return nil))
;; Try to determine if the X window is dead with _NET_WM_PING. ;; Try to determine if the X window is dead with _NET_WM_PING.
(setq exwm-manage--ping-lock t) (setq exwm-manage--ping-lock t)
@ -517,7 +517,7 @@ manager is shutting down."
exwm--connection))) exwm--connection)))
(xcb:flush exwm--connection) (xcb:flush exwm--connection)
(with-timeout (exwm-manage-ping-timeout (with-timeout (exwm-manage-ping-timeout
(if (yes-or-no-p (format "'%s' is not responding. \ (if (y-or-n-p (format "'%s' is not responding. \
Would you like to kill it? " Would you like to kill it? "
(buffer-name))) (buffer-name)))
(progn (exwm-manage--kill-client id) (progn (exwm-manage--kill-client id)