annotate lisp/format.el @ 18092:8428d56cd207

(smtpmail-via-smtp): Recognize XVRB as a synonym for VERB and XONE as a synonym for ONEX. (smtpmail-read-response): Add "%s" to `message' calls to avoid problems with percent signs in strings. (smtpmail-read-response): Return all lines of the response text as a list of strings. Formerly only the first line was returned. This is insufficient when one wants to parse e.g. an EHLO response. Ignore responses starting with "0". This is necessary to support the VERB SMTP extension. (smtpmail-via-smtp): Try EHLO and find out which SMTP service extensions the receiving mailer supports. Issue the ONEX and XUSR commands if the corresponding extensions are supported. Issue VERB if supported and `smtpmail-debug-info' is non-nil. Add SIZE attribute to MAIL FROM: command if SIZE extension is supported. Add code that could set the BODY= attribute to MAIL FROM: if the receiving mailer supports 8BITMIME. This is currently disabled, since doing it right might involve adding MIME headers to, and in some cases reencoding, the message.
author Richard M. Stallman <rms@gnu.org>
date Sun, 01 Jun 1997 22:24:22 +0000
parents 380e33f3a5c6
children f16cf00a2f42
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
13352
8dba183df579 Correct initial line typo.
Erik Naggum <erik@naggum.no>
parents: 13337
diff changeset
1 ;;; format.el --- read and save files in multiple formats
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
2
11234
4d2a2fe1d8d7 Update copyright.
Karl Heuer <kwzh@gnu.org>
parents: 11054
diff changeset
3 ;; Copyright (c) 1994, 1995 Free Software Foundation
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
4
12082
257af4819582 Change email address for Boris.
Boris Goldowsky <boris@gnu.org>
parents: 11234
diff changeset
5 ;; Author: Boris Goldowsky <boris@gnu.ai.mit.edu>
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
6
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
7 ;; This file is part of GNU Emacs.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
8
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
9 ;; GNU Emacs is free software; you can redistribute it and/or modify
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
10 ;; it under the terms of the GNU General Public License as published by
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
11 ;; the Free Software Foundation; either version 2, or (at your option)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
12 ;; any later version.
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
13
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
14 ;; GNU Emacs is distributed in the hope that it will be useful,
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
15 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
16 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
17 ;; GNU General Public License for more details.
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
18
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
19 ;; You should have received a copy of the GNU General Public License
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
20 ;; along with GNU Emacs; see the file COPYING. If not, write to the
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
21 ;; Free Software Foundation, Inc., 59 Temple Place - Suite 330,
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
22 ;; Boston, MA 02111-1307, USA.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
23
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
24 ;;; Commentary:
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
25
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
26 ;; This file defines a unified mechanism for saving & loading files stored
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
27 ;; in different formats. `format-alist' contains information that directs
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
28 ;; Emacs to call an encoding or decoding function when reading or writing
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
29 ;; files that match certain conditions.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
30 ;;
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
31 ;; When a file is visited, its format is determined by matching the
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
32 ;; beginning of the file against regular expressions stored in
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
33 ;; `format-alist'. If this fails, you can manually translate the buffer
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
34 ;; using `format-decode-buffer'. In either case, the formats used are
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
35 ;; listed in the variable `buffer-file-format', and become the default
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
36 ;; format for saving the buffer. To save a buffer in a different format,
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
37 ;; change this variable, or use `format-write-file'.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
38 ;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
39 ;; Auto-save files are normally created in the same format as the visited
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
40 ;; file, but the variable `auto-save-file-format' can be set to a
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
41 ;; particularly fast or otherwise preferred format to be used for
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
42 ;; auto-saving (or nil to do no encoding on auto-save files, but then you
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
43 ;; risk losing any text-properties in the buffer).
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
44 ;;
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
45 ;; You can manually translate a buffer into or out of a particular format
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
46 ;; with the functions `format-encode-buffer' and `format-decode-buffer'.
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
47 ;; To translate just the region use the functions `format-encode-region'
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
48 ;; and `format-decode-region'.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
49 ;;
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
50 ;; You can define a new format by writing the encoding and decoding
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
51 ;; functions, and adding an entry to `format-alist'. See enriched.el for
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
52 ;; an example of how to implement a file format. There are various
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
53 ;; functions defined in this file that may be useful for writing the
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
54 ;; encoding and decoding functions:
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
55 ;; * `format-annotate-region' and `format-deannotate-region' allow a
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
56 ;; single alist of information to be used for encoding and decoding.
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
57 ;; The alist defines a correspondence between strings in the file
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
58 ;; ("annotations") and text-properties in the buffer.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
59 ;; * `format-replace-strings' is similarly useful for doing simple
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
60 ;; string->string translations in a reversible manner.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
61
14169
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
62 ;;; Code:
83f275dcd93a Update FSF's address.
Erik Naggum <erik@naggum.no>
parents: 13983
diff changeset
63
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
64 (put 'buffer-file-format 'permanent-local t)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
65
16686
c5f50169bfbe (format-alist): Change defconst to defvar.
Richard M. Stallman <rms@gnu.org>
parents: 16020
diff changeset
66 (defvar format-alist
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
67 '((text/enriched "Extended MIME text/enriched format."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
68 "Content-[Tt]ype:[ \t]*text/enriched"
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
69 enriched-decode enriched-encode t enriched-mode)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
70 (plain "Standard ASCII format, no text properties."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
71 ;; Plain only exists so that there is an obvious neutral choice in
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
72 ;; the completion list.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
73 nil nil nil nil nil))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
74 "List of information about understood file formats.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
75 Elements are of the form \(NAME DOC-STR REGEXP FROM-FN TO-FN MODIFY MODE-FN).
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
76 NAME is a symbol, which is stored in `buffer-file-format'.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
77 DOC-STR should be a single line providing more information about the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
78 format. It is currently unused, but in the future will be shown to
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
79 the user if they ask for more information.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
80 REGEXP is a regular expression to match against the beginning of the file;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
81 it should match only files in that format.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
82 FROM-FN is called to decode files in that format; it gets two args, BEGIN
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
83 and END, and can make any modifications it likes, returning the new
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
84 end. It must make sure that the beginning of the file no longer
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
85 matches REGEXP, or else it will get called again.
16020
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
86 TO-FN is called to encode a region into that format; it is passed three
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
87 arguments: BEGIN, END, and BUFFER. BUFFER is the original buffer that
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
88 the data being written came from, which the function could use, for
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
89 example, to find the values of local variables. TO-FN should either
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
90 return a list of annotations like `write-region-annotate-functions',
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
91 or modify the region and return the new end.
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
92 MODIFY, if non-nil, means the TO-FN wants to modify the region. If nil,
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
93 TO-FN will not make any changes but will instead return a list of
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
94 annotations.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
95 MODE-FN, if specified, is called when visiting a file with that format.")
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
96
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
97 ;;; Basic Functions (called from Lisp)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
98
16020
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
99 (defun format-annotate-function (format from to orig-buf)
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
100 "Returns annotations for writing region as FORMAT.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
101 FORMAT is a symbol naming one of the formats defined in `format-alist',
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
102 it must be a single symbol, not a list like `buffer-file-format'.
16020
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
103 FROM and TO delimit the region to be operated on in the current buffer.
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
104 ORIG-BUF is the original buffer that the data came from.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
105 This function works like a function on `write-region-annotate-functions':
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
106 it either returns a list of annotations, or returns with a different buffer
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
107 current, which contains the modified text to write.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
108
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
109 For most purposes, consider using `format-encode-region' instead."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
110 ;; This function is called by write-region (actually build-annotations)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
111 ;; for each element of buffer-file-format.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
112 (let* ((info (assq format format-alist))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
113 (to-fn (nth 4 info))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
114 (modify (nth 5 info)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
115 (if to-fn
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
116 (if modify
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
117 ;; To-function wants to modify region. Copy to safe place.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
118 (let ((copy-buf (get-buffer-create " *Format Temp*")))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
119 (copy-to-buffer copy-buf from to)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
120 (set-buffer copy-buf)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
121 (format-insert-annotations write-region-annotations-so-far from)
16020
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
122 (funcall to-fn (point-min) (point-max) orig-buf)
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
123 nil)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
124 ;; Otherwise just call function, it will return annotations.
16020
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
125 (funcall to-fn from to orig-buf)))))
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
126
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
127 (defun format-decode (format length &optional visit-flag)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
128 ;; This function is called by insert-file-contents whenever a file is read.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
129 "Decode text from any known FORMAT.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
130 FORMAT is a symbol appearing in `format-alist' or a list of such symbols,
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
131 or nil, in which case this function tries to guess the format of the data by
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
132 matching against the regular expressions in `format-alist'. After a match is
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
133 found and the region decoded, the alist is searched again from the beginning
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
134 for another match.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
135
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
136 Second arg LENGTH is the number of characters following point to operate on.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
137 If optional third arg VISIT-FLAG is true, set `buffer-file-format'
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
138 to the list of formats used, and call any mode functions defined for those
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
139 formats.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
140
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
141 Returns the new length of the decoded region.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
142
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
143 For most purposes, consider using `format-decode-region' instead."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
144 (let ((mod (buffer-modified-p))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
145 (begin (point))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
146 (end (+ (point) length)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
147 (if (null format)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
148 ;; Figure out which format it is in, remember list in `format'.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
149 (let ((try format-alist))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
150 (while try
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
151 (let* ((f (car try))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
152 (regexp (nth 2 f))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
153 (p (point)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
154 (if (and regexp (looking-at regexp)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
155 (< (match-end 0) (+ begin length)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
156 (progn
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
157 (setq format (cons (car f) format))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
158 ;; Decode it
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
159 (if (nth 3 f) (setq end (funcall (nth 3 f) begin end)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
160 ;; Call visit function if required
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
161 (if (and visit-flag (nth 6 f)) (funcall (nth 6 f) 1))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
162 ;; Safeguard against either of the functions changing pt.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
163 (goto-char p)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
164 ;; Rewind list to look for another format
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
165 (setq try format-alist))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
166 (setq try (cdr try))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
167 ;; Deal with given format(s)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
168 (or (listp format) (setq format (list format)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
169 (let ((do format) f)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
170 (while do
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
171 (or (setq f (assq (car do) format-alist))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
172 (error "Unknown format" (car do)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
173 ;; Decode:
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
174 (if (nth 3 f) (setq end (funcall (nth 3 f) begin end)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
175 ;; Call visit function if required
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
176 (if (and visit-flag (nth 6 f)) (funcall (nth 6 f) 1))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
177 (setq do (cdr do)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
178 (if visit-flag
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
179 (setq buffer-file-format format))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
180 (set-buffer-modified-p mod)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
181 ;; Return new length of region
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
182 (- end begin)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
183
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
184 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
185 ;;; Interactive functions & entry points
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
186 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
187
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
188 (defun format-decode-buffer (&optional format)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
189 "Translate the buffer from some FORMAT.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
190 If the format is not specified, this function attempts to guess.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
191 `buffer-file-format' is set to the format used, and any mode-functions
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
192 for the format are called."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
193 (interactive
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
194 (list (format-read "Translate buffer from format (default: guess): ")))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
195 (save-excursion
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
196 (goto-char (point-min))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
197 (format-decode format (buffer-size) t)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
198
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
199 (defun format-decode-region (from to &optional format)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
200 "Decode the region from some format.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
201 Arg FORMAT is optional; if omitted the format will be determined by looking
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
202 for identifying regular expressions at the beginning of the region."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
203 (interactive
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
204 (list (region-beginning) (region-end)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
205 (format-read "Translate region from format (default: guess): ")))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
206 (save-excursion
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
207 (goto-char from)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
208 (format-decode format (- to from) nil)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
209
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
210 (defun format-encode-buffer (&optional format)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
211 "Translate the buffer into FORMAT.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
212 FORMAT defaults to `buffer-file-format'. It is a symbol naming one of the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
213 formats defined in `format-alist', or a list of such symbols."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
214 (interactive
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
215 (list (format-read (format "Translate buffer to format (default %s): "
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
216 buffer-file-format))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
217 (format-encode-region (point-min) (point-max) format))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
218
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
219 (defun format-encode-region (beg end &optional format)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
220 "Translate the region into some FORMAT.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
221 FORMAT defaults to `buffer-file-format', it is a symbol naming
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
222 one of the formats defined in `format-alist', or a list of such symbols."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
223 (interactive
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
224 (list (region-beginning) (region-end)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
225 (format-read (format "Translate region to format (default %s): "
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
226 buffer-file-format))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
227 (if (null format) (setq format buffer-file-format))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
228 (if (symbolp format) (setq format (list format)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
229 (save-excursion
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
230 (goto-char end)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
231 (let ((cur-buf (current-buffer))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
232 (end (point-marker)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
233 (while format
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
234 (let* ((info (assq (car format) format-alist))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
235 (to-fn (nth 4 info))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
236 (modify (nth 5 info))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
237 result)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
238 (if to-fn
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
239 (if modify
16020
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
240 (setq end (funcall to-fn beg end (current-buffer)))
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
241 (format-insert-annotations
0f704de0600f (format-alist): Doc fix.
Richard M. Stallman <rms@gnu.org>
parents: 14452
diff changeset
242 (funcall to-fn beg end (current-buffer)))))
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
243 (setq format (cdr format)))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
244
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
245 (defun format-write-file (filename format)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
246 "Write current buffer into a FILE using some FORMAT.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
247 Makes buffer visit that file and sets the format as the default for future
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
248 saves. If the buffer is already visiting a file, you can specify a directory
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
249 name as FILE, to write a file of the same old name in that directory."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
250 (interactive
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
251 ;; Same interactive spec as write-file, plus format question.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
252 (let* ((file (if buffer-file-name
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
253 (read-file-name "Write file: "
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
254 nil nil nil nil)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
255 (read-file-name "Write file: "
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
256 (cdr (assq 'default-directory
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
257 (buffer-local-variables)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
258 nil nil (buffer-name))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
259 (fmt (format-read (format "Write file `%s' in format: "
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
260 (file-name-nondirectory file)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
261 (list file fmt)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
262 (setq buffer-file-format format)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
263 (write-file filename))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
264
12154
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
265 (defun format-find-file (filename format)
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
266 "Find the file FILE using data format FORMAT.
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
267 If FORMAT is nil then do not do any format conversion."
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
268 (interactive
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
269 ;; Same interactive spec as write-file, plus format question.
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
270 (let* ((file (read-file-name "Find file: "))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
271 (fmt (format-read (format "Read file `%s' in format: "
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
272 (file-name-nondirectory file)))))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
273 (list file fmt)))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
274 (let ((format-alist nil))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
275 (find-file filename))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
276 (if format
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
277 (format-decode-buffer format)))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
278
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
279 (defun format-insert-file (filename format &optional beg end)
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
280 "Insert the contents of file FILE using data format FORMAT.
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
281 If FORMAT is nil then do not do any format conversion.
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
282 The optional third and fourth arguments BEG and END specify
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
283 the part of the file to read.
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
284
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
285 The return value is like the value of `insert-file-contents':
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
286 a list (ABSOLUTE-FILE-NAME . SIZE)."
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
287 (interactive
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
288 ;; Same interactive spec as write-file, plus format question.
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
289 (let* ((file (read-file-name "Find file: "))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
290 (fmt (format-read (format "Read file `%s' in format: "
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
291 (file-name-nondirectory file)))))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
292 (list file fmt)))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
293 (let (value size)
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
294 (let ((format-alist nil))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
295 (setq value (insert-file-contents filename nil beg end))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
296 (setq size (nth 1 value)))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
297 (if format
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
298 (setq size (format-decode size format)
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
299 value (cons (car value) size)))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
300 value))
38a933f88c87 (format-find-file, format-insert-file): New functions.
Karl Heuer <kwzh@gnu.org>
parents: 12082
diff changeset
301
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
302 (defun format-read (&optional prompt)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
303 "Read and return the name of a format.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
304 Return value is a list, like `buffer-file-format'; it may be nil.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
305 Formats are defined in `format-alist'. Optional arg is the PROMPT to use."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
306 (let* ((table (mapcar (lambda (x) (list (symbol-name (car x))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
307 format-alist))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
308 (ans (completing-read (or prompt "Format: ") table nil t)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
309 (if (not (equal "" ans)) (list (intern ans)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
310
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
311
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
312 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
313 ;;; Below are some functions that may be useful in writing encoding and
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
314 ;;; decoding functions for use in format-alist.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
315 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
316
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
317 (defun format-replace-strings (alist &optional reverse beg end)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
318 "Do multiple replacements on the buffer.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
319 ALIST is a list of (from . to) pairs, which should be proper arguments to
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
320 `search-forward' and `replace-match' respectively.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
321 Optional 2nd arg REVERSE, if non-nil, means the pairs are (to . from), so that
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
322 you can use the same list in both directions if it contains only literal
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
323 strings.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
324 Optional args BEGIN and END specify a region of the buffer to operate on."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
325 (save-excursion
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
326 (save-restriction
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
327 (or beg (setq beg (point-min)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
328 (if end (narrow-to-region (point-min) end))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
329 (while alist
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
330 (let ((from (if reverse (cdr (car alist)) (car (car alist))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
331 (to (if reverse (car (cdr alist)) (cdr (car alist)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
332 (goto-char beg)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
333 (while (search-forward from nil t)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
334 (goto-char (match-beginning 0))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
335 (insert to)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
336 (set-text-properties (- (point) (length to)) (point)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
337 (text-properties-at (point)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
338 (delete-region (point) (+ (point) (- (match-end 0)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
339 (match-beginning 0)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
340 (setq alist (cdr alist)))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
341
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
342 ;;; Some list-manipulation functions that we need.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
343
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
344 (defun format-delq-cons (cons list)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
345 "Remove the given CONS from LIST by side effect,
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
346 and return the new LIST. Since CONS could be the first element
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
347 of LIST, write `\(setq foo \(format-delq-cons element foo))' to be sure of
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
348 changing the value of `foo'."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
349 (if (eq cons list)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
350 (cdr list)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
351 (let ((p list))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
352 (while (not (eq (cdr p) cons))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
353 (if (null p) (error "format-delq-cons: not an element."))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
354 (setq p (cdr p)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
355 ;; Now (cdr p) is the cons to delete
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
356 (setcdr p (cdr cons))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
357 list)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
358
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
359 (defun format-make-relatively-unique (a b)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
360 "Delete common elements of lists A and B, return as pair.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
361 Compares using `equal'."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
362 (let* ((acopy (copy-sequence a))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
363 (bcopy (copy-sequence b))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
364 (tail acopy))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
365 (while tail
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
366 (let ((dup (member (car tail) bcopy))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
367 (next (cdr tail)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
368 (if dup (setq acopy (format-delq-cons tail acopy)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
369 bcopy (format-delq-cons dup bcopy)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
370 (setq tail next)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
371 (cons acopy bcopy)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
372
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
373 (defun format-common-tail (a b)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
374 "Given two lists that have a common tail, return it.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
375 Compares with `equal', and returns the part of A that is equal to the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
376 equivalent part of B. If even the last items of the two are not equal,
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
377 returns nil."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
378 (let ((la (length a))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
379 (lb (length b)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
380 ;; Make sure they are the same length
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
381 (if (> la lb)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
382 (setq a (nthcdr (- la lb) a))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
383 (setq b (nthcdr (- lb la) b))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
384 (while (not (equal a b))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
385 (setq a (cdr a)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
386 b (cdr b)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
387 a)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
388
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
389 (defun format-reorder (items order)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
390 "Arrange ITEMS to following partial ORDER.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
391 Elements of ITEMS equal to elements of ORDER will be rearranged to follow the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
392 ORDER. Unmatched items will go last."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
393 (if order
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
394 (let ((item (member (car order) items)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
395 (if item
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
396 (cons (car item)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
397 (format-reorder (format-delq-cons item items)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
398 (cdr order)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
399 (format-reorder items (cdr order))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
400 items))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
401
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
402 (put 'face 'format-list-valued t) ; These text-properties take values
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
403 (put 'unknown 'format-list-valued t) ; that are lists, the elements of which
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
404 ; should be considered separately.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
405 ; See format-deannotate-region and
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
406 ; format-annotate-region.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
407
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
408 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
409 ;;; Decoding
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
410 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
411
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
412 (defun format-deannotate-region (from to translations next-fn)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
413 "Translate annotations in the region into text properties.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
414 This sets text properties between FROM to TO as directed by the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
415 TRANSLATIONS and NEXT-FN arguments.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
416
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
417 NEXT-FN is a function that searches forward from point for an annotation.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
418 It should return a list of 4 elements: \(BEGIN END NAME POSITIVE). BEGIN and
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
419 END are buffer positions bounding the annotation, NAME is the name searched
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
420 for in TRANSLATIONS, and POSITIVE should be non-nil if this annotation marks
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
421 the beginning of a region with some property, or nil if it ends the region.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
422 NEXT-FN should return nil if there are no annotations after point.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
423
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
424 The basic format of the TRANSLATIONS argument is described in the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
425 documentation for the `format-annotate-region' function. There are some
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
426 additional things to keep in mind for decoding, though:
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
427
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
428 When an annotation is found, the TRANSLATIONS list is searched for a
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
429 text-property name and value that corresponds to that annotation. If the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
430 text-property has several annotations associated with it, it will be used only
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
431 if the other annotations are also in effect at that point. The first match
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
432 found whose annotations are all present is used.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
433
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
434 The text property thus determined is set to the value over the region between
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
435 the opening and closing annotations. However, if the text-property name has a
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
436 non-nil `format-list-valued' property, then the value will be consed onto the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
437 surrounding value of the property, rather than replacing that value.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
438
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
439 There are some special symbols that can be used in the \"property\" slot of
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
440 the TRANSLATIONS list: PARAMETER and FUNCTION \(spelled in uppercase).
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
441 Annotations listed under the pseudo-property PARAMETER are considered to be
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
442 arguments of the immediately surrounding annotation; the text between the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
443 opening and closing parameter annotations is deleted from the buffer but saved
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
444 as a string. The surrounding annotation should be listed under the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
445 pseudo-property FUNCTION. Instead of inserting a text-property for this
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
446 annotation, the function listed in the VALUE slot is called to make whatever
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
447 changes are appropriate. The function's first two arguments are the START and
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
448 END locations, and the rest of the arguments are any PARAMETERs found in that
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
449 region.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
450
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
451 Any annotations that are found by NEXT-FN but not defined by TRANSLATIONS
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
452 are saved as values of the `unknown' text-property \(which is list-valued).
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
453 The TRANSLATIONS list should usually contain an entry of the form
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
454 \(unknown \(nil format-annotate-value))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
455 to write these unknown annotations back into the file."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
456 (save-excursion
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
457 (save-restriction
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
458 (narrow-to-region (point-min) to)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
459 (goto-char from)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
460 (let (next open-ans todo loc unknown-ans)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
461 (while (setq next (funcall next-fn))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
462 (let* ((loc (nth 0 next))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
463 (end (nth 1 next))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
464 (name (nth 2 next))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
465 (positive (nth 3 next))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
466 (found nil))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
467
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
468 ;; Delete the annotation
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
469 (delete-region loc end)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
470 (if positive
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
471 ;; Positive annotations are stacked, remembering location
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
472 (setq open-ans (cons (list name loc) open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
473 ;; It is a negative annotation:
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
474 ;; Close the top annotation & add its text property.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
475 ;; If the file's nesting is messed up, the close might not match
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
476 ;; the top thing on the open-annotations stack.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
477 ;; If no matching annotation is open, just ignore the close.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
478 (if (not (assoc name open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
479 (message "Extra closing annotation (%s) in file" name)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
480 ;; If one is open, but not on the top of the stack, close
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
481 ;; the things in between as well. Set `found' when the real
13983
292411768ad9 (format-annotate-atomic-property-change): Doc fix.
Karl Heuer <kwzh@gnu.org>
parents: 13352
diff changeset
482 ;; one is closed.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
483 (while (not found)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
484 (let* ((top (car open-ans)) ; first on stack: should match.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
485 (top-name (car top))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
486 (start (car (cdr top))) ; location of start
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
487 (params (cdr (cdr top))) ; parameters
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
488 (aalist translations)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
489 (matched nil))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
490 (if (equal name top-name)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
491 (setq found t)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
492 (message "Improper nesting in file."))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
493 ;; Look through property names in TRANSLATIONS
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
494 (while aalist
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
495 (let ((prop (car (car aalist)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
496 (alist (cdr (car aalist))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
497 ;; And look through values for each property
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
498 (while alist
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
499 (let ((value (car (car alist)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
500 (ans (cdr (car alist))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
501 (if (member top-name ans)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
502 ;; This annotation is listed, but still have to
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
503 ;; check if multiple annotations are satisfied
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
504 (if (member 'nil (mapcar
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
505 (lambda (r)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
506 (assoc r open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
507 ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
508 nil ; multiple ans not satisfied
14452
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
509 ;; Yes, all set.
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
510 ;; If there are multiple annotations going
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
511 ;; into one text property, adjust the
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
512 ;; begin points of the other annotations
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
513 ;; so that we don't get double marking.
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
514 (let ((to-reset ans)
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
515 this-one)
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
516 (while to-reset
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
517 (setq this-one
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
518 (assoc (car to-reset)
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
519 (cdr open-ans)))
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
520 (if this-one
16954
380e33f3a5c6 Fix bug that caused crash on certain tags with parameters
Boris Goldowsky <boris@gnu.org>
parents: 16686
diff changeset
521 (setcar (cdr this-one) loc))
14452
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
522 (setq to-reset (cdr to-reset))))
7074747f9a8c (format-deannotate-region): Fixed bug that created
Richard M. Stallman <rms@gnu.org>
parents: 14169
diff changeset
523 ;; Set loop variables to nil so loop
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
524 ;; will exit.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
525 (setq alist nil aalist nil matched t
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
526 ;; pop annotation off stack.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
527 open-ans (cdr open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
528 (cond
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
529 ;; Check for pseudo-properties
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
530 ((eq prop 'PARAMETER)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
531 ;; This is a parameter of the top open ann:
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
532 ;; delete text and use as arg.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
533 (if open-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
534 ;; (If nothing open, discard).
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
535 (setq open-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
536 (cons (append (car open-ans)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
537 (list
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
538 (buffer-substring
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
539 start loc)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
540 (cdr open-ans))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
541 (delete-region start loc))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
542 ((eq prop 'FUNCTION)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
543 ;; Not a property, but a function to call.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
544 (let ((rtn (apply value start loc params)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
545 (if rtn (setq todo (cons rtn todo)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
546 (t
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
547 ;; Normal property/value pair
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
548 (setq todo
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
549 (cons (list start loc prop value)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
550 todo)))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
551 (setq alist (cdr alist))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
552 (setq aalist (cdr aalist)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
553 (if matched
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
554 nil
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
555 ;; Didn't find any match for the annotation:
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
556 ;; Store as value of text-property `unknown'.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
557 (setq open-ans (cdr open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
558 (setq todo (cons (list start loc 'unknown top-name)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
559 todo))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
560 (setq unknown-ans (cons name unknown-ans)))))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
561
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
562 ;; Once entire file has been scanned, add the properties.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
563 (while todo
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
564 (let* ((item (car todo))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
565 (from (nth 0 item))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
566 (to (nth 1 item))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
567 (prop (nth 2 item))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
568 (val (nth 3 item)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
569
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
570 (put-text-property
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
571 from to prop
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
572 (cond ((numberp val) ; add to ambient value if numeric
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
573 (+ val (or (get-text-property from prop) 0)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
574 ((get prop 'format-list-valued) ; value gets consed onto
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
575 ; list-valued properties
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
576 (let ((prev (get-text-property from prop)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
577 (cons val (if (listp prev) prev (list prev)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
578 (t val)))) ; normally, just set to val.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
579 (setq todo (cdr todo)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
580
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
581 (if unknown-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
582 (message "Unknown annotations: %s" unknown-ans))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
583
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
584 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
585 ;;; Encoding
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
586 ;;;
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
587
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
588 (defun format-insert-annotations (list &optional offset)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
589 "Apply list of annotations to buffer as `write-region' would.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
590 Inserts each element of the given LIST of buffer annotations at its
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
591 appropriate place. Use second arg OFFSET if the annotations' locations are
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
592 not relative to the beginning of the buffer: annotations will be inserted
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
593 at their location-OFFSET+1 \(ie, the offset is treated as the character number
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
594 of the first character in the buffer)."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
595 (if (not offset)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
596 (setq offset 0)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
597 (setq offset (1- offset)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
598 (let ((l (reverse list)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
599 (while l
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
600 (goto-char (- (car (car l)) offset))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
601 (insert (cdr (car l)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
602 (setq l (cdr l)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
603
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
604 (defun format-annotate-value (old new)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
605 "Return OLD and NEW as a \(close . open) annotation pair.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
606 Useful as a default function for TRANSLATIONS alist when the value of the text
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
607 property is the name of the annotation that you want to use, as it is for the
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
608 `unknown' text property."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
609 (cons (if old (list old))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
610 (if new (list new))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
611
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
612 (defun format-annotate-region (from to trans format-fn ignore)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
613 "Generate annotations for text properties in the region.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
614 Searches for changes between FROM and TO, and describes them with a list of
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
615 annotations as defined by alist TRANSLATIONS and FORMAT-FN. IGNORE lists text
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
616 properties not to consider; any text properties that are neither ignored nor
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
617 listed in TRANSLATIONS are warned about.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
618 If you actually want to modify the region, give the return value of this
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
619 function to `format-insert-annotations'.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
620
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
621 Format of the TRANSLATIONS argument:
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
622
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
623 Each element is a list whose car is a PROPERTY, and the following
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
624 elements are VALUES of that property followed by the names of zero or more
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
625 ANNOTATIONS. Whenever the property takes on that value, the annotations
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
626 \(as formatted by FORMAT-FN) are inserted into the file.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
627 When the property stops having that value, the matching negated annotation
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
628 will be inserted \(it may actually be closed earlier and reopened, if
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
629 necessary, to keep proper nesting).
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
630
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
631 If the property's value is a list, then each element of the list is dealt with
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
632 separately.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
633
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
634 If a VALUE is numeric, then it is assumed that there is a single annotation
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
635 and each occurrence of it increments the value of the property by that number.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
636 Thus, given the entry \(left-margin \(4 \"indent\")), if the left margin
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
637 changes from 4 to 12, two <indent> annotations will be generated.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
638
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
639 If the VALUE is nil, then instead of annotations, a function should be
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
640 specified. This function is used as a default: it is called for all
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
641 transitions not explicitly listed in the table. The function is called with
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
642 two arguments, the OLD and NEW values of the property. It should return
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
643 lists of annotations like `format-annotate-location' does.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
644
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
645 The same structure can be used in reverse for reading files."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
646 (let ((all-ans nil) ; All annotations - becomes return value
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
647 (open-ans nil) ; Annotations not yet closed
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
648 (loc nil) ; Current location
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
649 (not-found nil)) ; Properties that couldn't be saved
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
650 (while (or (null loc)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
651 (and (setq loc (next-property-change loc nil to))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
652 (< loc to)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
653 (or loc (setq loc from))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
654 (let* ((ans (format-annotate-location loc (= loc from) ignore trans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
655 (neg-ans (format-reorder (aref ans 0) open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
656 (pos-ans (aref ans 1))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
657 (ignored (aref ans 2)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
658 (setq not-found (append ignored not-found)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
659 ignore (append ignored ignore))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
660 ;; First do the negative (closing) annotations
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
661 (while neg-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
662 ;; Check if it's missing. This can happen (eg, a numeric property
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
663 ;; going negative can generate closing annotations before there are
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
664 ;; any open). Warn user & ignore.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
665 (if (not (member (car neg-ans) open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
666 (message "Can't close %s: not open." (car neg-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
667 (while (not (equal (car neg-ans) (car open-ans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
668 ;; To close anno. N, need to first close ans 1 to N-1,
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
669 ;; remembering to re-open them later.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
670 (setq pos-ans (cons (car open-ans) pos-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
671 (setq all-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
672 (cons (cons loc (funcall format-fn (car open-ans) nil))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
673 all-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
674 (setq open-ans (cdr open-ans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
675 ;; Now remove the one we're really interested in from open list.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
676 (setq open-ans (cdr open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
677 ;; And put the closing annotation here.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
678 (setq all-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
679 (cons (cons loc (funcall format-fn (car neg-ans) nil))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
680 all-ans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
681 (setq neg-ans (cdr neg-ans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
682 ;; Now deal with positive (opening) annotations
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
683 (let ((p pos-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
684 (while pos-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
685 (setq open-ans (cons (car pos-ans) open-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
686 (setq all-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
687 (cons (cons loc (funcall format-fn (car pos-ans) t))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
688 all-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
689 (setq pos-ans (cdr pos-ans))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
690
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
691 ;; Close any annotations still open
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
692 (while open-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
693 (setq all-ans
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
694 (cons (cons to (funcall format-fn (car open-ans) nil))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
695 all-ans))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
696 (setq open-ans (cdr open-ans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
697 (if not-found
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
698 (message "These text properties could not be saved:\n %s"
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
699 not-found))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
700 (nreverse all-ans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
701
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
702 ;;; Internal functions for format-annotate-region.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
703
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
704 (defun format-annotate-location (loc all ignore trans)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
705 "Return annotation(s) needed at LOCATION.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
706 This includes any properties that change between LOC-1 and LOC.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
707 If ALL is true, don't look at previous location, but generate annotations for
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
708 all non-nil properties.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
709 Third argument IGNORE is a list of text-properties not to consider.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
710
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
711 Return value is a vector of 3 elements:
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
712 1. List of names of the annotations to close
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
713 2. List of the names of annotations to open.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
714 3. List of properties that were ignored or couldn't be annotated."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
715 (let* ((prev-loc (1- loc))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
716 (before-plist (if all nil (text-properties-at prev-loc)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
717 (after-plist (text-properties-at loc))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
718 p negatives positives prop props not-found)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
719 ;; make list of all property names involved
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
720 (setq p before-plist)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
721 (while p
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
722 (if (not (memq (car p) props))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
723 (setq props (cons (car p) props)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
724 (setq p (cdr (cdr p))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
725 (setq p after-plist)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
726 (while p
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
727 (if (not (memq (car p) props))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
728 (setq props (cons (car p) props)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
729 (setq p (cdr (cdr p))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
730
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
731 (while props
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
732 (setq prop (car props)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
733 props (cdr props))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
734 (if (memq prop ignore)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
735 nil ; If it's been ignored before, ignore it now.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
736 (let ((before (if all nil (car (cdr (memq prop before-plist)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
737 (after (car (cdr (memq prop after-plist)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
738 (if (equal before after)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
739 nil ; no change; ignore
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
740 (let ((result (format-annotate-single-property-change
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
741 prop before after trans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
742 (if (not result)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
743 (setq not-found (cons prop not-found))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
744 (setq negatives (nconc negatives (car result))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
745 positives (nconc positives (cdr result)))))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
746 (vector negatives positives not-found)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
747
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
748 (defun format-annotate-single-property-change (prop old new trans)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
749 "Return annotations for PROPERTY changing from OLD to NEW.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
750 These are searched for in the TRANSLATIONS alist.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
751 If NEW does not appear in the list, but there is a default function, then that
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
752 function is called.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
753 Annotations to open and to close are returned as a dotted pair."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
754 (let ((prop-alist (cdr (assoc prop trans)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
755 default)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
756 (if (not prop-alist)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
757 nil
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
758 ;; If property is numeric, nil means 0
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
759 (cond ((and (numberp old) (null new))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
760 (setq new 0))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
761 ((and (numberp new) (null old))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
762 (setq old 0)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
763 ;; If either old or new is a list, have to treat both that way.
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
764 (if (or (consp old) (consp new))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
765 (let* ((old (if (listp old) old (list old)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
766 (new (if (listp new) new (list new)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
767 (tail (format-common-tail old new))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
768 close open)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
769 (while old
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
770 (setq close
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
771 (append (car (format-annotate-atomic-property-change
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
772 prop-alist (car old) nil))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
773 close)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
774 old (cdr old)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
775 (while new
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
776 (setq open
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
777 (append (cdr (format-annotate-atomic-property-change
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
778 prop-alist nil (car new)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
779 open)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
780 new (cdr new)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
781 (format-make-relatively-unique close open))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
782 (format-annotate-atomic-property-change prop-alist old new)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
783
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
784 (defun format-annotate-atomic-property-change (prop-alist old new)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
785 "Internal function annotate a single property change.
13983
292411768ad9 (format-annotate-atomic-property-change): Doc fix.
Karl Heuer <kwzh@gnu.org>
parents: 13352
diff changeset
786 PROP-ALIST is the relevant segment of a TRANSLATIONS list.
11054
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
787 OLD and NEW are the values."
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
788 (cond
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
789 ;; Numerical annotation - use difference
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
790 ((and (numberp old) (numberp new))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
791 (let* ((entry (progn
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
792 (while (and (car (car prop-alist))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
793 (not (numberp (car (car prop-alist)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
794 (setq prop-alist (cdr prop-alist)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
795 (car prop-alist)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
796 (increment (car (car prop-alist)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
797 (n (ceiling (/ (float (- new old)) (float increment))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
798 (anno (car (cdr (car prop-alist)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
799 (if (> n 0)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
800 (cons nil (make-list n anno))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
801 (cons (make-list (- n) anno) nil))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
802
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
803 ;; Standard annotation
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
804 (t (let ((close (and old (cdr (assoc old prop-alist))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
805 (open (and new (cdr (assoc new prop-alist)))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
806 (if (or close open)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
807 (format-make-relatively-unique close open)
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
808 ;; Call "Default" function, if any
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
809 (let ((default (assq nil prop-alist)))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
810 (if default
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
811 (funcall (car (cdr default)) old new))))))))
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
812
cf9842a72fe5 Initial revision
Boris Goldowsky <boris@gnu.org>
parents:
diff changeset
813 ;; format.el ends here