diff options
| author | Juanma Barranquero | 2013-07-22 03:25:47 +0200 |
|---|---|---|
| committer | Juanma Barranquero | 2013-07-22 03:25:47 +0200 |
| commit | a1c80d9d45a2182cf9c42904bd1cc418ac233977 (patch) | |
| tree | 64914c6da3623f6eb9df790627790b08d7694080 /lisp | |
| parent | 70f1b5e80dc89fae57cf7c97df915db99ca31237 (diff) | |
| download | emacs-a1c80d9d45a2182cf9c42904bd1cc418ac233977.tar.gz emacs-a1c80d9d45a2182cf9c42904bd1cc418ac233977.zip | |
lisp/desktop.el: Require 'cl-lib.
(desktop-before-saving-frames-functions): New hook.
(desktop--process-minibuffer-frames): Set desktop-mini parameter only
for frames being saved. Rename from desktop--save-minibuffer-frames.
(desktop-save-frames): Run hook desktop-before-saving-frames-functions.
Do not save frames with non-nil `desktop-dont-save' parameter. Filter
out deleted frames.
(desktop--find-frame): Use cl-find-if.
(desktop--select-frame): Use cl-(first|second|third) to access values
of desktop-mini.
(desktop--make-frame): Use cl-delete-if.
(desktop--sort-states): Fix sorting of minibuffer-owning frames.
(desktop-restore-frames): Use cl-(first|second|third) to access values
of desktop-mini. Look for visible frame at the end, not while
restoring frames.
Diffstat (limited to 'lisp')
| -rw-r--r-- | lisp/ChangeLog | 16 | ||||
| -rw-r--r-- | lisp/desktop.el | 117 |
2 files changed, 84 insertions, 49 deletions
diff --git a/lisp/ChangeLog b/lisp/ChangeLog index 1ea7c0d3c15..d1140d12a37 100644 --- a/lisp/ChangeLog +++ b/lisp/ChangeLog | |||
| @@ -1,5 +1,21 @@ | |||
| 1 | 2013-07-22 Juanma Barranquero <lekktu@gmail.com> | 1 | 2013-07-22 Juanma Barranquero <lekktu@gmail.com> |
| 2 | 2 | ||
| 3 | * desktop.el: Require 'cl-lib. | ||
| 4 | (desktop-before-saving-frames-functions): New hook. | ||
| 5 | (desktop--process-minibuffer-frames): Set desktop-mini parameter only | ||
| 6 | for frames being saved. Rename from desktop--save-minibuffer-frames. | ||
| 7 | (desktop-save-frames): Run hook desktop-before-saving-frames-functions. | ||
| 8 | Do not save frames with non-nil `desktop-dont-save' parameter. Filter | ||
| 9 | out deleted frames. | ||
| 10 | (desktop--find-frame): Use cl-find-if. | ||
| 11 | (desktop--select-frame): Use cl-(first|second|third) to access values | ||
| 12 | of desktop-mini. | ||
| 13 | (desktop--make-frame): Use cl-delete-if. | ||
| 14 | (desktop--sort-states): Fix sorting of minibuffer-owning frames. | ||
| 15 | (desktop-restore-frames): Use cl-(first|second|third) to access values | ||
| 16 | of desktop-mini. Look for visible frame at the end, not while | ||
| 17 | restoring frames. | ||
| 18 | |||
| 3 | * dired-x.el (dired-mark-unmarked-files, dired-virtual) | 19 | * dired-x.el (dired-mark-unmarked-files, dired-virtual) |
| 4 | (dired-guess-default, dired-mark-sexp, dired-filename-at-point): | 20 | (dired-guess-default, dired-mark-sexp, dired-filename-at-point): |
| 5 | Use string-match-p, looking-at-p (bug#14927). | 21 | Use string-match-p, looking-at-p (bug#14927). |
diff --git a/lisp/desktop.el b/lisp/desktop.el index 0f2ed2316fe..57a139ee7ee 100644 --- a/lisp/desktop.el +++ b/lisp/desktop.el | |||
| @@ -133,6 +133,8 @@ | |||
| 133 | 133 | ||
| 134 | ;;; Code: | 134 | ;;; Code: |
| 135 | 135 | ||
| 136 | (require 'cl-lib) | ||
| 137 | |||
| 136 | (defvar desktop-file-version "206" | 138 | (defvar desktop-file-version "206" |
| 137 | "Version number of desktop file format. | 139 | "Version number of desktop file format. |
| 138 | Written into the desktop file and used at desktop read to provide | 140 | Written into the desktop file and used at desktop read to provide |
| @@ -395,6 +397,13 @@ If `keep', existing frames are kept and not reused." | |||
| 395 | :group 'desktop | 397 | :group 'desktop |
| 396 | :version "24.4") | 398 | :version "24.4") |
| 397 | 399 | ||
| 400 | (defcustom desktop-before-saving-frames-functions nil | ||
| 401 | "Abnormal hook run before saving frames. | ||
| 402 | Functions in this hook are called with one argument, a live frame." | ||
| 403 | :type 'hook | ||
| 404 | :group 'desktop | ||
| 405 | :version "24.4") | ||
| 406 | |||
| 398 | (defcustom desktop-file-name-format 'absolute | 407 | (defcustom desktop-file-name-format 'absolute |
| 399 | "Format in which desktop file names should be saved. | 408 | "Format in which desktop file names should be saved. |
| 400 | Possible values are: | 409 | Possible values are: |
| @@ -1052,42 +1061,55 @@ Internal use only." | |||
| 1052 | (push desktop--target-display filtered)))) | 1061 | (push desktop--target-display filtered)))) |
| 1053 | filtered)) | 1062 | filtered)) |
| 1054 | 1063 | ||
| 1055 | (defun desktop--save-minibuffer-frames () | 1064 | (defun desktop--process-minibuffer-frames (frames) |
| 1056 | ;; Adds a desktop-mini parameter to frames | 1065 | ;; Adds a desktop-mini parameter to frames |
| 1057 | ;; desktop-mini is a list (MINIBUFFER NUMBER DEFAULT?) where | 1066 | ;; desktop-mini is a list (MINIBUFFER NUMBER DEFAULT?) where |
| 1058 | ;; MINIBUFFER t if the frame (including minibuffer-only) owns a minibuffer | 1067 | ;; MINIBUFFER t if the frame (including minibuffer-only) owns a minibuffer |
| 1059 | ;; NUMBER if MINIBUFFER = t, an ID for the frame; if nil, the ID of | 1068 | ;; NUMBER if MINIBUFFER = t, an ID for the frame; if nil, the ID of |
| 1060 | ;; the frame containing the minibuffer used by this frame | 1069 | ;; the frame containing the minibuffer used by this frame |
| 1061 | ;; DEFAULT? if t, this frame is the value of default-minibuffer-frame | 1070 | ;; DEFAULT? if t, this frame is the value of default-minibuffer-frame |
| 1062 | ;; FIXME: What happens with multi-terminal sessions? | 1071 | (let ((count 0)) |
| 1063 | (let ((frames (frame-list)) | ||
| 1064 | (count 0)) | ||
| 1065 | ;; Reset desktop-mini for all frames | 1072 | ;; Reset desktop-mini for all frames |
| 1066 | (dolist (frame frames) | 1073 | (dolist (frame (frame-list)) |
| 1067 | (set-frame-parameter frame 'desktop-mini nil)) | 1074 | (set-frame-parameter frame 'desktop-mini nil)) |
| 1068 | ;; Number all frames with its own minibuffer | 1075 | ;; Number all frames with its own minibuffer |
| 1069 | (dolist (frame (minibuffer-frame-list)) | 1076 | (dolist (frame (minibuffer-frame-list)) |
| 1070 | (set-frame-parameter frame 'desktop-mini | 1077 | (set-frame-parameter frame 'desktop-mini |
| 1071 | (list t | 1078 | (list t |
| 1072 | (setq count (1+ count)) | 1079 | (cl-incf count) |
| 1073 | (eq frame default-minibuffer-frame)))) | 1080 | (eq frame default-minibuffer-frame)))) |
| 1074 | ;; Now link minibufferless frames with their minibuffer frames | 1081 | ;; Now link minibufferless frames with their minibuffer frames |
| 1075 | (dolist (frame frames) | 1082 | (dolist (frame frames) |
| 1076 | (unless (frame-parameter frame 'desktop-mini) | 1083 | (unless (frame-parameter frame 'desktop-mini) |
| 1077 | (let* ((mb-frame (window-frame (minibuffer-window frame))) | 1084 | (let ((mb-frame (window-frame (minibuffer-window frame)))) |
| 1078 | (this (cadr (frame-parameter mb-frame 'desktop-mini)))) | 1085 | ;; Frames whose minibuffer frame has been filtered out will have |
| 1079 | (set-frame-parameter frame 'desktop-mini (list nil this nil))))))) | 1086 | ;; desktop-mini = nil, so desktop-restore-frames will restore them |
| 1087 | ;; according to their minibuffer parameter. Set up desktop-mini | ||
| 1088 | ;; for the rest. | ||
| 1089 | (when (memq mb-frame frames) | ||
| 1090 | (set-frame-parameter frame 'desktop-mini | ||
| 1091 | (list nil | ||
| 1092 | (cl-second (frame-parameter mb-frame 'desktop-mini)) | ||
| 1093 | nil)))))))) | ||
| 1080 | 1094 | ||
| 1081 | (defun desktop-save-frames () | 1095 | (defun desktop-save-frames () |
| 1082 | "Save frame state in `desktop-saved-frame-states'." | 1096 | "Save frame state in `desktop-saved-frame-states'. |
| 1097 | Runs the hook `desktop-before-saving-frames-functions'. | ||
| 1098 | Frames with a non-nil `desktop-dont-save' parameter are not saved." | ||
| 1083 | (setq desktop-saved-frame-states | 1099 | (setq desktop-saved-frame-states |
| 1084 | (and desktop-restore-frames | 1100 | (and desktop-restore-frames |
| 1085 | (progn | 1101 | (let ((frames (cl-delete-if |
| 1086 | (desktop--save-minibuffer-frames) | 1102 | (lambda (frame) |
| 1103 | (run-hook-with-args 'desktop-before-saving-frames-functions frame) | ||
| 1104 | (frame-parameter frame 'desktop-dont-save)) | ||
| 1105 | (frame-list)))) | ||
| 1106 | ;; In case some frame was deleted by a hook function | ||
| 1107 | (setq frames (cl-delete-if-not #'frame-live-p frames)) | ||
| 1108 | (desktop--process-minibuffer-frames frames) | ||
| 1087 | (mapcar (lambda (frame) | 1109 | (mapcar (lambda (frame) |
| 1088 | (cons (desktop--filter-frame-parms (frame-parameters frame) t) | 1110 | (cons (desktop--filter-frame-parms (frame-parameters frame) t) |
| 1089 | (window-state-get (frame-root-window frame) t))) | 1111 | (window-state-get (frame-root-window frame) t))) |
| 1090 | (frame-list)))))) | 1112 | frames))))) |
| 1091 | 1113 | ||
| 1092 | ;;;###autoload | 1114 | ;;;###autoload |
| 1093 | (defun desktop-save (dirname &optional release auto-save) | 1115 | (defun desktop-save (dirname &optional release auto-save) |
| @@ -1200,13 +1222,11 @@ Look through frames whose display property matches DISPLAY and | |||
| 1200 | return the first one for which (PREDICATE frame ARGS) returns t. | 1222 | return the first one for which (PREDICATE frame ARGS) returns t. |
| 1201 | If PREDICATE is nil, it is always satisfied. Internal use only. | 1223 | If PREDICATE is nil, it is always satisfied. Internal use only. |
| 1202 | This is an auxiliary function for `desktop--select-frame'." | 1224 | This is an auxiliary function for `desktop--select-frame'." |
| 1203 | (catch :found | 1225 | (cl-find-if (lambda (frame) |
| 1204 | (dolist (frame desktop--reuse-list) | 1226 | (and (equal (frame-parameter frame 'display) display) |
| 1205 | (when (and (equal (frame-parameter frame 'display) display) | 1227 | (or (null predicate) |
| 1206 | (or (null predicate) | 1228 | (apply predicate frame args)))) |
| 1207 | (apply predicate frame args))) | 1229 | desktop--reuse-list)) |
| 1208 | (throw :found frame))) | ||
| 1209 | nil)) | ||
| 1210 | 1230 | ||
| 1211 | (defun desktop--select-frame (display frame-cfg) | 1231 | (defun desktop--select-frame (display frame-cfg) |
| 1212 | "Look for an existing frame to reuse. | 1232 | "Look for an existing frame to reuse. |
| @@ -1241,13 +1261,13 @@ is the parameter list of the frame being restored. Internal use only." | |||
| 1241 | (lambda (f n) | 1261 | (lambda (f n) |
| 1242 | (let ((m (frame-parameter f 'desktop-mini))) | 1262 | (let ((m (frame-parameter f 'desktop-mini))) |
| 1243 | (and m | 1263 | (and m |
| 1244 | (null (car m)) | 1264 | (null (cl-first m)) |
| 1245 | (= (cadr m) n) | 1265 | (= (cl-second m) n) |
| 1246 | (equal (cadr (frame-parameter | 1266 | (equal (cl-second (frame-parameter |
| 1247 | (window-frame (minibuffer-window f)) | 1267 | (window-frame (minibuffer-window f)) |
| 1248 | 'desktop-mini)) | 1268 | 'desktop-mini)) |
| 1249 | n)))) | 1269 | n)))) |
| 1250 | display (cadr mini)))) | 1270 | display (cl-second mini)))) |
| 1251 | (;; Default to just finding a frame in the same display. | 1271 | (;; Default to just finding a frame in the same display. |
| 1252 | t | 1272 | t |
| 1253 | (setq frame (desktop--find-frame nil display)))) | 1273 | (setq frame (desktop--find-frame nil display)))) |
| @@ -1282,8 +1302,9 @@ its window state. Internal use only." | |||
| 1282 | (let ((width (and (eq fullscreen 'fullheight) (cdr (assq 'width filtered-cfg)))) | 1302 | (let ((width (and (eq fullscreen 'fullheight) (cdr (assq 'width filtered-cfg)))) |
| 1283 | (height (and (eq fullscreen 'fullwidth) (cdr (assq 'height filtered-cfg)))) | 1303 | (height (and (eq fullscreen 'fullwidth) (cdr (assq 'height filtered-cfg)))) |
| 1284 | (visible (assq 'visibility filtered-cfg))) | 1304 | (visible (assq 'visibility filtered-cfg))) |
| 1285 | (dolist (parameter '(visibility fullscreen width height)) | 1305 | (setq filtered-cfg (cl-delete-if (lambda (p) |
| 1286 | (setq filtered-cfg (assq-delete-all parameter filtered-cfg))) | 1306 | (memq p '(visibility fullscreen width height))) |
| 1307 | filtered-cfg)) | ||
| 1287 | (when width | 1308 | (when width |
| 1288 | (setq filtered-cfg (append `((user-size . t) (width . ,width)) | 1309 | (setq filtered-cfg (append `((user-size . t) (width . ,width)) |
| 1289 | filtered-cfg))) | 1310 | filtered-cfg))) |
| @@ -1312,11 +1333,12 @@ its window state. Internal use only." | |||
| 1312 | ;; minibufferless frames, ascending ID | 1333 | ;; minibufferless frames, ascending ID |
| 1313 | (let ((dm1 (cdr (assq 'desktop-mini (car state1)))) | 1334 | (let ((dm1 (cdr (assq 'desktop-mini (car state1)))) |
| 1314 | (dm2 (cdr (assq 'desktop-mini (car state2))))) | 1335 | (dm2 (cdr (assq 'desktop-mini (car state2))))) |
| 1315 | (cond ((nth 2 dm1) t) | 1336 | (cond ((cl-third dm1) t) |
| 1316 | ((nth 2 dm2) nil) | 1337 | ((cl-third dm2) nil) |
| 1317 | ((null (car dm2)) t) | 1338 | ((eq (cl-first dm1) (cl-first dm2)) |
| 1318 | ((null (car dm1)) nil) | 1339 | (< (cl-second dm1) (cl-second dm2))) |
| 1319 | (t (< (cadr dm1) (cadr dm2)))))) | 1340 | (t |
| 1341 | (cl-first dm1))))) | ||
| 1320 | 1342 | ||
| 1321 | (defun desktop-restoring-frames-p () | 1343 | (defun desktop-restoring-frames-p () |
| 1322 | "True if calling `desktop-restore-frames' will actually restore frames." | 1344 | "True if calling `desktop-restore-frames' will actually restore frames." |
| @@ -1328,7 +1350,6 @@ This function depends on the value of `desktop-saved-frame-states' | |||
| 1328 | being set (usually, by reading it from the desktop)." | 1350 | being set (usually, by reading it from the desktop)." |
| 1329 | (when (desktop-restoring-frames-p) | 1351 | (when (desktop-restoring-frames-p) |
| 1330 | (let* ((frame-mb-map nil) ;; Alist of frames with their own minibuffer | 1352 | (let* ((frame-mb-map nil) ;; Alist of frames with their own minibuffer |
| 1331 | (visible nil) | ||
| 1332 | (delete-saved (eq desktop-restore-in-current-display 'delete)) | 1353 | (delete-saved (eq desktop-restore-in-current-display 'delete)) |
| 1333 | (forcing (not (desktop-restore-in-original-display-p))) | 1354 | (forcing (not (desktop-restore-in-original-display-p))) |
| 1334 | (target (and forcing (cons 'display (frame-parameter nil 'display))))) | 1355 | (target (and forcing (cons 'display (frame-parameter nil 'display))))) |
| @@ -1369,15 +1390,15 @@ being set (usually, by reading it from the desktop)." | |||
| 1369 | (cond | 1390 | (cond |
| 1370 | ((null d-mini)) ;; No desktop-mini. Process as normal frame. | 1391 | ((null d-mini)) ;; No desktop-mini. Process as normal frame. |
| 1371 | (to-tty) ;; Ignore minibuffer stuff and process as normal frame. | 1392 | (to-tty) ;; Ignore minibuffer stuff and process as normal frame. |
| 1372 | ((car d-mini) ;; Frame has its own minibuffer (or it is minibuffer-only). | 1393 | ((cl-first d-mini) ;; Frame has minibuffer (or it is minibuffer-only). |
| 1373 | (setq num (cadr d-mini)) | 1394 | (setq num (cl-second d-mini)) |
| 1374 | (when (eq (cdr (assq 'minibuffer frame-cfg)) 'only) | 1395 | (when (eq (cdr (assq 'minibuffer frame-cfg)) 'only) |
| 1375 | (setq frame-cfg (append '((tool-bar-lines . 0) (menu-bar-lines . 0)) | 1396 | (setq frame-cfg (append '((tool-bar-lines . 0) (menu-bar-lines . 0)) |
| 1376 | frame-cfg)))) | 1397 | frame-cfg)))) |
| 1377 | (t ;; Frame depends on other frame's minibuffer window. | 1398 | (t ;; Frame depends on other frame's minibuffer window. |
| 1378 | (let ((mb-frame (cdr (assq (cadr d-mini) frame-mb-map)))) | 1399 | (let ((mb-frame (cdr (assq (cl-second d-mini) frame-mb-map)))) |
| 1379 | (unless (frame-live-p mb-frame) | 1400 | (unless (frame-live-p mb-frame) |
| 1380 | (error "Minibuffer frame %s not found" (cadr d-mini))) | 1401 | (error "Minibuffer frame %s not found" (cl-second d-mini))) |
| 1381 | (let ((mb-param (assq 'minibuffer frame-cfg)) | 1402 | (let ((mb-param (assq 'minibuffer frame-cfg)) |
| 1382 | (mb-window (minibuffer-window mb-frame))) | 1403 | (mb-window (minibuffer-window mb-frame))) |
| 1383 | (unless (and (window-live-p mb-window) | 1404 | (unless (and (window-live-p mb-window) |
| @@ -1390,12 +1411,9 @@ being set (usually, by reading it from the desktop)." | |||
| 1390 | ;; restore the window config. | 1411 | ;; restore the window config. |
| 1391 | (setq frame (desktop--make-frame frame-cfg window-cfg)) | 1412 | (setq frame (desktop--make-frame frame-cfg window-cfg)) |
| 1392 | ;; Set default-minibuffer if required. | 1413 | ;; Set default-minibuffer if required. |
| 1393 | (when (nth 2 d-mini) (setq default-minibuffer-frame frame)) | 1414 | (when (cl-third d-mini) (setq default-minibuffer-frame frame)) |
| 1394 | ;; Store frame/NUM to assign to minibufferless frames. | 1415 | ;; Store frame/NUM to assign to minibufferless frames. |
| 1395 | (when num (push (cons num frame) frame-mb-map)) | 1416 | (when num (push (cons num frame) frame-mb-map)))) |
| 1396 | ;; Try to locate at least one visible frame. | ||
| 1397 | (when (and (not visible) (frame-visible-p frame)) | ||
| 1398 | (setq visible frame)))) | ||
| 1399 | (error | 1417 | (error |
| 1400 | (delay-warning 'desktop (error-message-string err) :error)))) | 1418 | (delay-warning 'desktop (error-message-string err) :error)))) |
| 1401 | 1419 | ||
| @@ -1405,12 +1423,13 @@ being set (usually, by reading it from the desktop)." | |||
| 1405 | (ignore-errors (delete-frame frame)))) | 1423 | (ignore-errors (delete-frame frame)))) |
| 1406 | (setq desktop--reuse-list nil) | 1424 | (setq desktop--reuse-list nil) |
| 1407 | ;; Make sure there's at least one visible frame, and select it. | 1425 | ;; Make sure there's at least one visible frame, and select it. |
| 1408 | (unless (or visible (daemonp)) | 1426 | (unless (or (daemonp) |
| 1409 | (setq visible (if (frame-live-p default-minibuffer-frame) | 1427 | (cl-find-if #'frame-visible-p (frame-list))) |
| 1410 | default-minibuffer-frame | 1428 | (let ((visible (if (frame-live-p default-minibuffer-frame) |
| 1411 | (car (frame-list)))) | 1429 | default-minibuffer-frame |
| 1412 | (make-frame-visible visible) | 1430 | (car (frame-list))))) |
| 1413 | (select-frame-set-input-focus visible))))) | 1431 | (make-frame-visible visible) |
| 1432 | (select-frame-set-input-focus visible)))))) | ||
| 1414 | 1433 | ||
| 1415 | ;;;###autoload | 1434 | ;;;###autoload |
| 1416 | (defun desktop-read (&optional dirname) | 1435 | (defun desktop-read (&optional dirname) |