Mercurial > emacs
comparison lisp/map-ynp.el @ 304:f3dd86b71a52
Initial revision
author | Roland McGrath <roland@gnu.org> |
---|---|
date | Sat, 29 Jun 1991 20:04:01 +0000 |
parents | |
children | 71090e169ac8 |
comparison
equal
deleted
inserted
replaced
303:f7330c156716 | 304:f3dd86b71a52 |
---|---|
1 ;;; map-ynp.el -- General-purpose boolean question-asker. | |
2 ;;; Copyright (C) 1991 Free Software Foundation, Inc. | |
3 ;;; Written by Roland McGrath. | |
4 ;;; | |
5 ;;; This program is free software; you can redistribute it and/or modify | |
6 ;;; it under the terms of the GNU General Public License as published by | |
7 ;;; the Free Software Foundation; either version 1, or (at your option) | |
8 ;;; any later version. | |
9 ;;; | |
10 ;;; This program is distributed in the hope that it will be useful, | |
11 ;;; but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 ;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
13 ;;; GNU General Public License for more details. | |
14 ;;; | |
15 ;;; A copy of the GNU General Public License can be obtained from this | |
16 ;;; program's author (send electronic mail to roland@ai.mit.edu) or from | |
17 ;;; the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA | |
18 ;;; 02139, USA. | |
19 ;;; | |
20 ;;; map-y-or-n-p is a general-purpose question-asking function. | |
21 ;;; It asks a series of y/n questions (a la y-or-n-p), and decides to | |
22 ;;; applies an action to each element of a list based on the answer. | |
23 ;;; The nice thing is that you also get some other possible answers | |
24 ;;; to use, reminiscent of query-replace: ! to answer y to all remaining | |
25 ;;; questions; ESC or q to answer n to all remaining questions; . to answer | |
26 ;;; y once and then n for the remainder; and you can get help with C-h. | |
27 | |
28 (defun map-y-or-n-p-help (object objects action) | |
29 (format "Type SPC or `y' to %s the current %s; | |
30 DEL or `n' to skip the current %s; | |
31 ! to %s all remaining %s; | |
32 ESC or `q' to exit; | |
33 or . (period) to %s the current %s and exit." | |
34 action object object action objects action object)) | |
35 | |
36 ;;;###autoload | |
37 (defun map-y-or-n-p (prompter actor list &optional help) | |
38 "Ask a series of boolean questions. | |
39 Takes args PROMPTER ACTOR LIST, and optional arg HELP. | |
40 | |
41 LIST is a list of objects, or a function of no arguments to return the next | |
42 object or nil. | |
43 | |
44 PROMPTER is a function of one arg (an object from LIST), | |
45 which returns a string to be used as the prompt for that object. | |
46 If the return value is not a string, it is eval'd to get the answer. | |
47 So, it may be nil to ignore the object, t to act on the object without | |
48 asking the user, or a form to do a more complex prompt. | |
49 PROMPTER may instead be a string, in which case the prompt is | |
50 \(format PROMPTER OBJECT\). | |
51 | |
52 ACTOR is a function of one arg (an object from LIST), | |
53 which gets called with each object that the user answers `yes' for. | |
54 | |
55 If HELP is given, it is a list (OBJECT OBJECTS ACTION), | |
56 where OBJECT is a string giving the singular noun for an elt of LIST; | |
57 OBJECTS is the plural noun for elts of LIST, and ACTION is a transitive | |
58 verb describing ACTOR. The default is \(\"object\" \"objects\" \"act on\"\). | |
59 | |
60 At the prompts, the user may enter y, Y, or SPC to act on that object; | |
61 n, N, or DEL to skip that object; ! to act on all following objects; | |
62 ESC or q to exit (skip all following objects); . (period) to act on the | |
63 current object and then exit; or \\[help-command] to get help. | |
64 | |
65 Returns the number of actions taken." | |
66 (let ((old-help-form help-form) | |
67 (help-form (cons 'map-y-or-n-p-help | |
68 (or help '("object" "objects" "act on")))) | |
69 (actions 0) | |
70 prompt | |
71 char | |
72 (next (if (or (symbolp list) | |
73 (subrp list) | |
74 (compiled-function-p list) | |
75 (and (consp list) | |
76 (eq (car list) 'lambda))) | |
77 list | |
78 (function (lambda () | |
79 (if list | |
80 (prog1 | |
81 (car list) | |
82 (setq list (cdr list))) | |
83 nil))))) | |
84 elt) | |
85 (if (stringp prompter) | |
86 (setq prompter (` (lambda (object) | |
87 (format (, prompter) object))))) | |
88 (while (setq elt (funcall next)) | |
89 (setq prompt (funcall prompter elt)) | |
90 (if (stringp prompt) | |
91 (progn | |
92 ;; Prompt the user about this object. | |
93 (let ((cursor-in-echo-area t)) | |
94 (message "%s(y, n, ! ., q, or %s)" | |
95 prompt (key-description (char-to-string help-char))) | |
96 (setq char (read-char))) | |
97 (cond ((or (= ?q char) | |
98 (= ?\e char)) | |
99 (setq next (function (lambda () nil)))) | |
100 ((or (= ?y char) | |
101 (= ?Y char) | |
102 (= ? char)) | |
103 ;; Act on the object. | |
104 (let ((help-form old-help-form)) | |
105 (funcall actor elt)) | |
106 (setq actions (1+ actions))) | |
107 ((or (= ?n char) | |
108 (= ?N char) | |
109 (= ?\^? char)) | |
110 ;; Skip the object. | |
111 ) | |
112 ((= ?. char) | |
113 ;; Act on the object and then exit. | |
114 (funcall actor elt) | |
115 (setq actions (1+ actions) | |
116 next (function (lambda () nil)))) | |
117 ((= ?! char) | |
118 ;; Act on all following objects. | |
119 (while (setq elt (funcall next)) | |
120 (if (funcall prompter elt) | |
121 (progn | |
122 (funcall actor elt) | |
123 (setq actions (1+ actions))))) | |
124 ((= ?? char) | |
125 (setq unread-command-char help-char) | |
126 (setq next (` (function (lambda () | |
127 (setq next (, next)) | |
128 t))))) | |
129 (t | |
130 ;; Random char. | |
131 (message "Type %s for help." | |
132 (key-description (char-to-string help-char))) | |
133 (beep) | |
134 (sit-for 1) | |
135 (setq next (` (function (lambda () | |
136 (setq next (, next)) | |
137 t)))))))) | |
138 (if (eval prompt) | |
139 (progn | |
140 (funcall actor (car list)) | |
141 (setq actions (1+ actions))))) | |
142 (setq list (cdr list))) | |
143 ;; Clear the last prompt from the minibuffer. | |
144 (message "") | |
145 ;; Return the number of actions that were taken. | |
146 actions)) | |
147 | |
148 (provide 'map-ynp) |