Mercurial > hg > xemacs-beta
comparison lisp/packages/gnuserv.el @ 193:f53b5ca2e663 r20-3b23
Import from CVS: tag r20-3b23
author | cvs |
---|---|
date | Mon, 13 Aug 2007 09:58:30 +0200 |
parents | e121b013d1f0 |
children | a2f645c6b9f8 |
comparison
equal
deleted
inserted
replaced
192:9d35321dd38c | 193:f53b5ca2e663 |
---|---|
1 ;;; gnuserv.el --- Lisp interface code between Emacs and gnuserv | 1 ;;; gnuserv.el --- Lisp interface code between Emacs and gnuserv |
2 ;; Copyright (C) 1989-1997 Free Software Foundation, Inc. | 2 ;; Copyright (C) 1989-1997 Free Software Foundation, Inc. |
3 | 3 |
4 ;; Version: 3.9 | 4 ;; Version: 3.10 |
5 ;; Author: Andy Norman (ange@hplb.hpl.hp.com), originally based on server.el | 5 ;; Author: Andy Norman (ange@hplb.hpl.hp.com), originally based on server.el |
6 ;; Hrvoje Niksic <hniksic@srce.hr> | 6 ;; Hrvoje Niksic <hniksic@srce.hr>, rewritten from scratch in May 1997 |
7 ;; Maintainer: Jan Vroonhof <vroonhof@math.ethz.ch>, | 7 ;; Maintainer: Jan Vroonhof <vroonhof@math.ethz.ch>, |
8 ;; Hrvoje Niksic <hniksic@srce.hr> | 8 ;; Hrvoje Niksic <hniksic@srce.hr> |
9 ;; Keywords: environment, processes, terminals | 9 ;; Keywords: environment, processes, terminals |
10 | 10 |
11 ;; This file is part of XEmacs. | 11 ;; This file is part of XEmacs. |
61 ;; ver William Sommerfeld's server.el. Since then, a number of people | 61 ;; ver William Sommerfeld's server.el. Since then, a number of people |
62 ;; have worked on it, including Bob Weiner, Darell Kindred, Arup | 62 ;; have worked on it, including Bob Weiner, Darell Kindred, Arup |
63 ;; Mukherjee, Ben Wing and Jan Vroonhof. It was completely rewritten | 63 ;; Mukherjee, Ben Wing and Jan Vroonhof. It was completely rewritten |
64 ;; (labeled as version 3) by Hrvoje Niksic in May 1997. | 64 ;; (labeled as version 3) by Hrvoje Niksic in May 1997. |
65 | 65 |
66 ;; Jan Vroonhof <vroonhof@math.ethz.ch> July/1996 | |
67 ;; ported the server-temp-file-regexp feature from server.el | |
68 ;; ported server hooks from server.el | |
69 ;; ported kill-*-query functions from server.el (and made it optional) | |
70 ;; synced other behaviour with server.el | |
71 ;; | |
72 ;; Jan Vroonhof | 66 ;; Jan Vroonhof |
73 ;; Customized. | 67 ;; Customized. |
74 ;; | 68 ;; |
75 ;; Hrvoje Niksic <hniksic@srce.hr> May/1997 | 69 ;; Hrvoje Niksic <hniksic@srce.hr> May/1997 |
76 ;; Completely rewritten. Now uses `defstruct' and other CL stuff | 70 ;; Completely rewritten. Now uses `defstruct' and other CL stuff |
77 ;; to define clients cleanly. Many thanks to Dave Gillespie! | 71 ;; to define clients cleanly. Many thanks to Dave Gillespie! |
78 ;; | 72 ;; |
79 ;; Mike Scheidler <c23mts@eng.delcoelect.com> July, 1997 | 73 ;; Mike Scheidler <c23mts@eng.delcoelect.com> July, 1997 |
80 ;; Added 'Done' button to the menubar. | 74 ;; Added 'Done' button to the menubar. |
75 ;; | |
76 ;; Hrvoje Niksic <hniksic@srce.hr> Sep/1997 | |
77 ;; More pervasive changes. | |
81 | 78 |
82 | 79 |
83 ;;; Code: | 80 ;;; Code: |
84 | 81 |
85 (defgroup gnuserv nil | 82 (defgroup gnuserv nil |
90 | 87 |
91 | 88 |
92 ;; Provide the old variables as aliases, to avoid breaking .emacs | 89 ;; Provide the old variables as aliases, to avoid breaking .emacs |
93 ;; files. However, they are obsolete and should be converted to the | 90 ;; files. However, they are obsolete and should be converted to the |
94 ;; new forms. This ugly crock must be before the variable | 91 ;; new forms. This ugly crock must be before the variable |
95 ;; declaration, or the scheme fails. | 92 ;; declaration, or the scheme fails. I'd prefer if we could junk this |
93 ;; sh*t, but I guess the users will appreciate compatibility. Uh... | |
96 | 94 |
97 (define-obsolete-variable-alias 'server-frame 'gnuserv-frame) | 95 (define-obsolete-variable-alias 'server-frame 'gnuserv-frame) |
98 (define-obsolete-variable-alias 'server-done-function | 96 (define-obsolete-variable-alias 'server-done-function |
99 'gnuserv-done-function) | 97 'gnuserv-done-function) |
100 (define-obsolete-variable-alias 'server-done-temp-file-function | 98 (define-obsolete-variable-alias 'server-done-temp-file-function |
107 'gnuserv-visit-hook) | 105 'gnuserv-visit-hook) |
108 (define-obsolete-variable-alias 'server-done-hook | 106 (define-obsolete-variable-alias 'server-done-hook |
109 'gnuserv-done-hook) | 107 'gnuserv-done-hook) |
110 (define-obsolete-variable-alias 'server-kill-quietly | 108 (define-obsolete-variable-alias 'server-kill-quietly |
111 'gnuserv-kill-quietly) | 109 'gnuserv-kill-quietly) |
112 (define-obsolete-variable-alias 'server-temp-file-regexp | |
113 'gnuserv-temp-file-regexp) | |
114 (define-obsolete-variable-alias 'server-make-temp-file-backup | |
115 'gnuserv-make-temp-file-backup) | |
116 | 110 |
117 ;;;###autoload | 111 ;;;###autoload |
118 (defcustom gnuserv-frame nil | 112 (defcustom gnuserv-frame 'new |
119 "*The frame to be used to display all edited files. | 113 "*Determines what frame will be used to display all edited files. |
120 If nil, then a new frame is created for each file edited. | 114 Legal values are: |
121 If t, then the currently selected frame will be used. | 115 `new' -- a new frame will be created for each file edited; |
122 If a function, then this will be called with a symbol `x' or `tty' as the | 116 `current' -- the currently selected frame will be used; |
123 only argument, and its return value will be interpreted as above." | 117 `main' -- \"main\" Emacs frame will be used; |
118 `visible' -- a visible frame will be used, or a new one created; | |
119 `special' -- a special Gnuserv frame will be created, and used for | |
120 all gnuserv-edited files; | |
121 frame -- that particular frame will be used. | |
122 | |
123 If gnuclient is called using the `-nw' method (from a TTY device), the | |
124 behaviour will be as if gnuserv-frame were `new'. | |
125 This variable is read by `gnuserv-frame-default-function'. If you | |
126 change `gnuserv-frame-function' to anything else, this variable will | |
127 have no effect." | |
124 :tag "Gnuserv Frame" | 128 :tag "Gnuserv Frame" |
125 :type '(radio (const :tag "Create new frame each time" nil) | 129 ;; Compatibility |
126 (const :tag "Use selected frame" t) | 130 :type '(radio (const :tag "Create new frame each time" new) |
127 (function-item :tag "Use main Emacs frame" | 131 (const :tag "Use currently selected frame" current) |
128 gnuserv-main-frame-function) | 132 (const :tag "Use main Emacs frame" main) |
129 (function-item :tag "Use visible frame, otherwise create new" | 133 (const :tag "Use visible frame, otherwise create new" visible) |
130 gnuserv-visible-frame-function) | 134 (const :tag "Create special Gnuserv frame and use it" special)) |
131 (function-item :tag "Create special Gnuserv frame and use it" | 135 :group 'gnuserv) |
132 gnuserv-special-frame-function) | 136 |
133 (function :tag "Other")) | 137 (defcustom gnuserv-frame-properties nil |
134 :group 'gnuserv) | 138 "*Properties of the frame in which gnuclient buffers are displayed. |
139 Note that this is in effect only for frames created by | |
140 `gnuserv-frame-default-function'." | |
141 :type '(repeat (group :inline t | |
142 (symbol :tag "Property") | |
143 (sexp :tag "Value"))) | |
144 :group 'gnuserv) | |
145 | |
146 (defcustom gnuserv-frame-function 'gnuserv-frame-default-function | |
147 "*Function to return the appropriate frame for use by gnuclient. | |
148 The function will be called with two arguments: the first one as | |
149 described by `gnuserv-frame', and the second one as the device to | |
150 create the frame on. | |
151 The function must return a valid frame object." | |
152 :type 'function | |
153 :group 'gnuserv) | |
135 | 154 |
136 (defcustom gnuserv-done-function 'kill-buffer | 155 (defcustom gnuserv-done-function 'kill-buffer |
137 "*Function used to remove a buffer after editing. | 156 "*Function used to remove a buffer after editing. |
138 It is called with one BUFFER argument. Functions such as `kill-buffer' and | 157 It is called with one BUFFER argument. Functions such as `kill-buffer' and |
139 `bury-buffer' are good values. See also `gnuserv-done-temp-file-function'." | 158 `bury-buffer' are good values. See also `gnuserv-done-temp-file-function'." |
140 :type '(radio (function-item kill-buffer) | 159 :type '(radio (function-item kill-buffer) |
141 (function-item bury-buffer) | 160 (function-item bury-buffer) |
142 (function :tag "Other")) | 161 (function :tag "Other")) |
143 :group 'gnuserv) | 162 :group 'gnuserv) |
144 | 163 |
145 (defcustom gnuserv-done-temp-file-function 'kill-buffer | |
146 "*Function used to remove a temporary buffer after editing. | |
147 It is called with one BUFFER argument. Functions such as `kill-buffer' and | |
148 `bury-buffer' are good values. See also `gnuserv-done-temp-file-function'." | |
149 :type '(radio (function-item kill-buffer) | |
150 (function-item bury-buffer) | |
151 (function :tag "Other")) | |
152 :group 'gnuserv) | |
153 | |
154 (defcustom gnuserv-find-file-function 'find-file | 164 (defcustom gnuserv-find-file-function 'find-file |
155 "*Function to visit a file with. | 165 "*Function to visit a file with. |
156 It takes one argument, a file name to visit." | 166 It takes one argument, a file name to visit." |
157 :type 'function | 167 :type 'function |
158 :group 'gnuserv) | 168 :group 'gnuserv) |
192 :type 'hook | 202 :type 'hook |
193 :group 'gnuserv) | 203 :group 'gnuserv) |
194 | 204 |
195 (defcustom gnuserv-kill-quietly nil | 205 (defcustom gnuserv-kill-quietly nil |
196 "*Non-nil means to kill buffers with clients attached without requiring confirmation." | 206 "*Non-nil means to kill buffers with clients attached without requiring confirmation." |
197 :type 'boolean | |
198 :group 'gnuserv) | |
199 | |
200 (defcustom gnuserv-temp-file-regexp "^/tmp/Re\\|/draft$" | |
201 "*Regexp which should match filenames of temporary files deleted | |
202 and reused by the programs that invoke the Emacs server." | |
203 :type 'regexp | |
204 :group 'gnuserv) | |
205 | |
206 (defcustom gnuserv-make-temp-file-backup nil | |
207 "*Non-nil makes the server backup temporary files also." | |
208 :type 'boolean | 207 :type 'boolean |
209 :group 'gnuserv) | 208 :group 'gnuserv) |
210 | 209 |
211 | 210 |
212 ;;; Internal variables: | 211 ;;; Internal variables: |
228 (id nil) | 227 (id nil) |
229 (buffers nil) | 228 (buffers nil) |
230 (device nil) | 229 (device nil) |
231 (frame nil)) | 230 (frame nil)) |
232 | 231 |
233 (defvar gnuserv-process nil | 232 (defvar gnuserv-process nil |
234 "The current gnuserv process.") | 233 "The current gnuserv process.") |
235 | 234 |
236 (defvar gnuserv-string "" | 235 (defvar gnuserv-string "" |
237 "The last input string from the server.") | 236 "The last input string from the server.") |
238 | 237 |
244 Each element is a gnuclient structure that identifies a client.") | 243 Each element is a gnuclient structure that identifies a client.") |
245 | 244 |
246 (defvar gnuserv-devices nil | 245 (defvar gnuserv-devices nil |
247 "List of devices created by clients.") | 246 "List of devices created by clients.") |
248 | 247 |
248 ;; We want the client-infested buffers to have some modeline | |
249 ;; identification, so we'll make a "minor mode". We don't use | |
250 ;; `add-minor-mode', as we don't want it to be togglable. | |
251 (defvar gnuserv-minor-mode nil) | |
252 | |
253 (make-variable-buffer-local 'gnuserv-mode) | |
254 (pushnew '(gnuserv-minor-mode " Server") minor-mode-alist :test 'equal) | |
255 | |
249 (defvar gnuserv-special-frame nil | 256 (defvar gnuserv-special-frame nil |
250 "Frame created specially for Server.") | 257 "Frame created specially for Server.") |
251 | 258 |
252 ;; We want the client-infested buffers to have some modeline | |
253 ;; identification, so we'll make a "minor mode". | |
254 (defvar gnuserv-minor-mode nil) | |
255 (make-variable-buffer-local 'gnuserv-mode) | |
256 (pushnew '(gnuserv-minor-mode " Server") minor-mode-alist | |
257 :test 'equal) | |
258 | |
259 | 259 |
260 ;; Sample gnuserv-frame functions | 260 ;; Creating gnuserv frame. |
261 | 261 |
262 (defun gnuserv-main-frame-function (type) | 262 (defun gnuserv-frame-default-function (arg device) |
263 "Returns a sensible value for the main Emacs frame." | 263 "Default function to create Gnuserv frames. |
264 (if (eq type 'x) | 264 See the documentation of `gnuserv-frame' for instructions how to |
265 (car (frame-list)) | 265 customize it." |
266 nil)) | 266 ;; If we are on TTY, act as if `new' was given. |
267 | 267 (if (not (device-on-window-system-p)) |
268 (defun gnuserv-visible-frame-function (type) | 268 (gnuserv-frame-default-function 'new device) |
269 "Returns a frame if there is a frame that is truly visible, nil otherwise. | 269 (cond |
270 This is meant in the X sense, so it will not return frames that are on another | 270 ((or (eq arg 'new) |
271 visual screen. Totally visible frames are preferred. If none found, return nil." | 271 ;; nil for back-compat |
272 (if (eq type 'x) | 272 (eq arg nil)) |
273 (cond ((car (filtered-frame-list 'frame-totally-visible-p | 273 (make-frame gnuserv-frame-properties device)) |
274 (selected-device)))) | 274 ((or (eq arg 'current) |
275 ((car (filtered-frame-list (lambda (frame) | 275 ;; t for back-compat |
276 ;; eq t as in not 'hidden | 276 (eq arg t)) |
277 (eq t (frame-visible-p frame))) | 277 (selected-frame)) |
278 (selected-device))))) | 278 ((eq arg 'main) |
279 nil)) | 279 (car (frame-list))) |
280 | 280 ((eq arg 'visible) |
281 (defun gnuserv-special-frame-function (type) | 281 (cond ((car (filtered-frame-list 'frame-totally-visible-p device))) |
282 "Creates a special frame for Gnuserv and returns it on later invocations." | 282 ((car (filtered-frame-list (lambda (frame) |
283 (unless (frame-live-p gnuserv-special-frame) | 283 ;; eq t as in not 'hidden |
284 (setq gnuserv-special-frame (make-frame))) | 284 (eq (frame-visible-p frame) t)) |
285 gnuserv-special-frame) | 285 device))) |
286 (t (make-frame gnuserv-frame-properties device)))) | |
287 ((eq arg 'special) | |
288 (unless (frame-live-p gnuserv-special-frame) | |
289 (setq gnuserv-special-frame | |
290 (make-frame gnuserv-frame-properties device)))) | |
291 ((frame-live-p arg) | |
292 arg) | |
293 (t | |
294 (error "Invalid argument %s" arg))))) | |
286 | 295 |
287 | 296 |
288 ;;; Communication functions | 297 ;;; Communication functions |
289 | 298 |
290 ;; We used to restart the server here, but it's too risky -- if | 299 ;; We used to restart the server here, but it's too risky -- if |
400 (quick (setq quick t)) | 409 (quick (setq quick t)) |
401 (view (setq view t)) | 410 (view (setq view t)) |
402 (t (error "Invalid flag %s" flag)))) | 411 (t (error "Invalid flag %s" flag)))) |
403 flags) | 412 flags) |
404 (let* ((old-device-num (length (device-list))) | 413 (let* ((old-device-num (length (device-list))) |
405 (new-frame nil) | 414 (old-frame-num (length (frame-list))) |
406 (dest-frame (if (functionp gnuserv-frame) | 415 (device (case (car type) |
407 (funcall gnuserv-frame (car type)) | |
408 gnuserv-frame)) | |
409 ;; The gnuserv-frame dependencies are ugly. | |
410 (device (cond ((frame-live-p dest-frame) | |
411 (frame-device dest-frame)) | |
412 ((null dest-frame) | |
413 (case (car type) | |
414 (tty (apply 'make-tty-device (cdr type))) | 416 (tty (apply 'make-tty-device (cdr type))) |
415 (x (make-x-device (cadr type))) | 417 (x (make-x-device (cadr type))) |
416 (t (error "Invalid device type")))) | 418 (t (error "Invalid device type")))) |
417 (t | 419 (frame (funcall gnuserv-frame-function gnuserv-frame device)) |
418 (selected-device)))) | |
419 (frame (cond ((frame-live-p dest-frame) | |
420 dest-frame) | |
421 ((null dest-frame) | |
422 (setq new-frame (make-frame nil device)) | |
423 new-frame) | |
424 (t (selected-frame)))) | |
425 (client (make-gnuclient :id gnuserv-current-client | 420 (client (make-gnuclient :id gnuserv-current-client |
426 :device device | 421 :device device |
427 :frame new-frame))) | 422 :frame (if (= (length (frame-list)) |
423 old-frame-num) | |
424 nil frame)))) | |
428 (setq gnuserv-current-client nil) | 425 (setq gnuserv-current-client nil) |
429 ;; If the device was created by this client, push it to the list. | 426 ;; If the device was created by this client, push it to the list. |
430 (and (/= old-device-num (length (device-list))) | 427 (and (/= old-device-num (length (device-list))) |
431 (push device gnuserv-devices)) | 428 (push device gnuserv-devices)) |
432 (and (frame-iconified-p frame) | 429 (and (frame-iconified-p frame) |
433 (deiconify-frame frame)) | 430 (deiconify-frame frame)) |
434 ;; Visit all the listed files. | 431 ;; Visit all the listed files. |
435 (while list | 432 (while list |
436 (let ((line (caar list)) (path (cdar list))) | 433 (let ((line (caar list)) (path (cdar list))) |
437 (select-frame frame) | 434 (select-frame frame) |
435 (raise-frame frame) | |
438 ;; Visit the file. | 436 ;; Visit the file. |
439 (funcall (if view | 437 (funcall (if view |
440 gnuserv-view-file-function | 438 gnuserv-view-file-function |
441 gnuserv-find-file-function) | 439 gnuserv-find-file-function) |
442 path) | 440 path) |
444 ;; Don't memorize the quick and view buffers. | 442 ;; Don't memorize the quick and view buffers. |
445 (unless (or quick view) | 443 (unless (or quick view) |
446 (pushnew (current-buffer) (gnuclient-buffers client)) | 444 (pushnew (current-buffer) (gnuclient-buffers client)) |
447 (setq gnuserv-minor-mode t) | 445 (setq gnuserv-minor-mode t) |
448 ;; Add the "Done" button to the menubar, only in this buffer. | 446 ;; Add the "Done" button to the menubar, only in this buffer. |
449 (if (boundp 'current-menubar) | 447 (when (boundp 'current-menubar) |
450 (progn (set-buffer-menubar current-menubar) | 448 (set-buffer-menubar current-menubar) |
451 (add-menu-button nil ["Done" gnuserv-edit t])) | 449 (add-menu-button nil ["Done" gnuserv-edit t]))) |
452 )) | |
453 (run-hooks 'gnuserv-visit-hook) | 450 (run-hooks 'gnuserv-visit-hook) |
454 (pop list))) | 451 (pop list))) |
455 (cond | 452 (cond |
456 ((and (or quick view) | 453 ((and (or quick view) |
457 (device-on-window-system-p device)) | 454 (device-on-window-system-p device)) |
461 ;; should be unique. | 458 ;; should be unique. |
462 (gnuserv-write-to-client (gnuclient-id client) nil)) | 459 (gnuserv-write-to-client (gnuclient-id client) nil)) |
463 (t | 460 (t |
464 ;; Else, the client gets a vote. | 461 ;; Else, the client gets a vote. |
465 (push client gnuserv-clients) | 462 (push client gnuserv-clients) |
466 ;; Explain buffer exit options. If dest-frame is nil, the | 463 ;; Explain buffer exit options. If client-frame is non-nil, |
467 ;; user can exit via `delete-frame'. OTOH, if FLAGS are nil | 464 ;; the user can exit via `delete-frame'. OTOH, if FLAGS are |
468 ;; and there are some buffers, the user can exit via | 465 ;; nil and there are some buffers, the user can exit via |
469 ;; `gnuserv-edit'. | 466 ;; `gnuserv-edit'. |
470 (if (and (not (or quick view)) | 467 (if (and (not (or quick view)) |
471 (gnuclient-buffers client)) | 468 (gnuclient-buffers client)) |
472 (message "%s" | 469 (message "%s" |
473 (substitute-command-keys | 470 (substitute-command-keys |
474 "Type `\\[gnuserv-edit]' to finish editing")) | 471 "Type `\\[gnuserv-edit]' to finish editing")) |
475 (or dest-frame | 472 (and (gnuclient-frame client) |
476 (message "%s" | 473 (message "%s" |
477 (substitute-command-keys | 474 (substitute-command-keys |
478 "Type `\\[delete-frame]' to finish editing"))))))))) | 475 "Type `\\[delete-frame]' to finish editing"))))))))) |
479 | 476 |
480 | 477 |
481 ;;; Functions that hook into Emacs in various way to enable operation | 478 ;;; Functions that hook into Emacs in various way to enable operation |
482 | 479 |
483 ;; Defined later. | 480 ;; Defined later. |
487 ;; possible, because it is slow, and conses a list. Use | 484 ;; possible, because it is slow, and conses a list. Use |
488 ;; `gnuserv-buffer-p' when appropriate, for instance. | 485 ;; `gnuserv-buffer-p' when appropriate, for instance. |
489 (defun gnuserv-buffer-clients (buffer) | 486 (defun gnuserv-buffer-clients (buffer) |
490 "Returns a list of clients to which BUFFER belongs." | 487 "Returns a list of clients to which BUFFER belongs." |
491 (let (res) | 488 (let (res) |
492 (dolist (client gnuserv-clients) | 489 (dolist (client gnuserv-clients res) |
493 (when (memq buffer (gnuclient-buffers client)) | 490 (when (memq buffer (gnuclient-buffers client)) |
494 (push client res))) | 491 (push client res))))) |
495 res)) | |
496 | 492 |
497 ;; Like `gnuserv-buffer-clients', but returns a boolean; doesn't | 493 ;; Like `gnuserv-buffer-clients', but returns a boolean; doesn't |
498 ;; collect a list. | 494 ;; collect a list. |
499 (defun gnuserv-buffer-p (buffer) | 495 (defun gnuserv-buffer-p (buffer) |
500 (member* buffer gnuserv-clients | 496 (member* buffer gnuserv-clients |
550 ;; error when `delete-device' tries to do the job later. | 546 ;; error when `delete-device' tries to do the job later. |
551 (gnuserv-kill-client client t)))) | 547 (gnuserv-kill-client client t)))) |
552 (callf2 delq device gnuserv-devices)) | 548 (callf2 delq device gnuserv-devices)) |
553 | 549 |
554 (add-hook 'delete-device-hook 'gnuserv-check-device) | 550 (add-hook 'delete-device-hook 'gnuserv-check-device) |
555 | |
556 (defun gnuserv-temp-file-p (buffer) | |
557 "Return non-nil if BUFFER contains a file considered temporary. | |
558 These are files whose names suggest they are repeatedly | |
559 reused to pass information to another program. | |
560 | |
561 The variable `gnuserv-temp-file-regexp' controls which filenames | |
562 are considered temporary." | |
563 (and (buffer-file-name buffer) | |
564 (string-match gnuserv-temp-file-regexp (buffer-file-name buffer)))) | |
565 | 551 |
566 (defun gnuserv-kill-client (client &optional leave-frame) | 552 (defun gnuserv-kill-client (client &optional leave-frame) |
567 "Kill the gnuclient CLIENT. | 553 "Kill the gnuclient CLIENT. |
568 This will do away with all the associated buffers. If LEAVE-FRAME, | 554 This will do away with all the associated buffers. If LEAVE-FRAME, |
569 the function will not remove the frames associated with the client." | 555 the function will not remove the frames associated with the client." |
606 (run-hooks 'gnuserv-done-hook) | 592 (run-hooks 'gnuserv-done-hook) |
607 (setq gnuserv-minor-mode nil) | 593 (setq gnuserv-minor-mode nil) |
608 ;; Delete the menu button. | 594 ;; Delete the menu button. |
609 (if (boundp 'current-menubar) | 595 (if (boundp 'current-menubar) |
610 (delete-menu-item '("Done"))) | 596 (delete-menu-item '("Done"))) |
611 (funcall (if (gnuserv-temp-file-p buffer) | 597 (funcall gnuserv-done-function buffer))) |
612 gnuserv-done-temp-file-function | |
613 gnuserv-done-function) | |
614 buffer))) | |
615 | 598 |
616 | 599 |
617 ;;; Higher-level functions | 600 ;;; Higher-level functions |
618 | 601 |
619 ;; Choose a `next' server buffer, according to several criteria, and | 602 ;; Choose a `next' server buffer, according to several criteria, and |
648 Does the save/backup queries first, and calls `gnuserv-done-function'." | 631 Does the save/backup queries first, and calls `gnuserv-done-function'." |
649 ;; Check whether this is the real thing. | 632 ;; Check whether this is the real thing. |
650 (unless (gnuserv-buffer-p buffer) | 633 (unless (gnuserv-buffer-p buffer) |
651 (error "%s does not belong to a gnuserv client" buffer)) | 634 (error "%s does not belong to a gnuserv client" buffer)) |
652 ;; Backup/ask query. | 635 ;; Backup/ask query. |
653 (if (gnuserv-temp-file-p buffer) | 636 (if (and (buffer-modified-p) |
654 ;; For a temp file, save, and do NOT make a non-numeric backup | 637 (y-or-n-p (concat "Save file " buffer-file-name "? "))) |
655 ;; Why does server.el explicitly back up temporary files? | 638 (save-buffer buffer)) |
656 (let ((version-control nil) | |
657 (buffer-backed-up (not gnuserv-make-temp-file-backup))) | |
658 (save-buffer)) | |
659 (if (and (buffer-modified-p) | |
660 (y-or-n-p (concat "Save file " buffer-file-name "? "))) | |
661 (save-buffer buffer))) | |
662 (gnuserv-buffer-done-1 buffer)) | 639 (gnuserv-buffer-done-1 buffer)) |
663 | 640 |
664 ;; Called by `gnuserv-start-1' to clean everything. Hooked into | 641 ;; Called by `gnuserv-start-1' to clean everything. Hooked into |
665 ;; `kill-emacs-hook', too. | 642 ;; `kill-emacs-hook', too. |
666 (defun gnuserv-kill-all-clients () | 643 (defun gnuserv-kill-all-clients () |
713 (not (not gnuserv-process))) | 690 (not (not gnuserv-process))) |
714 | 691 |
715 ;;;###autoload | 692 ;;;###autoload |
716 (defun gnuserv-start (&optional leave-dead) | 693 (defun gnuserv-start (&optional leave-dead) |
717 "Allow this Emacs process to be a server for client processes. | 694 "Allow this Emacs process to be a server for client processes. |
718 This starts a gnuserv communications subprocess through which | 695 This starts a gnuserv communications subprocess through which |
719 client \"editors\" (gnuclient and gnudoit) can send editing commands to | 696 client \"editors\" (gnuclient and gnudoit) can send editing commands to |
720 this Emacs job. See the gnuserv(1) manual page for more details. | 697 this Emacs job. See the gnuserv(1) manual page for more details. |
721 | |
722 Prefix arg means just kill any existing server communications subprocess." | 698 Prefix arg means just kill any existing server communications subprocess." |
723 (interactive "P") | 699 (interactive "P") |
724 (and gnuserv-process | 700 (and gnuserv-process |
725 (not leave-dead) | 701 (not leave-dead) |
726 (message "Restarting gnuserv")) | 702 (message "Restarting gnuserv")) |
727 (gnuserv-start-1 leave-dead)) | 703 (gnuserv-start-1 leave-dead)) |
728 | 704 |
729 (defun gnuserv-edit (&optional count) | 705 (defun gnuserv-edit (&optional count) |
730 "Mark the current gnuserv editing buffer as \"done\", and switch to next one. | 706 "Mark the current gnuserv buffer as \"done\", and switch to next one. |
731 | |
732 Run with a numeric prefix argument, repeat the operation that number | 707 Run with a numeric prefix argument, repeat the operation that number |
733 of times. If given a universal prefix argument, close all the buffers | 708 of times. If given a universal prefix argument, close all the buffers |
734 of this buffer's clients. | 709 of this buffer's clients. |
735 | 710 The `gnuserv-done-function' (`kill-buffer' by default) is called to |
736 The `gnuserv-done-function' (bound to `kill-buffer' by default) is | 711 dispose of the buffer after marking it as done. |
737 called to dispose of the buffer after marking it as done. | 712 When all of a client's buffers are marked as \"done\", the client is |
738 | 713 notified." |
739 Files that match `gnuserv-temp-file-regexp' are considered temporary and | |
740 are saved unconditionally and backed up if `gnuserv-make-temp-file-backup' | |
741 is non-nil. They are disposed of using `gnuserv-done-temp-file-function' | |
742 (also bound to `kill-buffer' by default). | |
743 | |
744 When all of a client's buffers are marked as \"done\", the client is notified." | |
745 (interactive "P") | 714 (interactive "P") |
746 (when (null count) | 715 (when (null count) |
747 (setq count 1)) | 716 (setq count 1)) |
748 (cond ((numberp count) | 717 (cond ((numberp count) |
749 (let (next) | 718 (let (next) |