Mercurial > emacs
comparison lisp/desktop.el @ 52674:7490e5357dba
A lot of comments updated.
(desktop-save-mode): Minor mode introduced.
(desktop-enable, desktop-clear-preserve-buffers): Variables made obsolete.
(desktop-load-default): Function made obsolete.
(desktop-locals-to-save): Variable made customizable.
(desktop-read): Optional parameter `dirname' added.
(desktop-change-dir, desktop-revert): Parameter `dirname' in `desktop-read' used.
(desktop-save-in-load-dir): Renamed to `desktop-save-in-desktop-dir'.
author | Lars Hansen <larsh@soem.dk> |
---|---|
date | Tue, 30 Sep 2003 07:22:22 +0000 |
parents | 6d5981c8551c |
children | c9843219861e |
comparison
equal
deleted
inserted
replaced
52673:0d905c2ca814 | 52674:7490e5357dba |
---|---|
35 ;; - the point | 35 ;; - the point |
36 ;; - the mark & mark-active | 36 ;; - the mark & mark-active |
37 ;; - buffer-read-only | 37 ;; - buffer-read-only |
38 ;; - some local variables | 38 ;; - some local variables |
39 | 39 |
40 ;; To use this, add these lines to the bottom of your .emacs file: | 40 ;; To use this, use customize to turn on desktop-save-mode or add the |
41 ;; following line somewhere in your .emacs file: | |
41 ;; | 42 ;; |
42 ;; (require 'desktop) | 43 ;; (desktop-save-mode 1) |
43 ;; (setq desktop-enable t) | |
44 ;; | 44 ;; |
45 ;; Between the first two lines you may wish to add something that updates the | 45 ;; For further usage information, look at the section |
46 ;; variables `desktop-globals-to-save' and/or `desktop-locals-to-save'. If | 46 ;; "Saving Emacs Sessions" in the GNU Emacs Manual. |
47 ;; for instance you want to save the local variable `foobar' for every buffer | 47 |
48 ;; in which it is local, you could add the line | 48 ;; When the desktop module is loaded, the function `desktop-kill' is |
49 ;; | 49 ;; added to the `kill-emacs-hook'. This function is responsible for |
50 ;; (add-to-list 'desktop-locals-to-save 'foobar) | 50 ;; saving the desktop when Emacs is killed. Furthermore an anonymous |
51 ;; | 51 ;; function is added to the `after-init-hook'. This function is |
52 ;; To avoid saving excessive amounts of data you may also wish to add | 52 ;; responsible for loading the desktop when Emacs is started. |
53 ;; something like the following | |
54 ;; | |
55 ;; (add-hook 'kill-emacs-hook | |
56 ;; '(lambda () | |
57 ;; (desktop-truncate search-ring 3) | |
58 ;; (desktop-truncate regexp-search-ring 3))) | |
59 ;; | |
60 ;; which will make sure that no more than three search items are saved. You | |
61 ;; must place this line *after* the `(desktop-load-default)' line. See also | |
62 ;; the variable `desktop-save-hook'. | |
63 | |
64 ;; Start Emacs in the root directory of your "project". The desktop saver | |
65 ;; is inactive by default. You activate it by M-x desktop-save RET. When | |
66 ;; you exit the next time the above data will be saved. This ensures that | |
67 ;; all the files you were editing will be reloaded the next time you start | |
68 ;; Emacs from the same directory and that points will be set where you | |
69 ;; left them. If you save a desktop file in your home directory it will | |
70 ;; act as a default desktop when you start Emacs from a directory that | |
71 ;; doesn't have its own. I never do this, but you may want to. | |
72 | 53 |
73 ;; Some words on minor modes: Most minor modes are controlled by | 54 ;; Some words on minor modes: Most minor modes are controlled by |
74 ;; buffer-local variables, which have a standard save / restore | 55 ;; buffer-local variables, which have a standard save / restore |
75 ;; mechanism. To handle all minor modes, we take the following | 56 ;; mechanism. To handle all minor modes, we take the following |
76 ;; approach: (1) check whether the variable name from | 57 ;; approach: (1) check whether the variable name from |
119 | 100 |
120 (defgroup desktop nil | 101 (defgroup desktop nil |
121 "Save status of Emacs when you exit." | 102 "Save status of Emacs when you exit." |
122 :group 'frames) | 103 :group 'frames) |
123 | 104 |
124 (defcustom desktop-enable nil | 105 ;;;###autoload |
125 "*Non-nil enable Desktop to save the state of Emacs when you exit." | 106 (define-minor-mode desktop-save-mode |
126 :group 'desktop | 107 "Toggle desktop saving mode. |
127 :type 'boolean | 108 With numeric ARG, turn desktop saving on if ARG is positive, off |
128 :require 'desktop | 109 otherwise. See variable `desktop-save' for a description of when the |
129 :initialize 'custom-initialize-default | 110 desktop is saved." |
130 :version "20.3") | 111 :global t |
112 :group 'desktop) | |
113 | |
114 ;; Maintained for backward compatibility | |
115 (defvaralias 'desktop-enable 'desktop-save-mode) | |
116 (make-obsolete-variable 'desktop-enable 'desktop-save-mode) | |
131 | 117 |
132 (defcustom desktop-save 'ask-if-new | 118 (defcustom desktop-save 'ask-if-new |
133 "*When the user changes desktop or quits emacs, should the desktop be saved? | 119 "*Specifies whether the desktop should be saved when it is killed. |
134 \(in the current desktop directory) | 120 A desktop is killed when the user changes desktop or quits Emacs. |
121 Possible values are: | |
135 t -- always save. | 122 t -- always save. |
136 ask -- always ask. | 123 ask -- always ask. |
137 ask-if-new -- ask if no desktop file exists, otherwise just save. | 124 ask-if-new -- ask if no desktop file exists, otherwise just save. |
138 ask-if-exists -- ask if desktop file exists, otherwise don't save. | 125 ask-if-exists -- ask if desktop file exists, otherwise don't save. |
139 if-exists -- save if desktop file exists, otherwise don't save. | 126 if-exists -- save if desktop file exists, otherwise don't save. |
140 nil -- never save. | 127 nil -- never save. |
141 The desktop is never saved when `desktop-enable' is nil." | 128 The desktop is never saved when `desktop-save-mode' is nil. |
129 The variables `desktop-directory' and `desktop-base-file-name' | |
130 determine where the desktop is saved." | |
142 :type '(choice | 131 :type '(choice |
143 (const :tag "Always save" t) | 132 (const :tag "Always save" t) |
144 (const :tag "Always ask" ask) | 133 (const :tag "Always ask" ask) |
145 (const :tag "Ask if desktop file is new, else do save" ask-if-new) | 134 (const :tag "Ask if desktop file is new, else do save" ask-if-new) |
146 (const :tag "Ask if desktop file exists, else don't save" ask-if-exists) | 135 (const :tag "Ask if desktop file exists, else don't save" ask-if-exists) |
148 (const :tag "Never save" nil)) | 137 (const :tag "Never save" nil)) |
149 :group 'desktop) | 138 :group 'desktop) |
150 | 139 |
151 (defcustom desktop-base-file-name | 140 (defcustom desktop-base-file-name |
152 (convert-standard-filename ".emacs.desktop") | 141 (convert-standard-filename ".emacs.desktop") |
153 "File for Emacs desktop, not including the directory name." | 142 "Name of file for Emacs desktop, excluding the directory part." |
154 :type 'file | 143 :type 'file |
155 :group 'desktop) | 144 :group 'desktop) |
156 (defvaralias 'desktop-basefilename 'desktop-base-file-name) | 145 (defvaralias 'desktop-basefilename 'desktop-base-file-name) |
157 | 146 |
158 (defcustom desktop-path '("." "~") | 147 (defcustom desktop-path '("." "~") |
160 The base name of the file is specified in `desktop-base-file-name'." | 149 The base name of the file is specified in `desktop-base-file-name'." |
161 :type '(repeat directory) | 150 :type '(repeat directory) |
162 :group 'desktop) | 151 :group 'desktop) |
163 | 152 |
164 (defcustom desktop-missing-file-warning nil | 153 (defcustom desktop-missing-file-warning nil |
165 "*If non-nil then desktop warns when a file no longer exists. | 154 "*If non-nil then `desktop-read' warns when a file no longer exists. |
166 Otherwise it simply ignores that file." | 155 Otherwise it simply ignores that file." |
167 :type 'boolean | 156 :type 'boolean |
168 :group 'desktop) | 157 :group 'desktop) |
169 | 158 |
170 (defcustom desktop-no-desktop-file-hook nil | 159 (defcustom desktop-no-desktop-file-hook nil |
171 "Normal hook run after fail of `desktop-read' due to missing desktop file. | 160 "Normal hook run when `desktop-read' can't find a desktop file. |
172 May e.g. be used to show a dired buffer." | 161 May e.g. be used to show a dired buffer." |
173 :type 'hook | 162 :type 'hook |
174 :group 'desktop) | 163 :group 'desktop) |
175 | 164 |
176 (defcustom desktop-after-read-hook nil | 165 (defcustom desktop-after-read-hook nil |
178 May e.g. be used to show a buffer list." | 167 May e.g. be used to show a buffer list." |
179 :type 'hook | 168 :type 'hook |
180 :group 'desktop) | 169 :group 'desktop) |
181 | 170 |
182 (defcustom desktop-save-hook nil | 171 (defcustom desktop-save-hook nil |
183 "Hook run before desktop saves the state of Emacs. | 172 "Normal hook run before the desktop is saved in a desktop file. |
184 This is useful for truncating history lists, for example." | 173 This is useful for truncating history lists, for example." |
185 :type 'hook | 174 :type 'hook |
186 :group 'desktop) | 175 :group 'desktop) |
187 | 176 |
188 (defcustom desktop-globals-to-save '( | 177 (defcustom desktop-globals-to-save '( |
190 tags-file-name | 179 tags-file-name |
191 tags-table-list | 180 tags-table-list |
192 search-ring | 181 search-ring |
193 regexp-search-ring | 182 regexp-search-ring |
194 register-alist) | 183 register-alist) |
195 "List of global variables to save when killing Emacs. | 184 "List of global variables saved by `desktop-save'. |
196 An element may be variable name (a symbol) | 185 An element may be variable name (a symbol) or a cons cell of the form |
197 or a cons cell of the form (VAR . MAX-SIZE), | 186 \(VAR . MAX-SIZE), which means to truncate VAR's value to at most |
198 which means to truncate VAR's value to at most MAX-SIZE elements | 187 MAX-SIZE elements (if the value is a list) before saving the value. |
199 \(if the value is a list) before saving the value. | |
200 Feature: Saving `kill-ring' implies saving `kill-ring-yank-pointer'." | 188 Feature: Saving `kill-ring' implies saving `kill-ring-yank-pointer'." |
201 :type '(repeat (restricted-sexp :match-alternatives (symbolp consp))) | 189 :type '(repeat (restricted-sexp :match-alternatives (symbolp consp))) |
202 :group 'desktop) | 190 :group 'desktop) |
203 | 191 |
204 (defcustom desktop-globals-to-clear '( | 192 (defcustom desktop-globals-to-clear '( |
206 kill-ring-yank-pointer | 194 kill-ring-yank-pointer |
207 search-ring | 195 search-ring |
208 search-ring-yank-pointer | 196 search-ring-yank-pointer |
209 regexp-search-ring | 197 regexp-search-ring |
210 regexp-search-ring-yank-pointer) | 198 regexp-search-ring-yank-pointer) |
211 "List of global variables set to clear by `desktop-clear'. | 199 "List of global variables to clear by `desktop-clear'. |
212 An element may be variable name (a symbol) or a cons cell of the form | 200 An element may be variable name (a symbol) or a cons cell of the form |
213 \(VAR . FORM). Symbols are set to nil and for cons cells VAR is set | 201 \(VAR . FORM). Symbols are set to nil and for cons cells VAR is set |
214 to the value obtained by evaluateing FORM." | 202 to the value obtained by evaluateing FORM." |
215 :type '(repeat (restricted-sexp :match-alternatives (symbolp consp))) | 203 :type '(repeat (restricted-sexp :match-alternatives (symbolp consp))) |
216 :group 'desktop) | 204 :group 'desktop) |
217 | 205 |
218 (defcustom desktop-clear-preserve-buffers-regexp | 206 (defcustom desktop-clear-preserve-buffers-regexp |
219 "^\\*tramp/.+\\*$" | 207 "^\\(\\*scratch\\*\\|\\*Messages\\*\\|\\*tramp/.+\\*\\)$" |
220 "Regexp identifying buffers that `desktop-clear' should not delete." | 208 "Regexp identifying buffers that `desktop-clear' should not delete." |
221 :type 'regexp | 209 :type 'regexp |
222 :group 'desktop) | 210 :group 'desktop) |
223 | 211 |
224 ;; Maintained for backward compatibility | 212 ;; Maintained for backward compatibility |
225 (defcustom desktop-clear-preserve-buffers | 213 (defcustom desktop-clear-preserve-buffers nil |
226 '("*scratch*" "*Messages*") | 214 "*List of buffer names that `desktop-clear' should not delete. |
227 "*List of buffer names that `desktop-clear' should not delete." | 215 This variable is maintained for backward compatibility only. Use |
216 `desktop-clear-preserve-buffers-regexp' instead." | |
228 :type '(repeat string) | 217 :type '(repeat string) |
229 :group 'desktop) | 218 :group 'desktop) |
230 | 219 (make-obsolete-variable 'desktop-clear-preserve-buffers |
231 (defvar desktop-locals-to-save '( | 220 'desktop-clear-preserve-buffers-regexp) |
221 | |
222 (defcustom desktop-locals-to-save '( | |
232 desktop-locals-to-save ; Itself! Think it over. | 223 desktop-locals-to-save ; Itself! Think it over. |
233 truncate-lines | 224 truncate-lines |
234 case-fold-search | 225 case-fold-search |
235 case-replace | 226 case-replace |
236 fill-column | 227 fill-column |
237 overwrite-mode | 228 overwrite-mode |
238 change-log-default-name | 229 change-log-default-name |
239 line-number-mode) | 230 line-number-mode) |
240 "List of local variables to save for each buffer. | 231 "List of local variables to save for each buffer. |
241 The variables are saved only when they really are local.") | 232 The variables are saved only when they really are local." |
233 :type '(repeat symbol) | |
234 :group 'desktop) | |
242 (make-variable-buffer-local 'desktop-locals-to-save) | 235 (make-variable-buffer-local 'desktop-locals-to-save) |
243 | 236 |
244 ;; We skip .log files because they are normally temporary. | 237 ;; We skip .log files because they are normally temporary. |
245 ;; (ftp) files because they require passwords and whatnot. | 238 ;; (ftp) files because they require passwords and whatnot. |
246 ;; TAGS files to save time (tags-file-name is saved instead). | 239 ;; TAGS files to save time (tags-file-name is saved instead). |
248 "\\(^nn\\.a[0-9]+\\|\\.log\\|(ftp)\\|^tags\\|^TAGS\\)$" | 241 "\\(^nn\\.a[0-9]+\\|\\.log\\|(ftp)\\|^tags\\|^TAGS\\)$" |
249 "Regexp identifying buffers that are to be excluded from saving." | 242 "Regexp identifying buffers that are to be excluded from saving." |
250 :type 'regexp | 243 :type 'regexp |
251 :group 'desktop) | 244 :group 'desktop) |
252 | 245 |
253 ;; Skip ange-ftp files | 246 ;; Skip tramp and ange-ftp files |
254 (defcustom desktop-files-not-to-save | 247 (defcustom desktop-files-not-to-save |
255 "^/[^/:]*:" | 248 "^/[^/:]*:" |
256 "Regexp identifying files whose buffers are to be excluded from saving." | 249 "Regexp identifying files whose buffers are to be excluded from saving." |
257 :type 'regexp | 250 :type 'regexp |
258 :group 'desktop) | 251 :group 'desktop) |
259 | 252 |
260 (defcustom desktop-buffer-modes-to-save | 253 (defcustom desktop-buffer-modes-to-save |
261 '(Info-mode rmail-mode) | 254 '(Info-mode rmail-mode) |
262 "If a buffer is of one of these major modes, save the buffer name. | 255 "If a buffer is of one of these major modes, save the buffer state. |
263 It is up to the functions in `desktop-buffer-handlers' to decide | 256 It is up to the functions in `desktop-buffer-handlers' to decide |
264 whether the buffer should be recreated or not, and how." | 257 whether the buffer should be recreated or not, and how." |
265 :type '(repeat symbol) | 258 :type '(repeat symbol) |
266 :group 'desktop) | 259 :group 'desktop) |
267 | 260 |
281 | 274 |
282 (defcustom desktop-buffer-misc-functions | 275 (defcustom desktop-buffer-misc-functions |
283 '(desktop-buffer-info-misc-data | 276 '(desktop-buffer-info-misc-data |
284 desktop-buffer-dired-misc-data) | 277 desktop-buffer-dired-misc-data) |
285 "*Functions used to determine auxiliary information for a buffer. | 278 "*Functions used to determine auxiliary information for a buffer. |
286 These functions are called in order, with no arguments. If a function | 279 These functions are called by `desktop-save' in order, with no |
287 returns non-nil, its value is saved along with the desktop buffer for | 280 arguments. If a function returns non-nil, its value is saved along |
288 which it was called; no further functions will be called. | 281 with the state of the buffer for which it was called; no further |
289 | 282 functions will be called. |
290 File names should formatted using the call | 283 |
284 When file names are returned, they should be formatted using the call | |
291 \"(desktop-file-name FILE-NAME dirname)\". | 285 \"(desktop-file-name FILE-NAME dirname)\". |
292 | 286 |
293 Later, when desktop.el restores the buffers it has saved, each of the | 287 Later, when `desktop-read' restores buffers, each of the functions in |
294 `desktop-buffer-handlers' functions will have access to a buffer local | 288 `desktop-buffer-handlers' will have access to a buffer local variable, |
295 variable, named `desktop-buffer-misc', whose value is what the | 289 named `desktop-buffer-misc', whose value is what the function in |
296 \"misc\" function returned previously." | 290 `desktop-buffer-misc-functions' returned." |
297 :type '(repeat function) | 291 :type '(repeat function) |
298 :group 'desktop) | 292 :group 'desktop) |
299 | 293 |
300 (defcustom desktop-buffer-handlers | 294 (defcustom desktop-buffer-handlers |
301 '(desktop-buffer-dired | 295 '(desktop-buffer-dired |
302 desktop-buffer-rmail | 296 desktop-buffer-rmail |
303 desktop-buffer-mh | 297 desktop-buffer-mh |
304 desktop-buffer-info | 298 desktop-buffer-info |
305 desktop-buffer-file) | 299 desktop-buffer-file) |
306 "*List of functions to call in order to create a buffer. | 300 "*Functions called by `desktop-read' in order to create a buffer. |
307 The functions are called without explicit parameters but can use the | 301 The functions are called without explicit parameters but can use the |
308 following variables: | 302 following variables: |
309 | 303 |
310 desktop-file-version | 304 desktop-file-version |
311 desktop-buffer-file-name | 305 desktop-buffer-file-name |
340 :type 'sexp | 334 :type 'sexp |
341 :group 'desktop) | 335 :group 'desktop) |
342 | 336 |
343 ;; ---------------------------------------------------------------------------- | 337 ;; ---------------------------------------------------------------------------- |
344 (defvar desktop-dirname nil | 338 (defvar desktop-dirname nil |
345 "The directory in which the current desktop file resides.") | 339 "The directory in which the desktop file should be saved.") |
346 | 340 |
347 (defconst desktop-header | 341 (defconst desktop-header |
348 ";; -------------------------------------------------------------------------- | 342 ";; -------------------------------------------------------------------------- |
349 ;; Desktop File for Emacs | 343 ;; Desktop File for Emacs |
350 ;; -------------------------------------------------------------------------- | 344 ;; -------------------------------------------------------------------------- |
361 (setcdr here nil)))) | 355 (setcdr here nil)))) |
362 | 356 |
363 ;; ---------------------------------------------------------------------------- | 357 ;; ---------------------------------------------------------------------------- |
364 (defun desktop-clear () | 358 (defun desktop-clear () |
365 "Empty the Desktop. | 359 "Empty the Desktop. |
366 This kills all buffers except for internal ones and those listed | 360 This kills all buffers except for internal ones and those matching |
367 in `desktop-clear-preserve-buffers'. Furthermore, it clears the | 361 `desktop-clear-preserve-buffers-regexp' or listed in |
362 `desktop-clear-preserve-buffers'. Furthermore, it clears the | |
368 variables listed in `desktop-globals-to-clear'." | 363 variables listed in `desktop-globals-to-clear'." |
369 (interactive) | 364 (interactive) |
370 (dolist (var desktop-globals-to-clear) | 365 (dolist (var desktop-globals-to-clear) |
371 (if (symbolp var) | 366 (if (symbolp var) |
372 (eval `(setq-default ,var nil)) | 367 (eval `(setq-default ,var nil)) |
386 | 381 |
387 ;; ---------------------------------------------------------------------------- | 382 ;; ---------------------------------------------------------------------------- |
388 (add-hook 'kill-emacs-hook 'desktop-kill) | 383 (add-hook 'kill-emacs-hook 'desktop-kill) |
389 | 384 |
390 (defun desktop-kill () | 385 (defun desktop-kill () |
391 "If `desktop-enable' is non-nil, do what `desktop-save' says to do. | 386 "If `desktop-save-mode' is non-nil, do what `desktop-save' says to do. |
392 If the desktop should be saved and `desktop-dirname' | 387 If the desktop should be saved and `desktop-dirname' |
393 is nil, ask the user where to save the desktop." | 388 is nil, ask the user where to save the desktop." |
394 (when | 389 (when |
395 (and | 390 (and |
396 desktop-enable | 391 desktop-save-mode |
397 (let ((exists (file-exists-p (expand-file-name desktop-base-file-name desktop-dirname)))) | 392 (let ((exists (file-exists-p (expand-file-name desktop-base-file-name desktop-dirname)))) |
398 (or | 393 (or |
399 (eq desktop-save t) | 394 (eq desktop-save t) |
400 (and exists (memq desktop-save '(ask-if-new if-exists))) | 395 (and exists (memq desktop-save '(ask-if-new if-exists))) |
401 (and | 396 (and |
577 ((eq desktop-file-name-format 'local) (file-relative-name filename dirname)) | 572 ((eq desktop-file-name-format 'local) (file-relative-name filename dirname)) |
578 (t (expand-file-name filename)))) | 573 (t (expand-file-name filename)))) |
579 | 574 |
580 ;; ---------------------------------------------------------------------------- | 575 ;; ---------------------------------------------------------------------------- |
581 (defun desktop-save (dirname) | 576 (defun desktop-save (dirname) |
582 "Save the Desktop file. Parameter DIRNAME specifies where to save desktop." | 577 "Save the desktop in a desktop file. |
578 Parameter DIRNAME specifies where to save the desktop file. | |
579 See also `desktop-base-file-name'." | |
583 (interactive "DDirectory to save desktop file in: ") | 580 (interactive "DDirectory to save desktop file in: ") |
584 (run-hooks 'desktop-save-hook) | 581 (run-hooks 'desktop-save-hook) |
585 (setq dirname (file-name-as-directory (expand-file-name dirname))) | 582 (setq dirname (file-name-as-directory (expand-file-name dirname))) |
586 (save-excursion | 583 (save-excursion |
587 (let ((filename (expand-file-name desktop-base-file-name dirname)) | 584 (let ((filename (expand-file-name desktop-base-file-name dirname)) |
662 (write-region (point-min) (point-max) filename nil 'nomessage)))) | 659 (write-region (point-min) (point-max) filename nil 'nomessage)))) |
663 (setq desktop-dirname dirname)) | 660 (setq desktop-dirname dirname)) |
664 | 661 |
665 ;; ---------------------------------------------------------------------------- | 662 ;; ---------------------------------------------------------------------------- |
666 (defun desktop-remove () | 663 (defun desktop-remove () |
667 "Delete the Desktop file and inactivate the desktop system." | 664 "Delete desktop file in `desktop-dirname'. |
665 This function also sets `desktop-dirname' to nil." | |
668 (interactive) | 666 (interactive) |
669 (if desktop-dirname | 667 (when desktop-dirname |
670 (let ((filename (expand-file-name desktop-base-file-name desktop-dirname))) | 668 (let ((filename (expand-file-name desktop-base-file-name desktop-dirname))) |
671 (setq desktop-dirname nil) | 669 (setq desktop-dirname nil) |
672 (if (file-exists-p filename) | 670 (when (file-exists-p filename) |
673 (delete-file filename))))) | 671 (delete-file filename))))) |
672 | |
674 ;; ---------------------------------------------------------------------------- | 673 ;; ---------------------------------------------------------------------------- |
675 ;;;###autoload | 674 ;;;###autoload |
676 (defun desktop-read () | 675 (defun desktop-read (&optional dirname) |
677 "Read the Desktop file and the files it specifies. | 676 "Read and process the desktop file in directory DIRNAME. |
678 This is a no-op when Emacs is running in batch mode. | 677 Look for a desktop file in DIRNAME, or if DIRNAME is omitted, look in |
679 Look for the desktop file according to the variables `desktop-base-file-name' | 678 directories listed in `desktop-path'. If a desktop file is found, it |
680 and `desktop-path'. If no desktop file is found, clear the desktop. | 679 is processed and `desktop-after-read-hook' is run. If no desktop file |
681 Returns t if it has read a desktop file, nil otherwise." | 680 is found, clear the desktop and run `desktop-no-desktop-file-hook'. |
681 This function is a no-op when Emacs is running in batch mode. | |
682 It returns t if a desktop file was loaded, nil otherwise." | |
682 (interactive) | 683 (interactive) |
683 (unless noninteractive | 684 (unless noninteractive |
684 (let ((dirs desktop-path)) | 685 (setq desktop-dirname |
685 (while | 686 (file-name-as-directory |
686 (and | 687 (expand-file-name |
687 dirs | 688 (or |
688 (not | 689 ;; If DIRNAME is specified, use it. |
689 (file-exists-p (expand-file-name desktop-base-file-name (car dirs))))) | 690 (and (< 0 (length dirname)) dirname) |
690 (setq dirs (cdr dirs))) | 691 ;; Otherwise search desktop file in desktop-path. |
691 (setq desktop-dirname (and dirs (file-name-as-directory (expand-file-name (car dirs))))) | 692 (let ((dirs desktop-path)) |
692 (if desktop-dirname | 693 (while |
693 (let ((desktop-first-buffer nil)) | 694 (and |
694 ;; Evaluate desktop buffer. | 695 dirs |
695 (load (expand-file-name desktop-base-file-name desktop-dirname) t t t) | 696 (not |
696 ;; `desktop-create-buffer' puts buffers at end of the buffer list. | 697 (file-exists-p (expand-file-name desktop-base-file-name (car dirs))))) |
697 ;; We want buffers existing prior to evaluating the desktop (and not reused) | 698 (setq dirs (cdr dirs))) |
698 ;; to be placed at the end of the buffer list, so we move them here. | 699 (and dirs (car dirs))) |
699 (mapcar 'bury-buffer | 700 ;; If not found and `desktop-path' is non-nil, use its first element. |
700 (nreverse (cdr (memq desktop-first-buffer (nreverse (buffer-list)))))) | 701 (and desktop-path (car desktop-path)) |
701 (switch-to-buffer (car (buffer-list))) | 702 ;; Default: Home directory. |
702 (run-hooks 'desktop-delay-hook) | 703 "~")))) |
703 (setq desktop-delay-hook nil) | 704 (if (file-exists-p (expand-file-name desktop-base-file-name desktop-dirname)) |
704 (run-hooks 'desktop-after-read-hook) | 705 ;; Desktop file found, process it. |
705 (message "Desktop loaded.") | 706 (let ((desktop-first-buffer nil)) |
706 t) | 707 ;; Evaluate desktop buffer. |
707 (desktop-clear) | 708 (load (expand-file-name desktop-base-file-name desktop-dirname) t t t) |
708 (run-hooks 'desktop-no-desktop-file-hook) | 709 ;; `desktop-create-buffer' puts buffers at end of the buffer list. |
709 (message "No desktop file.") | 710 ;; We want buffers existing prior to evaluating the desktop (and not reused) |
710 nil)))) | 711 ;; to be placed at the end of the buffer list, so we move them here. |
711 | 712 (mapcar 'bury-buffer |
712 ;; ---------------------------------------------------------------------------- | 713 (nreverse (cdr (memq desktop-first-buffer (nreverse (buffer-list)))))) |
714 (switch-to-buffer (car (buffer-list))) | |
715 (run-hooks 'desktop-delay-hook) | |
716 (setq desktop-delay-hook nil) | |
717 (run-hooks 'desktop-after-read-hook) | |
718 (message "Desktop loaded.") | |
719 t) | |
720 ;; No desktop file found. | |
721 (desktop-clear) | |
722 (let ((default-directory desktop-dirname)) | |
723 (run-hooks 'desktop-no-desktop-file-hook)) | |
724 (message "No desktop file.") | |
725 nil))) | |
726 | |
727 ;; ---------------------------------------------------------------------------- | |
728 ;; Maintained for backward compatibility | |
713 ;;;###autoload | 729 ;;;###autoload |
714 (defun desktop-load-default () | 730 (defun desktop-load-default () |
715 "Load the `default' start-up library manually. | 731 "Load the `default' start-up library manually. |
716 Also inhibit further loading of it. Call this from your `.emacs' file | 732 Also inhibit further loading of it." |
717 to provide correct modes for autoloaded files." | |
718 (if (not inhibit-default-init) ; safety check | 733 (if (not inhibit-default-init) ; safety check |
719 (progn | 734 (progn |
720 (load "default" t t) | 735 (load "default" t t) |
721 (setq inhibit-default-init t)))) | 736 (setq inhibit-default-init t)))) |
737 (make-obsolete 'desktop-load-default 'desktop-save-mode) | |
722 | 738 |
723 ;; ---------------------------------------------------------------------------- | 739 ;; ---------------------------------------------------------------------------- |
724 ;;;###autoload | 740 ;;;###autoload |
725 (defun desktop-change-dir (dir) | 741 (defun desktop-change-dir (dirname) |
726 "Save and clear the desktop, then load the desktop from directory DIR. | 742 "Change to desktop saved in DIRNAME. |
727 However, if `desktop-enable' was nil at call, don't save the old desktop. | 743 Kill the desktop as specified by variables `desktop-save-mode' and |
728 This function always sets `desktop-enable' to t." | 744 `desktop-save', then clear the desktop and load the desktop file in |
729 (interactive "DNew directory: ") | 745 directory DIRNAME." |
730 (setq dir (file-name-as-directory (expand-file-name dir desktop-dirname))) | 746 (interactive "DChange to directory: ") |
747 (setq dirname (file-name-as-directory (expand-file-name dirname desktop-dirname))) | |
731 (desktop-kill) | 748 (desktop-kill) |
732 (desktop-clear) | 749 (desktop-clear) |
733 (setq desktop-enable t) | 750 (desktop-read dirname)) |
734 (let ((desktop-path (list dir)) | 751 |
735 (default-directory dir)) | 752 ;; ---------------------------------------------------------------------------- |
736 (desktop-read)) | |
737 ;; Set `desktop-dirname' even in no desktop file was found | |
738 (setq desktop-dirname dir)) | |
739 ;; ---------------------------------------------------------------------------- | |
740 ;;;###autoload | 753 ;;;###autoload |
741 (defun desktop-save-in-load-dir () | 754 (defun desktop-save-in-desktop-dir () |
742 "Save desktop in directory from which it was loaded." | 755 "Save the desktop in directory `desktop-dirname'." |
743 (interactive) | 756 (interactive) |
744 (if desktop-dirname | 757 (if desktop-dirname |
745 (desktop-save desktop-dirname) | 758 (desktop-save desktop-dirname) |
746 (call-interactively 'desktop-save)) | 759 (call-interactively 'desktop-save)) |
747 (message "Desktop saved in %s" desktop-dirname)) | 760 (message "Desktop saved in %s" desktop-dirname)) |
749 ;; ---------------------------------------------------------------------------- | 762 ;; ---------------------------------------------------------------------------- |
750 ;;;###autoload | 763 ;;;###autoload |
751 (defun desktop-revert () | 764 (defun desktop-revert () |
752 "Revert to the last loaded desktop." | 765 "Revert to the last loaded desktop." |
753 (interactive) | 766 (interactive) |
754 (unless desktop-dirname (error "No desktop has been loaded")) | 767 (unless desktop-dirname |
755 (setq desktop-enable nil) | 768 (error "Unknown desktop directory")) |
756 (desktop-change-dir desktop-dirname)) | 769 (unless (file-exists-p (expand-file-name desktop-base-file-name desktop-dirname)) |
770 (error "No desktop file found")) | |
771 (desktop-clear) | |
772 (desktop-read desktop-dirname)) | |
757 | 773 |
758 ;; ---------------------------------------------------------------------------- | 774 ;; ---------------------------------------------------------------------------- |
759 ;; Note: the following functions use the dynamic variable binding in Lisp. | 775 ;; Note: the following functions use the dynamic variable binding in Lisp. |
760 ;; | 776 ;; |
761 | 777 |
960 (cons 'case-fold-search cfs) | 976 (cons 'case-fold-search cfs) |
961 (cons 'case-replace cr) | 977 (cons 'case-replace cr) |
962 (cons 'overwrite-mode (car mim))))) | 978 (cons 'overwrite-mode (car mim))))) |
963 | 979 |
964 ;; ---------------------------------------------------------------------------- | 980 ;; ---------------------------------------------------------------------------- |
965 ;; When `desktop-enable' is non-nil and "--no-desktop" is not specified on the | 981 ;; When `desktop-save-mode' is non-nil and "--no-desktop" is not specified on the |
966 ;; command line, we do the rest of what it takes to use desktop, but do it | 982 ;; command line, we do the rest of what it takes to use desktop, but do it |
967 ;; after finishing loading the init file. | 983 ;; after finishing loading the init file. |
968 ;; We cannot use `command-switch-alist' to process "--no-desktop" because these | 984 ;; We cannot use `command-switch-alist' to process "--no-desktop" because these |
969 ;; functions are processed after `after-init-hook'. | 985 ;; functions are processed after `after-init-hook'. |
970 (add-hook | 986 (add-hook |
971 'after-init-hook | 987 'after-init-hook |
972 '(lambda () | 988 '(lambda () |
973 (let ((key "--no-desktop")) | 989 (let ((key "--no-desktop")) |
974 (if (member key command-line-args) | 990 (if (member key command-line-args) |
975 (delete key command-line-args) | 991 (delete key command-line-args) |
976 (when desktop-enable | 992 (when desktop-save-mode (desktop-read)))))) |
977 (desktop-load-default) | |
978 (desktop-read)))))) | |
979 | 993 |
980 (provide 'desktop) | 994 (provide 'desktop) |
981 | 995 |
982 ;;; arch-tag: 221907c3-1771-4fd3-9c2e-c6f700c6ede9 | 996 ;;; arch-tag: 221907c3-1771-4fd3-9c2e-c6f700c6ede9 |
983 ;;; desktop.el ends here | 997 ;;; desktop.el ends here |