Merge branch 'bldchn' into next
[sxemacs] / info / lispref / specifiers.texi
1 @c -*-texinfo-*-
2 @c This is part of the SXEmacs Lisp Reference Manual.
3 @c Copyright (C) 1995, 1996 Ben Wing.
4 @c Copyright (C) 2002, 2004 Free Software Foundation, Inc.
5 @c Copyright (C) 2005 Sebastian Freundt <hroptatyr@sxemacs.org>
6 @c See the file lispref.texi for copying conditions.
7 @setfilename ../../info/specifiers.info
8
9 @node Specifiers, Faces and Window-System Objects, Extents, top
10 @chapter Specifiers
11 @cindex specifier
12
13 A specifier is an object used to keep track of a property whose value
14 should vary according to @emph{display context}, a window, a frame, or
15 device.  The value of many built-in properties, such as the font,
16 foreground, background, and such properties of a face and variables
17 such as @code{modeline-shadow-thickness} and
18 @code{top-toolbar-height}, is actually a specifier object.  The
19 specifier object, in turn, is ``instanced'' in a particular situation
20 to yield the real value of the property in the current context.
21
22 @defun specifierp object
23 This function returns non-@code{nil} if @var{object} is a specifier.
24 @end defun
25
26 @menu
27 * Introduction to Specifiers::  Specifiers provide a clean way for
28                                 display and other properties to vary
29                                 (under user control) in a wide variety
30                                 of contexts.
31 * Simple Specifier Usage::      Getting started with specifiers.
32 * Specifiers In-Depth::         Gory details about specifier innards.
33 * Specifier Instancing::        Instancing means obtaining the ``value'' of
34                                 a specifier in a particular context.
35 * Specifier Types::             Specifiers come in different flavors.
36 * Adding Specifications::       Specifications control a specifier's ``value''
37                                 by giving conditions under which a
38                                 particular value is valid.
39 * Retrieving Specifications::   Querying a specifier's specifications.
40 * Specifier Tag Functions::     Working with specifier tags.
41 * Specifier Instancing Functions::
42                                 Functions to instance a specifier.
43 * Specifier Examples::          Making all this stuff clearer.
44 * Creating Specifiers::         Creating specifiers for your own use.
45 * Specifier Validation Functions::
46                                 Validating the components of a specifier.
47 * Other Specification Functions::
48                                 Other ways of working with specifications.
49 @end menu
50
51
52 @node Introduction to Specifiers
53 @section Introduction to Specifiers
54
55 Perhaps the most useful way to explain specifiers is via an analogy.
56 SXEmacs Lisp programmers are used to @emph{buffer-local variables}
57 @ref{Buffer-Local Variables}. For example, the variable
58 @code{modeline-format}, which controls the format of the modeline, can
59 have different values depending on the particular buffer being edited.
60 The variable has a default value which most modes will use, but a
61 specialized package such as Calendar might change the variable so as to
62 tailor the modeline to its own purposes. Other variables are perhaps
63 best thought of as ``mode local,'' such as font-lock keywords, but they
64 are implemented as buffer locals.
65
66 Other properties (such as those that can be changed by the
67 @code{modify-frame-parameters} function, for example the color of the
68 text cursor) can have frame-local values, although it might also make
69 sense for them to have buffer-local values.  In other cases, you might
70 want the property to vary depending on the particular window within the
71 frame that applies (e.g. the top or bottom window in a split frame), the
72 device type that that frame appears on (X or tty), etc.  Perhaps you can
73 envision some more complicated scenario where you want a particular
74 value in a specified buffer, another value in all other buffers
75 displayed on a particular frame, another value in all other buffers
76 displayed in all other frames on any mono (two-color, e.g. black and
77 white only) displays, and a default value in all other circumstances.
78
79 Specifiers generalize both buffer- and frame-local properties.
80 Specifiers vary according to the @emph{display} context.  Font-lock
81 keywords in a buffer will be the same no matter which window the
82 buffer is displayed in, but windows on TTY devices will simply not be
83 capable of the flexibility that windows on modern GUI devices are.
84 Specifiers provide a way for the programmer to @emph{declare} that an
85 emphasized text should be italic on GUI devices and inverse video on
86 TTYs.  They also provide a way for the programmer to declare
87 fallbacks, so that a color specified as ``chartreuse'' where possible
88 can fall back to ``yellow'' on devices where only ANSI (4-bit) color
89 is available.  The complex calculations and device querying are
90 transparent to both user and programmer.  You ask for what you want;
91 it's up to SXEmacs to provide it, or a reasonable approximation.
92
93 We call such a declaration a @dfn{specification}.  A @dfn{specification}
94 applies in a particular @dfn{locale}, which is a window, buffer, frame,
95 device, or the global locale.  The value part of the specification is
96 called an @dfn{instantiator}.  The process of determining the value in a
97 particular context, or @dfn{domain}, is called @dfn{instantiation} or
98 @dfn{instancing}.  A domain is a window, frame, or device.
99
100 The difference between @dfn{locale} and @dfn{domain} is somewhat subtle.
101 You may think of a locale as a class of domains, which may span
102 different devices.  Since the specification is abstract (a Lisp form),
103 you can state it without reference to a device.  On the other hand, when
104 you instantiate a specification, you must know the type of the device.
105 It is useless to specify that ``blue means emphasis'' on a monochrome
106 device.  Thus instantiation requires specification of the device on
107 which it will be rendered.
108
109 Thus a @dfn{specifier} allows a great deal of flexibility in
110 controlling exactly what value a property has in which circumstances.
111 Specifiers are most commonly used for display properties, such as an image or
112 the foreground color of a face.  As a simple example, you can specify
113 that the foreground of the default face be
114
115 @itemize @bullet
116 @item
117 blue for a particular buffer
118 @item
119 green for all other buffers
120 @end itemize
121
122 As a more complicated example, you could specify that the foreground of
123 the default face be
124
125 @itemize @bullet
126 @item
127 forest green for all buffers displayed in a particular SXEmacs window, or
128 green if the X server doesn't recognize the color @samp{forest green}
129 @item
130 blue for all buffers displayed in a particular frame
131 @item
132 red for all other buffers displayed on a color device
133 @item
134 white for all other buffers
135 @end itemize
136
137
138 @node Simple Specifier Usage
139 @section Simple Specifier Usage
140 @cindex specifier examples
141 @cindex examples, specifier
142 @cindex adding a button to a toolbar
143 @cindex toolbar button, adding
144
145 A useful specifier application is adding a button to a toolbar.  SXEmacs
146 provides several toolbars, one along each edge of the frame.  Normally
147 only one is used at a time, the default.  The default toolbar is
148 actually a specifier object which is the value of
149 @code{default-toolbar}.  @xref{Toolbar Intro}.
150
151 The specification of a toolbar is simple:  it is a list of buttons.
152 Each button is a vector with four elements:  an icon, a command, the
153 enabled flag, and a help string.  Let's retrieve the instance of the
154 toolbar you see in the selected frame.
155
156 @example
157 (specifier-instance default-toolbar)
158 @end example
159
160 The value returned is, as promised, a list of vectors.  Now let's build
161 up a button, and add it to the toolbar.  Our button will invoke the last
162 defined keyboard macro.  This is an alternative to
163 @code{name-last-kbd-macro} for creating a persistent macro, rather than
164 an alias for @kbd{C-x e}.
165
166 A toolbar button icon can be quite sophisticated, with different images
167 for button up, button down, and disabled states, and a similar set with
168 captions.  We'll use a very simple icon, but we have to jump through a
169 few non-obvious hoops designed to support the sophisticated applications.
170 The rest of the button descriptor is straightforward.
171
172 @example
173 (setq toolbar-my-kbd-macro-button
174   `[ (list (make-glyph "MyKbdMac"))
175      (lambda () (interactive) (execute-kbd-macro ,last-kbd-macro))
176      t
177      "Execute a previously defined keyboard macro." ])
178
179 (set-specifier default-toolbar
180                (cons toolbar-my-kbd-macro-button
181                      (specifier-specs default-toolbar 'global))
182                'global)
183 @end example
184
185 To remove the button, just substitute the function @code{delete} for the
186 @code{cons} above.
187
188 What is the difference between @code{specifier-instance}, which we used
189 in the example of retrieving the toolbar descriptor, and
190 @code{specifier-specs}, which was used in the toolbar manipulating code?
191 @code{specifier-specs} retrieves a copy of the instantiator, which is
192 abstract and does not depend on context.  @code{specifier-instance}, on
193 the other hand, actually instantiates the specification, and returns the
194 result for the given context.  Another way to express this is:
195 @code{specifier-specs} takes a @emph{locale} as an argument, while
196 @code{specifier-instance} takes a @emph{domain}.  The reason for
197 providing @code{specifier-instance} is that sometimes you wish to see
198 the object that SXEmacs will actually use.  @code{specifier-specs}, on
199 the other hand, shows you what the programmer (or user) requested.  When
200 a program manipulates specifications, clearly it's the latter that is
201 desirable.
202
203 In the case of the toolbar descriptor, it turns out that these are the
204 same:  the instancing process is trivial.  However, many specifications
205 have non-trivial instancing.  Compare the results of the following forms
206 on my system.  (The @samp{(cdr (first ...))} form is due to my use of
207 Mule.  On non-Mule SXEmacsen, just use @code{specifier-specs}.)
208
209 @example
210 (cdr (first (specifier-specs (face-font 'default) 'global)))
211 => "-*--14-*jisx0208*-0"
212
213 (specifier-instance (face-font 'default))
214 #<font-instance "-*--14-*jisx0208*-0" on #<x-device on ":0.0" 0x970> 0xe0028b 0x176b>
215 @end example
216
217 In this case, @code{specifier-instance} returns an opaque object;
218 programs can't work on it, they can only pass it around.  Worse, in some
219 environments the instantiation will fail, resulting in a different value
220 (when another instantiation succeeds), or worse yet, an error, if all
221 attempts to instance the specifier fail.  @code{specifier-instance} is
222 context-dependent, even for the exact same specification.
223 @code{specifier-specs} is deterministic, and only depends on the
224 specifications.
225
226 Note that in the toolbar-changing code we operate in the global locale.
227 This means that narrower locales, if they have specifications, will
228 shadow our changes.  (Specifier instancing does not merge
229 specifications.  It selects the "highest-priority successful
230 specification" and instances that.)
231
232 In fact, in our example, it seems pretty likely that different buffers
233 @emph{should} have different buttons.  (The icon can be the same, but
234 the keyboard macro you create in a Dired buffer is highly unlikely to be
235 useful in a LaTeX buffer!)  Here's one way to implement this:
236
237 @example
238 (setq toolbar-my-kbd-macro-button
239   `[ (list (make-glyph "MyKbdMac"))
240      (lambda () (interactive) (execute-kbd-macro ,last-kbd-macro))
241      t
242      "Execute a previously defined keyboard macro." ])
243
244 (set-specifier default-toolbar
245                (cons toolbar-my-kbd-macro-button
246                      (cond ((specifier-specs default-toolbar
247                                              (current-buffer)))
248                            ((specifier-specs default-toolbar
249                                              'global)))
250                (current-buffer))
251 @end example
252
253 Finally, a cautionary note: the use of @code{specifier-specs} in the
254 code above is for expository purposes.  Don't use it in production code.
255 In fact, the @code{set-specifier} form above is likely to fail
256 occasionally, because you can add many specifications for the same
257 locale.
258
259 In these cases, @code{specifier-specs} will return a list.  A further
260 refinement is that a specification may be associated with a set of
261 @dfn{specifier tags}.  If the list of specifier tags is non-nil, then
262 @code{specifier-specs} will return a cons of the tag set and the
263 instantiator.  Evidently @code{specifier-specs} is a bit unreliable.
264 (For toolbars, the code above should work 99% of the time, because
265 toolbars are rarely changed.  Since instantiation is trivial, multiple
266 specs are not useful---the first one always succeeds.)
267
268 In fact, @code{specifier-specs} is intended to be used to display specs
269 to humans with a minimum of clutter. The robust way to access
270 specifications is via @code{specifier-spec-list}. @xref{Adding
271 Specifications}, for the definition of @dfn{spec-list}. @xref{Retrieving
272 Specifications}, for documentation of @code{specifier-specs} and
273 @code{specifier-spec-list}. To get the desired effect, replace the form
274 @code{(specifier-spec default-toolbar 'global)} with
275
276 @example
277 (cdr (second (first (specifier-spec-list default-toolbar 'global))))
278 @end example
279
280 (It should be obvious why the example uses the lazy unreliable method!)
281
282
283 @node Specifiers In-Depth
284 @section In-Depth Overview of a Specifier
285 @cindex specification (in a specifier)
286 @cindex domain (in a specifier)
287 @cindex locale (in a specifier)
288 @cindex instantiator (in a specifier)
289 @cindex instancing (in a specifier)
290 @cindex instance (in a specifier)
291 @cindex inst-list (in a specifier)
292 @cindex inst-pair (in a specifier)
293 @cindex tag (in a specifier)
294 @cindex tag set (in a specifier)
295 @cindex specifier, specification
296 @cindex specifier, domain
297 @cindex specifier, locale
298 @cindex specifier, instantiator
299 @cindex specifier, instancing
300 @cindex specifier, instance
301 @cindex specifier, inst-list
302 @cindex specifier, inst-pair
303 @cindex specifier, tag
304 @cindex specifier, tag set
305
306 Having variables vary according the editing context is very useful, and
307 the buffer is the natural ``atomic'' unit of editing context.  In a GUI
308 environment, it can be similarly useful to have variables whose values
309 vary according to display context.  The atomic unit of display context
310 is the SXEmacs window.  Buffers are cleanly grouped by modes, but windows
311 are not so easily pigeonholed.  On the one hand, a window displays a
312 buffer, and thus one possible hierarchy is window, buffer, mode.  On the
313 other, a window is a component of a frame.  This generates the window,
314 frame, device hierarchy.  Finally, there are objects such as toolbars
315 whose properties are described by specifiers.  These do not fit
316 naturally into either hierarchy.  This problem is as yet not cleanly
317 solved.
318
319 Another potential source of conceptual confusion is the instantiation
320 process.  Instantiating a buffer-local variable is simple: at any given
321 point in time there is a current buffer, and its local values are used
322 and set whenever the variable is accessed, unless the programmer goes to
323 some special effort (uses @code{default-value} and @code{set-default}.
324 However, a specifier object encapsulates a set of @dfn{specifications},
325 each of which says what its value should be if a particular condition
326 applies.  Several such conditions might apply simultaneously in a given
327 window.
328
329 For example, one specification might be ``The value should be
330 darkseagreen2 on X devices'' another might be ``The value should be blue
331 in the *Help* buffer''.  So what do we do for "the *Help* buffer on an X
332 device"?  The answer is simple: give each type of locale a priority and
333 check them in priority order, returning the first instantiator that
334 successfully instantiates a value.
335
336 Given a specifier, a logical question is ``What is its value in a
337 particular situation?'' This involves looking through the specifications
338 to see which ones apply to this particular situation, and perhaps
339 preferring one over another if more than one applies.  In specifier
340 terminology, a ``particular situation'' is called a @dfn{domain}, and
341 determining its value in a particular domain is called @dfn{instancing}.
342 Most of the time, a domain is identified by a particular window.  For
343 example, if the redisplay engine is drawing text in the default face in
344 a particular window, it retrieves the specifier for the foreground color
345 of the default face and @dfn{instances} it in the domain given by that
346 window; in other words, it asks the specifier, ``What is your value in
347 this window?''.
348
349 Note that the redisplay example is in a sense canonical.  That is,
350 specifiers are designed to present a uniform and @emph{efficient} API
351 to redisplay.  It is the efficiency constraint that motivates the
352 introduction of specifier tags, and many restrictions on access (for
353 example, a buffer is not a domain, and you cannot instantiate a
354 specifier over a buffer).
355
356 More specifically, a specifier contains a set of @dfn{specifications},
357 each of which associates a @dfn{locale} (a window object, a buffer
358 object, a frame object, a device object, or the symbol @code{global})
359 with an @dfn{inst-list}, which is a list of one or more
360 @dfn{inst-pairs}. (For each possible locale, there can be at most one
361 specification containing that locale.) Each inst-pair is a cons of a
362 @dfn{tag set} (an unordered list of zero or more symbols, or @dfn{tags})
363 and an @dfn{instantiator} (the allowed form of this varies depending on
364 the type of specifier).  In a given specification, there may be more
365 than one inst-pair with the same tag set; this is unlike for locales.
366
367 The tag set is used to restrict the sorts of devices over which the
368 instantiator is valid and to uniquely identify instantiators added by a
369 particular application, so that different applications can work on the
370 same specifier and not interfere with each other.  Each tag can have a
371 @dfn{predicate} associated with it, which is a function of one argument
372 (a device) that specifies whether the tag matches that particular
373 device. (If a tag does not have a predicate, it matches all devices.)
374 All tags in a tag set must match a device for the associated inst-pair
375 to be instantiable over that device.  (A null tag set is perfectly
376 valid, and trivially matches all devices.)
377
378 @c #### don't we have more device types now, gtk, ms-windows, mac-carbon?
379 The valid device types (normally @code{x}, @code{tty}, and
380 @code{stream}) and device classes (normally @code{color},
381 @code{grayscale}, and @code{mono}) can always be used as tags, and match
382 devices of the associated type or class (@pxref{Consoles and Devices}).
383 User-defined tags may be defined, with an optional predicate specified.
384 An application can create its own tag, use it to mark all its
385 instantiators, and be fairly confident that it will not interfere with
386 other applications that modify the same specifier---Functions that add
387 a specification to a specifier usually only overwrite existing
388 inst-pairs with the same tag set as was given, and a particular tag or
389 tag set can be specified when removing instantiators.
390
391 When a specifier is instanced in a domain, both the locale and the tag
392 set can be viewed as specifying necessary conditions that must apply in
393 that domain for an instantiator to be considered as a possible result of
394 the instancing.  More specific locales always override more general
395 locales (thus, there is no particular ordering of the specifications in
396 a specifier); however, the tag sets are simply considered in the order
397 that the inst-pairs occur in the specification's inst-list.
398
399 Note also that the actual object that results from the instancing
400 (called an @dfn{instance object}) may not be the same as the instantiator
401 from which it was derived.  For some specifier types (such as integer
402 specifiers and boolean specifiers), the instantiator will be returned
403 directly as the instance object.  For other types, however, this
404 is not the case.  For example, for font specifiers, the instantiator
405 is a font-description string and the instance object is a font-instance
406 object, which describes how the font is displayed on a particular device.
407 A font-instance object encapsulates such things as the actual font name
408 used to display the font on that device (a font-description string
409 under X is usually a wildcard specification that may resolve to
410 different font names, with possibly different foundries, widths, etc.,
411 on different devices), the extra properties of that font on that
412 device, etc.  Furthermore, this conversion (called @dfn{instantiation})
413 might fail---a font or color might not exist on a particular device,
414 for example.
415
416
417 @node Specifier Instancing
418 @section How a Specifier Is Instanced
419 @cindex fallback (in a specifier)
420 @cindex specifier, fallback
421
422 Instancing of a specifier in a particular window domain proceeds as
423 follows:
424
425 @itemize @bullet
426 @item
427 First, SXEmacs searches for a specification whose locale is the same as
428 the window.  If that fails, the search is repeated, looking for a locale
429 that is the same as the window's buffer.  If that fails, the search is
430 repeated using the window's frame, then using the device that frame is
431 on.  Finally, the specification whose locale is the symbol @code{global}
432 (if there is such a specification) is considered.
433 @item
434 The inst-pairs contained in the specification that was found are
435 considered in their order in the inst-list, looking for one whose tag
436 set matches the device that is derived from the window domain.  (The
437 tag set is an unordered list of zero or more tag symbols.  For all
438 tags that have predicates associated with them, the predicate must
439 match the device.)
440 @item
441 If a matching tag set is found, the corresponding instantiator is passed
442 to the specifier's instantiation method, which is specific to the type
443 of the specifier.  If it succeeds, the resulting instance object is
444 returned as the result of the instancing and the instancing is done.
445 Otherwise, the operation continues, looking for another matching
446 inst-pair in the current specification.
447 @item
448 When there are no more inst-pairs to be considered in the current
449 specification, the search starts over, looking for another specification
450 as in the first step above.
451 @item
452 If all specifications are exhausted and no instance object can be
453 derived, the instancing fails. (Actually, this is not completely true.
454 Some specifier objects for built-in properties have a @dfn{fallback}
455 value, which is either an inst-list or another specifier object, that is
456 consulted if the instancing is about to fail.  If it is an inst-list,
457 the searching proceeds using the inst-pairs in that list.  If it is a
458 specifier, the entire instancing starts over using that specifier
459 instead of the given one.  Fallback values are set by the C code and
460 cannot be modified, except perhaps indirectly, using any Lisp functions.
461 The purpose of them is to supply some values to make sure that
462 instancing of built-in properties can't fail and to implement some basic
463 specifier inheritance, such as the fact that faces inherit their
464 properties from the @code{default} face.)
465 @end itemize
466
467 It is also possible to instance a specifier over a frame domain or
468 device domain instead of over a window domain.  The C code, for example,
469 instances the @code{top-toolbar-height} variable over a frame domain in
470 order to determine the height of a frame's top toolbar.  Instancing over
471 a frame or device is similar to instancing over a window except that
472 specifications for locales that cannot be derived from the domain are
473 ignored.  Specifically, instancing over a frame looks first for frame
474 locales, then device locales, then the @code{global} locale.  Instancing
475 over a device domain looks only for device locales and the @code{global}
476 locale.
477
478
479 @node Specifier Types
480 @section Specifier Types
481
482 There are various different types of specifiers.  The type of a
483 specifier controls what sorts of instantiators are valid, how an
484 instantiator is instantiated, etc.  Here is a list of built-in specifier
485 types:
486
487 @table @code
488 @item boolean
489 The valid instantiators are the symbols @code{t} and @code{nil}.
490 Instance objects are the same as instantiators so no special
491 instantiation function is needed.
492
493 @item integer
494 The valid instantiators are integers.  Instance objects are the same as
495 instantiators so no special instantiation function is needed.
496 @code{modeline-shadow-thickness} is an example of an integer specifier
497 (negative thicknesses indicate that the shadow is drawn recessed instead
498 of raised).
499
500 @item natnum
501 The valid instantiators are natnums (non-negative integers).  Instance
502 objects are the same as instantiators so no special instantiation
503 function is needed.  Natnum specifiers are used for dimension variables
504 such as @code{top-toolbar-height}.
505
506 @item generic
507 All Lisp objects are valid instantiators.  Instance objects are the same
508 as instantiators so no special instantiation function is needed.
509
510 @item font
511 The valid instantiators are strings describing fonts or vectors
512 indicating inheritance from the font of some face.  Instance objects are
513 font-instance objects, which are specific to a particular device.  The
514 instantiation method for font specifiers can fail, unlike for integer,
515 natnum, boolean, and generic specifiers.
516
517 @item color
518 The valid instantiators are strings describing colors or vectors
519 indicating inheritance from the foreground or background of some face.
520 Instance objects are color-instance objects, which are specific to a
521 particular device.  The instantiation method for color specifiers can fail,
522 as for font specifiers.
523
524 @item image
525 Images are perhaps the most complicated type of built-in specifier.  The
526 valid instantiators are strings (a filename, inline data for a pixmap,
527 or text to be displayed in a text glyph) or vectors describing inline
528 data of various sorts or indicating inheritance from the
529 background-pixmap property of some face.  Instance objects are either
530 strings (for text images), image-instance objects (for pixmap images),
531 or subwindow objects (for subwindow images).  The instantiation method
532 for image specifiers can fail, as for font and color specifiers.
533
534 @item face-boolean
535 The valid instantiators are the symbols @code{t} and @code{nil} and
536 vectors indicating inheritance from a boolean property of some face.
537 Specifiers of this sort are used for all of the built-in boolean
538 properties of faces.  Instance objects are either the symbol @code{t}
539 or the symbol @code{nil}.
540
541 @item toolbar
542 The valid instantiators are toolbar descriptors, which are lists
543 of toolbar-button descriptors (each of which is a vector of two
544 or four elements).  @xref{Toolbar}, for more information.
545 @end table
546
547 Color and font instance objects can also be used in turn as
548 instantiators for a new color or font instance object.  Since these
549 instance objects are device-specific, the instantiator can be used
550 directly as the new instance object, but only if they are of the same
551 device.  If the devices differ, the base color or font of the
552 instantiating object is effectively used instead as the instantiator.
553
554 @xref{Faces and Window-System Objects}, for more information on fonts,
555 colors, and face-boolean specifiers.  @xref{Glyphs}, for more information
556 about image specifiers.  @xref{Toolbar}, for more information on toolbar
557 specifiers.
558
559 @defun specifier-type specifier
560 This function returns the type of @var{specifier}.  The returned value
561 will be a symbol: one of @code{integer}, @code{boolean}, etc., as
562 listed in the above table.
563 @end defun
564
565 Functions are also provided to query whether an object is a particular
566 kind of specifier:
567
568 @defun boolean-specifier-p object
569 This function returns non-@code{nil} if @var{object} is a boolean
570 specifier.
571 @end defun
572
573 @defun integer-specifier-p object
574 This function returns non-@code{nil} if @var{object} is an integer
575 specifier.
576 @end defun
577
578 @defun natnum-specifier-p object
579 This function returns non-@code{nil} if @var{object} is a natnum
580 specifier.
581 @end defun
582
583 @defun generic-specifier-p object
584 This function returns non-@code{nil} if @var{object} is a generic
585 specifier.
586 @end defun
587
588 @defun face-boolean-specifier-p object
589 This function returns non-@code{nil} if @var{object} is a face-boolean
590 specifier.
591 @end defun
592
593 @defun toolbar-specifier-p object
594 This function returns non-@code{nil} if @var{object} is a toolbar
595 specifier.
596 @end defun
597
598 @defun font-specifier-p object
599 This function returns non-@code{nil} if @var{object} is a font
600 specifier.
601 @end defun
602
603 @defun color-specifier-p object
604 This function returns non-@code{nil} if @var{object} is a color
605 specifier.
606 @end defun
607
608 @defun image-specifier-p object
609 This function returns non-@code{nil} if @var{object} is an image
610 specifier.
611 @end defun
612
613
614 @node Adding Specifications
615 @section Adding specifications to a Specifier
616
617 @defun add-spec-to-specifier specifier instantiator &optional locale tag-set how-to-add
618 This function adds a specification to @var{specifier}.  The
619 specification maps from @var{locale} (which should be a window, buffer,
620 frame, device, or the symbol @code{global}, and defaults to
621 @code{global}) to @var{instantiator}, whose allowed values depend on the
622 type of the specifier.  Optional argument @var{tag-set} limits the
623 instantiator to apply only to the specified tag set, which should be a
624 list of tags all of which must match the device being instantiated over
625 (tags are a device type, a device class, or tags defined with
626 @code{define-specifier-tag}).  Specifying a single symbol for
627 @var{tag-set} is equivalent to specifying a one-element list containing
628 that symbol.  Optional argument @var{how-to-add} specifies what to do if
629 there are already specifications in the specifier.  It should be one of
630
631 @table @code
632 @item prepend
633 Put at the beginning of the current list of instantiators for @var{locale}.
634 @item append
635 Add to the end of the current list of instantiators for @var{locale}.
636 @item remove-tag-set-prepend
637 This is the default.  Remove any existing instantiators whose tag set is
638 the same as @var{tag-set}; then put the new instantiator at the
639 beginning of the current list.
640 @item remove-tag-set-append
641 Remove any existing instantiators whose tag set is the same as
642 @var{tag-set}; then put the new instantiator at the end of the current
643 list.
644 @item remove-locale
645 Remove all previous instantiators for this locale before adding the new
646 spec.
647 @item remove-locale-type
648 Remove all specifications for all locales of the same type as
649 @var{locale} (this includes @var{locale} itself) before adding the new
650 spec.
651 @item remove-all
652 Remove all specifications from the specifier before adding the new spec.
653 @end table
654
655 @code{remove-tag-set-prepend} is the default.
656
657 You can retrieve the specifications for a particular locale or locale type
658 with the function @code{specifier-spec-list} or @code{specifier-specs}.
659 @end defun
660
661 @defun add-spec-list-to-specifier specifier spec-list &optional how-to-add
662 This function adds a @dfn{spec-list} (a list of specifications) to
663 @var{specifier}.  The format of a spec-list is
664
665 @example
666   @code{((@var{locale} (@var{tag-set} . @var{instantiator}) ...) ...)}
667 @end example
668
669 where
670
671 @itemize @bullet
672 @item
673 @var{locale} := a window, a buffer, a frame, a device, or @code{global}
674 @item
675 @var{tag-set} := an unordered list of zero or more @var{tags}, each of
676 which is a symbol
677 @item
678 @var{tag} := a device class (@pxref{Consoles and Devices}), a device type,
679 or a tag defined with @code{define-specifier-tag}
680 @item
681 @var{instantiator} := format determined by the type of specifier
682 @end itemize
683
684 The pair @code{(@var{tag-set} . @var{instantiator})} is called an
685 @dfn{inst-pair}.  A list of inst-pairs is called an @dfn{inst-list}.
686 The pair @code{(@var{locale} . @var{inst-list})} is called a
687 @dfn{specification}.  A spec-list, then, can be viewed as a list of
688 specifications.
689
690 @var{how-to-add} specifies how to combine the new specifications with
691 the existing ones, and has the same semantics as for
692 @code{add-spec-to-specifier}.
693
694 The higher-level function @code{set-specifier} is often
695 more convenient because it allows abbreviations of spec-lists to be used
696 instead of the heavily nested canonical syntax.  However, one should
697 take great care in using them with specifiers types which can have lists
698 as instantiators, such as toolbar specifiers and generic specifiers.  In
699 those cases it's probably best to use @code{add-spec-to-specifier} or
700 @code{add-spec-list-to-specifier}.
701 @end defun
702
703 @defspec let-specifier specifier-list &rest body
704 This special form temporarily adds specifications to specifiers,
705 evaluates forms in @var{body} and restores the specifiers to their
706 previous states.  The specifiers and their temporary specifications are
707 listed in @var{specifier-list}.
708
709 The format of @var{specifier-list} is
710
711 @example
712 ((@var{specifier} @var{value} &optional @var{locale} @var{tag-set} @var{how-to-add}) ...)
713 @end example
714
715 @var{specifier} is the specifier to be temporarily modified.
716 @var{value} is the instantiator to be temporarily added to specifier in
717 @var{locale}.  @var{locale}, @var{tag-set} and @var{how-to-add} have the
718 same meaning as in @code{add-spec-to-specifier}.
719
720 This special form is implemented as a macro; the code resulting from
721 macro expansion will add specifications to specifiers using
722 @code{add-spec-to-specifier}.  After forms in @var{body} are evaluated,
723 the temporary specifications are removed and old specifier spec-lists
724 are restored.
725
726 @var{locale}, @var{tag-set} and @var{how-to-add} may be omitted, and
727 default to @code{nil}.  The value of the last form in @var{body} is
728 returned.
729
730 NOTE: If you want the specifier's instance to change in all
731 circumstances, use @code{(selected-window)} as the @var{locale}.  If
732 @var{locale} is @code{nil} or omitted, it defaults to @code{global}.
733
734 The following example removes the 3D modeline effect in the currently
735 selected window for the duration of a second:
736
737 @example
738 (let-specifier ((modeline-shadow-thickness 0 (selected-window)))
739   (sit-for 1))
740 @end example
741 @end defspec
742
743 @defun set-specifier specifier value &optional locale tag-set how-to-add
744 This function adds some specifications to @var{specifier}.  @var{value}
745 can be a single instantiator or tagged instantiator (added as a global
746 specification), a list of tagged and/or untagged instantiators (added as
747 a global specification), a cons of a locale and instantiator or locale
748 and instantiator list, a list of such conses, or nearly any other
749 reasonable form.  More specifically, @var{value} can be anything
750 accepted by @code{canonicalize-spec-list} (described below).
751
752 @var{locale}, @var{tag-set}, and @var{how-to-add} are the same as in
753 @code{add-spec-to-specifier}.
754
755 Note that @code{set-specifier} is exactly complementary to
756 @code{specifier-specs} except in the case where @var{specifier} has no
757 specs at all in it but @code{nil} is a valid instantiator (in that case,
758 @code{specifier-specs} will return @code{nil} (meaning no specs) and
759 @code{set-specifier} will interpret the @code{nil} as meaning ``I'm
760 adding a global instantiator and its value is @code{nil}''), or in
761 strange cases where there is an ambiguity between a spec-list and an
762 inst-list, etc. (The built-in specifier types are designed in such a way
763 as to avoid any such ambiguities.)  For robust code,
764 @code{set-specifier} should probably be avoided for specifier types
765 which accept lists as instantiators (currently toolbar specifiers and
766 generic specifiers).
767
768 If you want to work with spec-lists, you should probably not use these
769 functions, but should use the lower-level functions
770 @code{specifier-spec-list} and @code{add-spec-list-to-specifier}.  These
771 functions always work with fully-qualified spec-lists; thus, there is no
772 ambiguity.
773 @end defun
774
775 @defun canonicalize-inst-pair inst-pair specifier-type &optional noerror
776 This function canonicalizes the given @var{inst-pair}.
777
778 @var{specifier-type} specifies the type of specifier that this
779 @var{spec-list} will be used for.
780
781 Canonicalizing means converting to the full form for an inst-pair, i.e.
782 @code{(@var{tag-set} . @var{instantiator})}.  A single, untagged
783 instantiator is given a tag set of @code{nil} (the empty set), and a
784 single tag is converted into a tag set consisting only of that tag.
785
786 If @var{noerror} is non-@code{nil}, signal an error if the inst-pair is
787 invalid; otherwise return @code{t}.
788 @end defun
789
790 @defun canonicalize-inst-list inst-list specifier-type &optional noerror
791 This function canonicalizes the given @var{inst-list} (a list of
792 inst-pairs).
793
794 @var{specifier-type} specifies the type of specifier that this @var{inst-list}
795 will be used for.
796
797 Canonicalizing means converting to the full form for an inst-list, i.e.
798 @code{((@var{tag-set} . @var{instantiator}) ...)}.  This function
799 accepts a single inst-pair or any abbreviation thereof or a list of
800 (possibly abbreviated) inst-pairs. (See @code{canonicalize-inst-pair}.)
801
802 If @var{noerror} is non-@code{nil}, signal an error if the inst-list is
803 invalid; otherwise return @code{t}.
804 @end defun
805
806 @defun canonicalize-spec spec specifier-type &optional noerror
807 This function canonicalizes the given @var{spec} (a specification).
808
809 @var{specifier-type} specifies the type of specifier that this
810 @var{spec-list} will be used for.
811
812 Canonicalizing means converting to the full form for a spec, i.e.
813 @code{(@var{locale} (@var{tag-set} . @var{instantiator}) ...)}.  This
814 function accepts a possibly abbreviated inst-list or a cons of a locale
815 and a possibly abbreviated inst-list. (See
816 @code{canonicalize-inst-list}.)
817
818 If @var{noerror} is @code{nil}, signal an error if the specification is
819 invalid; otherwise return @code{t}.
820 @end defun
821
822 @defun canonicalize-spec-list spec-list specifier-type &optional noerror
823 This function canonicalizes the given @var{spec-list} (a list of
824 specifications).
825
826 @var{specifier-type} specifies the type of specifier that this
827 @var{spec-list} will be used for.
828
829 If @var{noerror} is @code{nil}, signal an error if the spec-list is
830 invalid; otherwise return @code{t} for an invalid spec-list.  (Note that
831 this cannot be confused with a canonical spec-list.)
832
833 Canonicalizing means converting to the full form for a spec-list, i.e.
834 @code{((@var{locale} (@var{tag-set} . @var{instantiator}) ...) ...)}.
835 This function accepts a possibly abbreviated specification or a list of
836 such things. (See @code{canonicalize-spec}.) This is the function used
837 to convert spec-lists accepted by @code{set-specifier} and such into a
838 form suitable for @code{add-spec-list-to-specifier}.
839
840 This function tries extremely hard to resolve any ambiguities,
841 and the built-in specifier types (font, image, toolbar, etc.) are
842 designed so that there won't be any ambiguities.
843
844 The canonicalization algorithm is as follows:
845
846 @enumerate
847 @item
848 Attempt to parse @var{spec-list} as a single, possibly abbreviated,
849 specification.
850 @item
851 If that fails, attempt to parse @var{spec-list} as a list of (abbreviated)
852 specifications.
853 @item
854 If that fails, @var{spec-list} is invalid.
855 @end enumerate
856
857 A possibly abbreviated specification @var{spec} is parsed by
858
859 @enumerate
860 @item
861 Attempt to parse @var{spec} as a possibly abbreviated inst-list.
862 @item
863 If that fails, attempt to parse @var{spec} as a cons of a locale and an
864 (abbreviated) inst-list.
865 @item
866 If that fails, @var{spec} is invalid.
867 @end enumerate
868
869 A possibly abbreviated inst-list @var{inst-list} is parsed by
870
871 @enumerate
872 @item
873 Attempt to parse @var{inst-list} as a possibly abbreviated inst-pair.
874 @item
875 If that fails, attempt to parse @var{inst-list} as a list of (abbreviated)
876 inst-pairs.
877 @item
878 If that fails, @var{inst-list} is invalid.
879 @end enumerate
880
881 A possibly abbreviated inst-pair @var{inst-pair} is parsed by
882
883 @enumerate
884 @item
885 Check if @var{inst-pair} is @code{valid-instantiator-p}.
886 @item
887 If not, check if @var{inst-pair} is a cons of something that is a tag, ie,
888 @code{valid-specifier-tag-p}, and something that is @code{valid-instantiator-p}.
889 @item
890 If not, check if @var{inst-pair} is a cons of a list of tags and something that
891 is @code{valid-instantiator-p}.
892 @item
893 Otherwise, @var{inst-pair} is invalid.
894 @end enumerate
895
896 In summary, this function generally prefers more abbreviated forms.
897 @end defun
898
899
900 @node Retrieving Specifications
901 @section Retrieving the Specifications from a Specifier
902
903 @defun specifier-spec-list specifier &optional locale tag-set exact-p
904 This function returns the spec-list of specifications for
905 @var{specifier} in @var{locale}.
906
907 If @var{locale} is a particular locale (a window, buffer, frame, device,
908 or the symbol @code{global}), a spec-list consisting of the
909 specification for that locale will be returned.
910
911 If @var{locale} is a locale type (i.e. one of the symbols @code{window},
912 @code{buffer}, @code{frame}, or @code{device}), a spec-list of the
913 specifications for all locales of that type will be returned.
914
915 If @var{locale} is @code{nil} or the symbol @code{all}, a spec-list of
916 all specifications in @var{specifier} will be returned.
917
918 @var{locale} can also be a list of locales, locale types, and/or
919 @code{all}; the result is as if @code{specifier-spec-list} were called
920 on each element of the list and the results concatenated together.
921
922 Only instantiators where @var{tag-set} (a list of zero or more tags) is
923 a subset of (or possibly equal to) the instantiator's tag set are
924 returned.  (The default value of @code{nil} is a subset of all tag sets,
925 so in this case no instantiators will be screened out.) If @var{exact-p}
926 is non-@code{nil}, however, @var{tag-set} must be equal to an
927 instantiator's tag set for the instantiator to be returned.
928 @end defun
929
930 @defun specifier-specs specifier &optional locale tag-set exact-p
931 This function returns the specification(s) for @var{specifier} in
932 @var{locale}.
933
934 If @var{locale} is a single locale or is a list of one element
935 containing a single locale, then a ``short form'' of the instantiators
936 for that locale will be returned.  Otherwise, this function is identical
937 to @code{specifier-spec-list}.
938
939 The ``short form'' is designed for readability and not for ease of use
940 in Lisp programs, and is as follows:
941
942 @enumerate
943 @item
944 If there is only one instantiator, then an inst-pair (i.e. cons of tag
945 and instantiator) will be returned; otherwise a list of inst-pairs will
946 be returned.
947 @item
948 For each inst-pair returned, if the instantiator's tag is @code{any},
949 the tag will be removed and the instantiator itself will be returned
950 instead of the inst-pair.
951 @item
952 If there is only one instantiator, its value is @code{nil}, and its tag
953 is @code{any}, a one-element list containing @code{nil} will be returned
954 rather than just @code{nil}, to distinguish this case from there being
955 no instantiators at all.
956 @end enumerate
957
958 @end defun
959
960 @defun specifier-fallback specifier
961 This function returns the fallback value for @var{specifier}.  Fallback
962 values are provided by the C code for certain built-in specifiers to
963 make sure that instancing won't fail even if all specs are removed from
964 the specifier, or to implement simple inheritance behavior (e.g. this
965 method is used to ensure that faces other than @code{default} inherit
966 their attributes from @code{default}).  By design, you cannot change the
967 fallback value, and specifiers created with @code{make-specifier} will
968 never have a fallback (although a similar, Lisp-accessible capability
969 may be provided in the future to allow for inheritance).
970
971 The fallback value will be an inst-list that is instanced like
972 any other inst-list, a specifier of the same type as @var{specifier}
973 (results in inheritance), or @code{nil} for no fallback.
974
975 When you instance a specifier, you can explicitly request that the
976 fallback not be consulted. (The C code does this, for example, when
977 merging faces.) See @code{specifier-instance}.
978 @end defun
979
980
981 @node Specifier Tag Functions
982 @section Working With Specifier Tags
983
984 A specifier tag set is an entity that is attached to an instantiator
985 and can be used to restrict the scope of that instantiator to a
986 particular device class or device type and/or to mark instantiators
987 added by a particular package so that they can be later removed.
988
989 A specifier tag set consists of a list of zero or more specifier tags,
990 each of which is a symbol that is recognized by SXEmacs as a tag.  (The
991 valid device types and device classes are always tags, as are any tags
992 defined by @code{define-specifier-tag}.) It is called a ``tag set'' (as
993 opposed to a list) because the order of the tags or the number of times
994 a particular tag occurs does not matter.
995
996 Each tag has a predicate associated with it, which specifies whether
997 that tag applies to a particular device.  The tags which are device
998 types and classes match devices of that type or class.  User-defined
999 tags can have any predicate, or none (meaning that all devices match).
1000 When attempting to instance a specifier, a particular instantiator is
1001 only considered if the device of the domain being instanced over matches
1002 all tags in the tag set attached to that instantiator.
1003
1004 Most of the time, a tag set is not specified, and the instantiator gets
1005 a null tag set, which matches all devices.
1006
1007 @defun valid-specifier-tag-p tag
1008 This function returns non-@code{nil} if @var{tag} is a valid specifier
1009 tag.
1010 @end defun
1011
1012 @defun valid-specifier-tag-set-p tag-set
1013 This function returns non-@code{nil} if @var{tag-set} is a valid
1014 specifier tag set.
1015 @end defun
1016
1017 @defun canonicalize-tag-set tag-set
1018 This function canonicalizes the given tag set.  Two canonicalized tag
1019 sets can be compared with @code{equal} to see if they represent the same
1020 tag set. (Specifically, canonicalizing involves sorting by symbol name
1021 and removing duplicates.)
1022 @end defun
1023
1024 @defun device-matches-specifier-tag-set-p device tag-set
1025 This function returns non-@code{nil} if @var{device} matches specifier
1026 tag set @var{tag-set}.  This means that @var{device} matches each tag in
1027 the tag set.
1028 @end defun
1029
1030 @defun define-specifier-tag tag &optional predicate
1031 This function defines a new specifier tag.  If @var{predicate} is
1032 specified, it should be a function of one argument (a device) that
1033 specifies whether the tag matches that particular device.  If
1034 @var{predicate} is omitted, the tag matches all devices.
1035
1036 You can redefine an existing user-defined specifier tag.  However, you
1037 cannot redefine the built-in specifier tags (the device types and
1038 classes) or the symbols @code{nil}, @code{t}, @code{all}, or
1039 @code{global}.
1040 @end defun
1041
1042 @defun device-matching-specifier-tag-list &optional device
1043 This function returns a list of all specifier tags matching
1044 @var{device}.  @var{device} defaults to the selected device if omitted.
1045 @end defun
1046
1047 @defun specifier-tag-list
1048 This function returns a list of all currently-defined specifier tags.
1049 This includes the built-in ones (the device types and classes).
1050 @end defun
1051
1052 @defun specifier-tag-predicate tag
1053 This function returns the predicate for the given specifier tag.
1054 @end defun
1055
1056
1057 @node Specifier Instancing Functions
1058 @section Functions for Instancing a Specifier
1059
1060 @defun specifier-instance specifier &optional domain default no-fallback
1061 This function instantiates @var{specifier} (returns its value) in
1062 @var{domain}.  If no instance can be generated for this domain, return
1063 @var{default}.
1064
1065 @var{domain} should be a window, frame, or device.  Other values that
1066 are legal as a locale (e.g. a buffer) are not valid as a domain because
1067 they do not provide enough information to identify a particular device
1068 (see @code{valid-specifier-domain-p}).  @var{domain} defaults to the
1069 selected window if omitted.
1070
1071 @dfn{Instantiating} a specifier in a particular domain means determining
1072 the specifier's ``value'' in that domain.  This is accomplished by
1073 searching through the specifications in the specifier that correspond to
1074 all locales that can be derived from the given domain, from specific to
1075 general.  In most cases, the domain is an SXEmacs window.  In that case
1076 specifications are searched for as follows:
1077
1078 @enumerate
1079 @item
1080 A specification whose locale is the window itself;
1081 @item
1082 A specification whose locale is the window's buffer;
1083 @item
1084 A specification whose locale is the window's frame;
1085 @item
1086 A specification whose locale is the window's frame's device;
1087 @item
1088 A specification whose locale is the symbol @code{global}.
1089 @end enumerate
1090
1091 If all of those fail, then the C-code-provided fallback value for this
1092 specifier is consulted (see @code{specifier-fallback}).  If it is an
1093 inst-list, then this function attempts to instantiate that list just as
1094 when a specification is located in the first five steps above.  If the
1095 fallback is a specifier, @code{specifier-instance} is called recursively
1096 on this specifier and the return value used.  Note, however, that if the
1097 optional argument @var{no-fallback} is non-@code{nil}, the fallback
1098 value will not be consulted.
1099
1100 Note that there may be more than one specification matching a particular
1101 locale; all such specifications are considered before looking for any
1102 specifications for more general locales.  Any particular specification
1103 that is found may be rejected because it is tagged to a particular
1104 device class (e.g. @code{color}) or device type (e.g. @code{x}) or both
1105 and the device for the given domain does not match this, or because the
1106 specification is not valid for the device of the given domain (e.g.  the
1107 font or color name does not exist for this particular X server).
1108
1109 The returned value is dependent on the type of specifier.  For example,
1110 for a font specifier (as returned by the @code{face-font} function), the
1111 returned value will be a font-instance object.  For images, the returned
1112 value will be a string, pixmap, or subwindow.
1113 @end defun
1114
1115 @defun specifier-matching-instance specifier matchspec &optional domain default no-fallback
1116 This function returns an instance for @var{specifier} in @var{domain}
1117 that matches @var{matchspec}.  If no instance can be generated for
1118 @var{domain}, return @var{default}.
1119
1120 This function is identical to @code{specifier-instance} except that a
1121 specification will only be considered if it matches @var{matchspec}.
1122 The definition of ``match,'' and allowed values for @var{matchspec}, are
1123 dependent on the particular type of specifier.  Here are some examples:
1124
1125 @itemize
1126 @item
1127 For chartable (e.g. display table) specifiers, @var{matchspec} should be a
1128 character, and the specification (a chartable) must give a value for
1129 that character in order to be considered.  This allows you to specify,
1130 @emph{e.g.}, a buffer-local display table that only gives values for particular
1131 characters.  All other characters are handled as if the buffer-local
1132 display table is not there. (Chartable specifiers are not yet
1133 implemented.)
1134 @item
1135 For font specifiers, @var{matchspec} should be a charset,
1136 and the specification (a font string) must have
1137 a registry that matches the charset's registry.  (This only makes sense
1138 with Mule support.)  This makes it easy to choose a font that can
1139 display a particular character.  (This is what redisplay does, in fact.)
1140 @end itemize
1141 @end defun
1142
1143 @defun specifier-instance-from-inst-list specifier domain inst-list &optional default
1144 This function attempts to convert a particular inst-list into an
1145 instance.  This attempts to instantiate @var{inst-list} in the given
1146 @var{domain}, as if @var{inst-list} existed in a specification in
1147 @var{specifier}.  If the instantiation fails, @var{default} is returned.
1148 In most circumstances, you should not use this function; use
1149 @code{specifier-instance} instead.
1150 @end defun
1151
1152
1153 @node Specifier Examples
1154 @section Examples of Specifier Usage
1155
1156 Now let us present an example to clarify the theoretical discussions we
1157 have been through.  In this example, we will use the general specifier
1158 functions for clarity.  Keep in mind that many types of specifiers, and
1159 some other types of objects that are associated with specifiers
1160 (e.g. faces), provide convenience functions making it easier to work
1161 with objects of that type.
1162
1163 Let us consider the background color of the default face.  A specifier
1164 is used to specify how that color will appear in different domains.
1165 First, let's retrieve the specifier:
1166
1167 @example
1168 (setq sp (face-property 'default 'background))
1169     @result{}   #<color-specifier 0x3da>
1170 @end example
1171
1172 @example
1173 (specifier-specs sp)
1174     @result{}   ((#<buffer "device.c"> (nil . "forest green"))
1175                  (#<window on "Makefile" 0x8a2b> (nil . "hot pink"))
1176                  (#<x-frame "emacs" 0x4ac> (nil . "puke orange")
1177                                            (nil . "moccasin"))
1178                  (#<x-frame "VM" 0x4ac> (nil . "magenta"))
1179                  (global ((tty) . "cyan") (nil . "white"))
1180                 )
1181 @end example
1182
1183 Then, say we want to determine what the background color of the default
1184 face is for the window currently displaying the buffer @samp{*scratch*}.
1185 We call
1186
1187 @example
1188 (get-buffer-window "*scratch*")
1189     @result{} #<window on "*scratch*" 0x4ad>
1190 (window-frame (get-buffer-window "*scratch*"))
1191     @result{} #<x-frame "emacs" 0x4ac>
1192 (specifier-instance sp (get-buffer-window "*scratch*"))
1193     @result{} #<color-instance moccasin 47=(FFFF,E4E4,B5B5) 0x6309>
1194 @end example
1195
1196 Note that we passed a window to @code{specifier-instance}, not a buffer.
1197 We cannot pass a buffer because a buffer by itself does not provide enough
1198 information.  The buffer might not be displayed anywhere at all, or
1199 could be displayed in many different frames on different devices.
1200
1201 The result is arrived at like this:
1202
1203 @enumerate
1204 @item
1205 First, we look for a specification matching the buffer displayed in the
1206 window, i.e. @samp{*scratch*}.  There are none, so we proceed.
1207 @item
1208 Then, we look for a specification matching the window itself.  Again, there
1209 are none.
1210 @item
1211 Then, we look for a specification matching the window's frame.  The
1212 specification @code{(#<x-frame "emacs" 0x4ac> . "puke orange")} is
1213 found.  We call the instantiation method for colors, passing it the
1214 locale we were searching over (i.e. the window, in this case) and the
1215 instantiator (@samp{"puke orange"}).  However, the particular device
1216 which this window is on (let's say it's an X connection) doesn't
1217 recognize the color @samp{"puke orange"}, so the specification is
1218 rejected.
1219 @item
1220 So we continue looking for a specification matching the window's frame.
1221 We find @samp{(#<x-frame "emacs" 0x4ac> . "moccasin")}.  Again, we
1222 call the instantiation method for colors.  This time, the X server
1223 our window is on recognizes the color @samp{moccasin}, and so the
1224 instantiation method succeeds and returns a color instance.
1225 @end enumerate
1226
1227 Here's another example, which implements something like GNU Emacs's
1228 ``frame-local'' variables.
1229
1230 @example
1231 ;; Implementation
1232
1233 ;; There are probably better ways to write this macro
1234 ;; Heaven help you if VAR is a buffer-local; you will become very
1235 ;; confused.  Probably should error on that.
1236 (defmacro define-frame-local-variable (var)
1237   "Make the unbound symbol VAR become a frame-local variable."
1238   (let ((val (if (boundp var) (symbol-value var) nil)))
1239     `(progn
1240       (setq ,var (make-specifier 'generic))
1241       (add-spec-to-specifier ,var ',val 'global))))
1242
1243 ;; I'm not real happy about this terminology, how can `setq' be a defun?
1244 ;; But `frame-set' would have people writing "(frame-set 'foo value)".
1245 (defun frame-setq (var value &optional frame)
1246   "Set the local value of VAR to VALUE in FRAME.
1247
1248 FRAME defaults to the selected frame."
1249   (and frame (not (framep frame))
1250        (error 'invalid-argument "FRAME must be a frame", frame))
1251   (add-spec-to-specifier var value (or frame (selected-frame))))
1252
1253 (defun frame-value (var &optional frame)
1254   "Get the local value of VAR in FRAME.
1255
1256 FRAME defaults to the selected frame."
1257   (and frame (not (framep frame))
1258        (error 'invalid-argument "FRAME must be a frame", frame))
1259   ;; this is not just a map from frames to values; it also falls back
1260   ;; to the global value
1261   (specifier-instance var (or frame (selected-frame))))
1262
1263 ;; for completeness
1264 (defun frame-set-default (var value)
1265   "Set the default value of frame-local variable VAR to VALUE."
1266   (add-spec-to-specifier var value 'global))
1267
1268 (defun frame-get-default (var)
1269   "Get the default value of frame-local variable VAR."
1270   (car (specifier-specs var 'global)))
1271 @end example
1272
1273 Now you can execute the above definitions (eg, with @code{eval-last-sexp})
1274 and switch to @file{*scratch*} to play.  Things will work differently if
1275 you already have a variable named @code{foo}.
1276
1277 @example
1278 ;; Usage
1279
1280 foo
1281 @error{} Symbol's value as variable is void: foo
1282
1283 (define-frame-local-variable foo)
1284 @result{} nil
1285
1286 ;; the value of foo is a specifier, which is an opaque object;
1287 ;; you must use accessor functions to get values
1288
1289 foo
1290 @result{} #<generic-specifier global=(nil) 0x4f5cb>
1291
1292 ;; since no frame-local value is set, the global value (which is the
1293 ;; constant `nil') is returned
1294 (frame-value foo)
1295 @result{} nil
1296
1297 ;; get the default explicitly
1298 (frame-get-default foo)
1299 @result{} nil
1300
1301 ;; get the whole specification list
1302 (specifier-specs foo 'global)
1303 @result{} (nil)
1304
1305 ;; give foo a frame-local value
1306
1307 (frame-setq foo 'bar)
1308 @result{} nil
1309
1310 ;; access foo in several ways
1311
1312 ;; Note that the print function for this kind of specifier only
1313 ;; gives you the global setting.  To get the full list of specs for
1314 ;; debugging or study purposes, you must use specifier-specs or
1315 ;; specifier-spec-list.
1316 foo
1317 @result{} #<generic-specifier global=(nil) 0x4f5cb>
1318
1319 ;; get the whole specification list
1320 (specifier-specs foo)
1321 @result{} ((#<x-frame "Message" 0x1bd66> (nil . bar)) (global (nil)))
1322
1323 ;; get the frame-local value
1324 (frame-value foo)
1325 @result{} bar
1326
1327 ;; get the default explicitly
1328 (frame-get-default foo)
1329 @result{} nil
1330
1331 ;; Switch to another frame and evaluate:
1332 ;; C-x 5 o M-: (frame-setq foo 'baz) RET M-: (frame-value foo) RET
1333 @result{} baz
1334
1335 ;; Switch back.
1336 ;; C-x 5 o
1337 (specifier-specs foo)
1338 @result{} ((#<x-frame "emacs" 0x28ec> (nil . baz))
1339     (#<x-frame "Message" 0x1bd66> (nil . bar))
1340     (global (nil)))
1341
1342 (frame-value foo)
1343 @result{} bar
1344
1345 (frame-get-default foo)
1346 @result{} nil
1347 @end example
1348
1349 Note that since specifiers generalize both frame-local and buffer-local
1350 variables in a sensible way, SXEmacs is not likely to put a high priority
1351 on implementing frame-local variables.
1352 @c Thanks to Jerry James for the following explanation.  He is not
1353 @c responsible for its use here, Stephen Turnbull is.
1354 In fact, some developers think that frame-local variables are evil for
1355 the same reason that buffer-local variables are evil: the declaration is
1356 both global and invisible.  That is, you cannot tell whether a variable
1357 is ``normal,'' buffer-local, or frame-local just by looking at it.  So
1358 if you have namespace management problems, and some other Lisp package
1359 happens to use a variable name that you already declared frame- or
1360 buffer-local, weird stuff happens, and it is extremely hard to track
1361 down.
1362
1363
1364 @node Creating Specifiers
1365 @section Creating New Specifier Objects
1366
1367 @defun make-specifier type
1368 This function creates a new specifier.
1369
1370 A specifier is an object that can be used to keep track of a property
1371 whose value can be per-buffer, per-window, per-frame, or per-device,
1372 and can further be restricted to a particular device-type or device-class.
1373 Specifiers are used, for example, for the various built-in properties of a
1374 face; this allows a face to have different values in different frames,
1375 buffers, etc.  For more information, see @code{specifier-instance},
1376 @code{specifier-specs}, and @code{add-spec-to-specifier}; or, for a detailed
1377 description of specifiers, including how they are instantiated over a
1378 particular domain (i.e. how their value in that domain is determined),
1379 see the chapter on specifiers in the SXEmacs Lisp Reference Manual.
1380
1381 @var{type} specifies the particular type of specifier, and should be one
1382 of the symbols @code{generic}, @code{integer}, @code{natnum},
1383 @code{boolean}, @code{color}, @code{font}, @code{image},
1384 @code{face-boolean}, or @code{toolbar}.
1385
1386 For more information on particular types of specifiers, see the
1387 functions @code{make-generic-specifier}, @code{make-integer-specifier},
1388 @code{make-natnum-specifier}, @code{make-boolean-specifier},
1389 @code{make-color-specifier}, @code{make-font-specifier},
1390 @code{make-image-specifier}, @code{make-face-boolean-specifier}, and
1391 @code{make-toolbar-specifier}.
1392 @end defun
1393
1394 @defun make-specifier-and-init type spec-list &optional dont-canonicalize
1395 This function creates and initializes a new specifier.
1396
1397 This is a convenience API combining @code{make-specifier} and
1398 @code{set-specifier} that allows you to create
1399 a specifier and add specs to it at the same time.  @var{type} specifies
1400 the specifier type.  Allowed types are as for @code{make-specifier}.
1401
1402 @var{spec-list} supplies the specification(s) to be
1403 added to the specifier.  Any abbreviation of
1404 the full spec-list form accepted by @code{canonicalize-spec-list} may
1405 be used.
1406 However, if the optional argument @var{dont-canonicalize} is non-@code{nil},
1407 canonicalization is not performed, and the @var{spec-list} must already
1408 be in full form.
1409 @end defun
1410
1411 @defun make-integer-specifier spec-list
1412
1413 Return a new @code{integer} specifier object with the given
1414 specification list.  @var{spec-list} can be a list of specifications
1415 (each of which is a cons of a locale and a list of instantiators), a
1416 single instantiator, or a list of instantiators.
1417
1418 Valid instantiators for integer specifiers are integers.
1419 @end defun
1420
1421 @defun make-boolean-specifier spec-list
1422
1423 Return a new @code{boolean} specifier object with the given
1424 specification list.  @var{spec-list} can be a list of specifications
1425 (each of which is a cons of a locale and a list of instantiators), a
1426 single instantiator, or a list of instantiators.
1427
1428 Valid instantiators for boolean specifiers are @code{t} and @code{nil}.
1429 @end defun
1430
1431 @defun make-natnum-specifier spec-list
1432
1433 Return a new @code{natnum} specifier object with the given specification
1434 list.  @var{spec-list} can be a list of specifications (each of which is
1435 a cons of a locale and a list of instantiators), a single instantiator,
1436 or a list of instantiators.
1437
1438 Valid instantiators for natnum specifiers are non-negative integers.
1439 @end defun
1440
1441 @defun make-generic-specifier spec-list
1442
1443 Return a new @code{generic} specifier object with the given
1444 specification list.  @var{spec-list} can be a list of specifications
1445 (each of which is a cons of a locale and a list of instantiators), a
1446 single instantiator, or a list of instantiators.
1447
1448 Valid instantiators for generic specifiers are all Lisp values.  They
1449 are returned back unchanged when a specifier is instantiated.
1450 @end defun
1451
1452 @defun make-display-table-specifier spec-list
1453
1454 Return a new @code{display-table} specifier object with the given spec
1455 list.  @var{spec-list} can be a list of specifications (each of which is
1456 a cons of a locale and a list of instantiators), a single instantiator,
1457 or a list of instantiators.
1458
1459 Valid instantiators for display-table specifiers are described in detail
1460 in the doc string for @code{current-display-table} (@pxref{Active
1461 Display Table}).
1462 @end defun
1463
1464
1465 @node Specifier Validation Functions
1466 @section Functions for Checking the Validity of Specifier Components
1467
1468 @defun valid-specifier-domain-p domain
1469 This function returns non-@code{nil} if @var{domain} is a valid
1470 specifier domain.  A domain is used to instance a specifier
1471 (i.e. determine the specifier's value in that domain).  Valid domains
1472 are a window, frame, or device.  (@code{nil} is not valid.)
1473 @end defun
1474
1475 @defun valid-specifier-locale-p locale
1476 This function returns non-@code{nil} if @var{locale} is a valid
1477 specifier locale.  Valid locales are a device, a frame, a window, a
1478 buffer, and @code{global}.  (@code{nil} is not valid.)
1479 @end defun
1480
1481 @defun valid-specifier-locale-type-p locale-type
1482 Given a specifier @var{locale-type}, this function returns non-@code{nil} if it
1483 is valid.  Valid locale types are the symbols @code{global},
1484 @code{device}, @code{frame}, @code{window}, and @code{buffer}. (Note,
1485 however, that in functions that accept either a locale or a locale type,
1486 @code{global} is considered an individual locale.)
1487 @end defun
1488
1489 @defun valid-specifier-type-p specifier-type
1490 Given a @var{specifier-type}, this function returns non-@code{nil} if it
1491 is valid.  Valid types are @code{generic}, @code{integer},
1492 @code{boolean}, @code{color}, @code{font}, @code{image},
1493 @code{face-boolean}, and @code{toolbar}.
1494 @end defun
1495
1496 @defun valid-specifier-tag-p tag
1497 This function returns non-@code{nil} if @var{tag} is a valid specifier
1498 tag.
1499 @end defun
1500
1501 @defun valid-instantiator-p instantiator specifier-type
1502 This function returns non-@code{nil} if @var{instantiator} is valid for
1503 @var{specifier-type}.
1504 @end defun
1505
1506 @defun valid-inst-list-p inst-list type
1507 This function returns non-@code{nil} if @var{inst-list} is valid for
1508 specifier type @var{type}.
1509 @end defun
1510
1511 @defun valid-spec-list-p spec-list type
1512 This function returns non-@code{nil} if @var{spec-list} is valid for
1513 specifier type @var{type}.
1514 @end defun
1515
1516 @defun check-valid-instantiator instantiator specifier-type
1517 This function signals an error if @var{instantiator} is invalid for
1518 @var{specifier-type}.
1519 @end defun
1520
1521 @defun check-valid-inst-list inst-list type
1522 This function signals an error if @var{inst-list} is invalid for
1523 specifier type @var{type}.
1524 @end defun
1525
1526 @defun check-valid-spec-list spec-list type
1527 This function signals an error if @var{spec-list} is invalid for
1528 specifier type @var{type}.
1529 @end defun
1530
1531
1532 @node Other Specification Functions
1533 @section Other Functions for Working with Specifications in a Specifier
1534
1535 @defun copy-specifier specifier &optional dest locale tag-set exact-p how-to-add
1536 This function copies @var{specifier} to @var{dest}, or creates a new one
1537 if @var{dest} is @code{nil}.
1538
1539 If @var{dest} is @code{nil} or omitted, a new specifier will be created
1540 and the specifications copied into it.  Otherwise, the specifications
1541 will be copied into the existing specifier in @var{dest}.
1542
1543 If @var{locale} is @code{nil} or the symbol @code{all}, all
1544 specifications will be copied.  If @var{locale} is a particular locale,
1545 the specification for that particular locale will be copied.  If
1546 @var{locale} is a locale type, the specifications for all locales of
1547 that type will be copied.  @var{locale} can also be a list of locales,
1548 locale types, and/or @code{all}; this is equivalent to calling
1549 @code{copy-specifier} for each of the elements of the list.  See
1550 @code{specifier-spec-list} for more information about @var{locale}.
1551
1552 Only instantiators where @var{tag-set} (a list of zero or more tags) is
1553 a subset of (or possibly equal to) the instantiator's tag set are
1554 copied.  (The default value of @code{nil} is a subset of all tag sets,
1555 so in this case no instantiators will be screened out.) If @var{exact-p}
1556 is non-@code{nil}, however, @var{tag-set} must be equal to an
1557 instantiator's tag set for the instantiator to be copied.
1558
1559 Optional argument @var{how-to-add} specifies what to do with existing
1560 specifications in @var{dest}.  If @code{nil}, then whichever locales or locale
1561 types are copied will first be completely erased in @var{dest}.
1562 Otherwise, it is the same as in @code{add-spec-to-specifier}.
1563 @end defun
1564
1565 @defun remove-specifier specifier &optional locale tag-set exact-p
1566 This function removes specification(s) for @var{specifier}.
1567
1568 If @var{locale} is a particular locale (a buffer, window, frame, device,
1569 or the symbol @code{global}), the specification for that locale will be
1570 removed.
1571
1572 If instead, @var{locale} is a locale type (i.e. a symbol @code{buffer},
1573 @code{window}, @code{frame}, or @code{device}), the specifications for
1574 all locales of that type will be removed.
1575
1576 If @var{locale} is @code{nil} or the symbol @code{all}, all
1577 specifications will be removed.
1578
1579 @var{locale} can also be a list of locales, locale types, and/or
1580 @code{all}; this is equivalent to calling @code{remove-specifier} for
1581 each of the elements in the list.
1582
1583 Only instantiators where @var{tag-set} (a list of zero or more tags) is
1584 a subset of (or possibly equal to) the instantiator's tag set are
1585 removed.  (The default value of @code{nil} is a subset of all tag sets,
1586 so in this case no instantiators will be screened out.) If @var{exact-p}
1587 is non-@code{nil}, however, @var{tag-set} must be equal to an
1588 instantiator's tag set for the instantiator to be removed.
1589 @end defun
1590
1591 @defun map-specifier specifier func &optional locale maparg
1592 This function applies @var{func} to the specification(s) for
1593 @var{locale} in @var{specifier}.
1594
1595 If optional @var{locale} is a locale, @var{func} will be called for that
1596 locale.
1597 If @var{locale} is a locale type, @var{func} will be mapped over all
1598 locales of that type.  If @var{locale} is @code{nil} or the symbol
1599 @code{all}, @var{func} will be mapped over all locales in
1600 @var{specifier}.
1601
1602 Optional @var{ms-maparg} will be passed to @var{ms-func}.
1603
1604 @var{func} is called with four arguments: the @var{specifier}, the
1605 locale being mapped over, the inst-list for that locale, and the
1606 optional @var{maparg}.  If any invocation of @var{func} returns
1607 non-@code{nil}, the mapping will stop and the returned value becomes the
1608 value returned from @code{map-specifier}.  Otherwise,
1609 @code{map-specifier} returns @code{nil}.
1610 @end defun
1611
1612 @defun specifier-locale-type-from-locale locale
1613 Given a specifier @var{locale}, this function returns its type.
1614 @end defun