(occur-read-primary-args): Pass default to read-from-minibuffer.
[bpt/emacs.git] / lisp / textmodes / texinfmt.el
CommitLineData
e8af40ee 1;;; texinfmt.el --- format Texinfo files into Info files
be010748 2
db95369b 3;; Copyright (C) 1985, 1986, 1988, 1990, 1991, 1992, 1993,
64a1ba18 4;; 1994, 1995, 1996, 1997, 1998, 2000, 2001
8bb6eb14 5;; Free Software Foundation, Inc.
4dd29d03 6
64a1ba18 7;; Maintainer: Robert J. Chassell <bug-texinfo@gnu.org>
92f62199 8;; Keywords: maint, tex, docs
58142744 9
be010748 10;; This file is part of GNU Emacs.
4dd29d03
BP
11
12;; GNU Emacs is free software; you can redistribute it and/or modify
13;; it under the terms of the GNU General Public License as published by
e5167999 14;; the Free Software Foundation; either version 2, or (at your option)
4dd29d03
BP
15;; any later version.
16
17;; GNU Emacs is distributed in the hope that it will be useful,
18;; but WITHOUT ANY WARRANTY; without even the implied warranty of
19;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20;; GNU General Public License for more details.
21
22;; You should have received a copy of the GNU General Public License
b578f267
EN
23;; along with GNU Emacs; see the file COPYING. If not, write to the
24;; Free Software Foundation, Inc., 59 Temple Place - Suite 330,
25;; Boston, MA 02111-1307, USA.
4dd29d03 26
e8af40ee
PJ
27;;; Commentary:
28
7f3e80e3 29;;; Code:
e5167999 30
7f3e80e3 31;;; Emacs lisp functions to convert Texinfo files to Info files.
4dd29d03 32
80216a47
RS
33(or (fboundp 'defgroup)
34 (defmacro defgroup (&rest ignore) nil))
35
36(or (fboundp 'defcustom)
37 (defmacro defcustom (var value doc &rest ignore)
38 `(defvar ,var ,value ,doc)))
39
a66ccdcf 40(defvar texinfmt-version "2.40 of 6 Dec 2002")
92f62199
RS
41
42(defun texinfmt-version (&optional here)
43 "Show the version of texinfmt.el in the minibuffer.
44If optional argument HERE is non-nil, insert info at point."
45 (interactive "P")
db95369b 46 (let ((version-string
92f62199 47 (format "Version of \`texinfmt.el\': %s" texinfmt-version)))
db95369b 48 (if here
92f62199
RS
49 (insert version-string)
50 (if (interactive-p)
51 (message "%s" version-string)
52 version-string))))
53
7f3e80e3
RS
54\f
55;;; Variable definitions
56
57(require 'texinfo) ; So `texinfo-footnote-style' is defined.
58(require 'texnfo-upd) ; So `texinfo-section-types-regexp' is defined.
e5167999 59
4dd29d03
BP
60(defvar texinfo-format-syntax-table nil)
61
62(defvar texinfo-vindex)
63(defvar texinfo-findex)
64(defvar texinfo-cindex)
65(defvar texinfo-pindex)
66(defvar texinfo-tindex)
67(defvar texinfo-kindex)
68(defvar texinfo-last-node)
69(defvar texinfo-node-names)
7f3e80e3 70(defvar texinfo-enclosure-list)
dc7deb17 71(defvar texinfo-alias-list)
8d66d13d 72(defvar texinfo-fold-nodename-case nil)
7f3e80e3 73
64c8498a
RS
74(defvar texinfo-command-start)
75(defvar texinfo-command-end)
76(defvar texinfo-command-name)
77(defvar texinfo-defun-type)
78(defvar texinfo-last-node-pos)
79(defvar texinfo-stack)
80(defvar texinfo-short-index-cmds-alist)
81(defvar texinfo-short-index-format-cmds-alist)
82(defvar texinfo-format-filename)
83(defvar texinfo-footnote-number)
84(defvar texinfo-start-of-header)
85(defvar texinfo-end-of-header)
86(defvar texinfo-raisesections-alist)
87(defvar texinfo-lowersections-alist)
7f3e80e3
RS
88\f
89;;; Syntax table
4dd29d03
BP
90
91(if texinfo-format-syntax-table
92 nil
93 (setq texinfo-format-syntax-table (make-syntax-table))
72190a54
MB
94 (modify-syntax-entry ?\" " " texinfo-format-syntax-table)
95 (modify-syntax-entry ?\\ " " texinfo-format-syntax-table)
4dd29d03
BP
96 (modify-syntax-entry ?@ "\\" texinfo-format-syntax-table)
97 (modify-syntax-entry ?\^q "\\" texinfo-format-syntax-table)
98 (modify-syntax-entry ?\[ "." texinfo-format-syntax-table)
99 (modify-syntax-entry ?\] "." texinfo-format-syntax-table)
100 (modify-syntax-entry ?\( "." texinfo-format-syntax-table)
101 (modify-syntax-entry ?\) "." texinfo-format-syntax-table)
102 (modify-syntax-entry ?{ "(}" texinfo-format-syntax-table)
103 (modify-syntax-entry ?} "){" texinfo-format-syntax-table)
104 (modify-syntax-entry ?\' "." texinfo-format-syntax-table))
105
7f3e80e3
RS
106\f
107;;; Top level buffer and region formatting functions
108
90a44351 109;;;###autoload
1c87ab31 110(defun texinfo-format-buffer (&optional nosplit)
4dd29d03
BP
111 "Process the current buffer as texinfo code, into an Info file.
112The Info file output is generated in a buffer visiting the Info file
92f62199 113name specified in the @setfilename command.
4dd29d03
BP
114
115Non-nil argument (prefix, if interactive) means don't make tag table
116and don't split the file if large. You can use Info-tagify and
117Info-split to do these manually."
118 (interactive "P")
2990dcd4
KH
119 (let ((lastmessage "Formatting Info file...")
120 (coding-system-for-write buffer-file-coding-system))
4dd29d03 121 (message lastmessage)
1c87ab31 122 (widen)
4dd29d03 123 (texinfo-format-buffer-1)
1c87ab31
RS
124 (Info-tagify)
125 (if nosplit
4dd29d03 126 nil
4dd29d03
BP
127 (if (> (buffer-size) 100000)
128 (progn
129 (message (setq lastmessage "Splitting Info file..."))
130 (Info-split))))
131 (message (concat lastmessage
132 (if (interactive-p) "done. Now save it." "done.")))))
133
7f3e80e3
RS
134(defvar texinfo-region-buffer-name "*Info Region*"
135 "*Name of the temporary buffer used by \\[texinfo-format-region].")
136
01cf96d5
EZ
137(defvar texinfo-pre-format-hook nil
138 "Hook called before the conversion of the Texinfo file to Info format.
139The functions on this hook are called with argument BUFFER, the buffer
140containing the Texinfo file.")
141
d02677ab
RS
142;; These come from tex-mode.el.
143(defvar tex-start-of-header)
144(defvar tex-end-of-header)
145
90a44351 146;;;###autoload
7f3e80e3
RS
147(defun texinfo-format-region (region-beginning region-end)
148 "Convert the current region of the Texinfo file to Info format.
149This lets you see what that part of the file will look like in Info.
150The command is bound to \\[texinfo-format-region]. The text that is
151converted to Info is stored in a temporary buffer."
152 (interactive "r")
153 (message "Converting region to Info format...")
154 (let (texinfo-command-start
155 texinfo-command-end
156 texinfo-command-name
157 texinfo-vindex
158 texinfo-findex
159 texinfo-cindex
160 texinfo-pindex
161 texinfo-tindex
162 texinfo-kindex
163 texinfo-stack
164 (texinfo-format-filename "")
165 texinfo-example-start
166 texinfo-last-node-pos
167 texinfo-last-node
168 texinfo-node-names
169 (texinfo-footnote-number 0)
170 last-input-buffer
171 (fill-column-for-info fill-column)
172 (input-buffer (current-buffer))
173 (input-directory default-directory)
174 (header-text "")
175 (header-beginning 1)
176 (header-end 1))
db95369b
JB
177
178;;; Copy lines between beginning and end of header lines,
7f3e80e3
RS
179;;; if any, or else copy the `@setfilename' line, if any.
180 (save-excursion
181 (save-restriction
182 (widen)
183 (goto-char (point-min))
184 (let ((search-end (save-excursion (forward-line 100) (point))))
185 (if (or
186 ;; Either copy header text.
db95369b
JB
187 (and
188 (prog1
9dc96d32 189 (search-forward tex-start-of-header search-end t)
7f3e80e3
RS
190 (forward-line 1)
191 ;; Mark beginning of header.
192 (setq header-beginning (point)))
db95369b 193 (prog1
9dc96d32 194 (search-forward tex-end-of-header nil t)
7f3e80e3
RS
195 (beginning-of-line)
196 ;; Mark end of header
197 (setq header-end (point))))
198 ;; Or copy @filename line.
199 (prog2
200 (goto-char (point-min))
201 (search-forward "@setfilename" search-end t)
202 (beginning-of-line)
203 (setq header-beginning (point))
204 (forward-line 1)
205 (setq header-end (point))))
db95369b
JB
206
207 ;; Copy header
7f3e80e3 208 (setq header-text
289df0fc 209 (buffer-substring-no-properties
7f3e80e3
RS
210 (min header-beginning region-beginning)
211 header-end))))))
212
213;;; Find a buffer to use.
214 (switch-to-buffer (get-buffer-create texinfo-region-buffer-name))
215 (erase-buffer)
216 ;; Insert the header into the buffer.
217 (insert header-text)
218 ;; Insert the region into the buffer.
219 (insert-buffer-substring
220 input-buffer
221 (max region-beginning header-end)
222 region-end)
01cf96d5 223 (run-hook-with-args 'texinfo-pre-format-hook input-buffer)
7f3e80e3
RS
224 ;; Make sure region ends in a newline.
225 (or (= (preceding-char) ?\n)
226 (insert "\n"))
db95369b 227
7f3e80e3
RS
228 (goto-char (point-min))
229 (texinfo-mode)
230 (message "Converting region to Info format...")
231 (setq fill-column fill-column-for-info)
232 ;; Install a syntax table useful for scanning command operands.
233 (set-syntax-table texinfo-format-syntax-table)
234
235 ;; Insert @include files so `texinfo-raise-lower-sections' can
236 ;; work on them without losing track of multiple
db95369b 237 ;; @raise/@lowersections commands.
7f3e80e3
RS
238 (while (re-search-forward "^@include" nil t)
239 (setq texinfo-command-end (point))
240 (let ((filename (concat input-directory
241 (texinfo-parse-line-arg))))
214b69d9 242 (re-search-backward "^@include")
7f3e80e3
RS
243 (delete-region (point) (save-excursion (forward-line 1) (point)))
244 (message "Reading included file: %s" filename)
245 (save-excursion
246 (save-restriction
247 (narrow-to-region
248 (point)
249 (+ (point) (car (cdr (insert-file-contents filename)))))
250 (goto-char (point-min))
251 ;; Remove `@setfilename' line from included file, if any,
252 ;; so @setfilename command not duplicated.
6147e725
SM
253 (if (re-search-forward "^@setfilename" (line-end-position 100) t)
254 (delete-region (line-beginning-position 1)
255 (line-beginning-position 2)))))))
7f3e80e3
RS
256
257 ;; Raise or lower level of each section, if necessary.
258 (goto-char (point-min))
259 (texinfo-raise-lower-sections)
260 ;; Append @refill to appropriate paragraphs for filling.
261 (goto-char (point-min))
262 (texinfo-append-refill)
263 ;; If the region includes the effective end of the data,
264 ;; discard everything after that.
265 (goto-char (point-max))
266 (if (re-search-backward "^@bye" nil t)
267 (delete-region (point) (point-max)))
268 ;; Make sure buffer ends in a newline.
269 (or (= (preceding-char) ?\n)
270 (insert "\n"))
271 ;; Don't use a previous value of texinfo-enclosure-list.
272 (setq texinfo-enclosure-list nil)
dc7deb17 273 (setq texinfo-alias-list nil)
7f3e80e3
RS
274
275 (goto-char (point-min))
276 (if (looking-at "\\\\input[ \t]+texinfo")
6147e725 277 (delete-region (point) (line-beginning-position 2)))
7f3e80e3
RS
278
279 ;; Insert Info region title text.
280 (goto-char (point-min))
db95369b 281 (if (search-forward
7f3e80e3
RS
282 "@setfilename" (save-excursion (forward-line 100) (point)) t)
283 (progn
284 (setq texinfo-command-end (point))
285 (beginning-of-line)
286 (setq texinfo-command-start (point))
287 (let ((arg (texinfo-parse-arg-discard)))
288 (insert " "
289 texinfo-region-buffer-name
db95369b 290 " buffer for: `")
7f3e80e3
RS
291 (insert (file-name-nondirectory (expand-file-name arg)))
292 (insert "', -*-Text-*-\n")))
293 ;; Else no `@setfilename' line
294 (insert " "
295 texinfo-region-buffer-name
296 " buffer -*-Text-*-\n"))
297 (insert "produced by `texinfo-format-region'\n"
298 "from a region in: "
299 (if (buffer-file-name input-buffer)
300 (concat "`"
301 (file-name-sans-versions
302 (file-name-nondirectory
303 (buffer-file-name input-buffer)))
304 "'")
305 (concat "buffer `" (buffer-name input-buffer) "'"))
306 "\nusing `texinfmt.el' version "
307 texinfmt-version
308 ".\n\n")
309
310 ;; Now convert for real.
311 (goto-char (point-min))
312 (texinfo-format-scan)
313 (goto-char (point-min))
1c87ab31
RS
314 (Info-tagify input-buffer)
315 (goto-char (point-min))
7f3e80e3
RS
316 (message "Done.")))
317
92f62199 318;;;###autoload
1c87ab31 319(defun texi2info (&optional nosplit)
92f62199
RS
320 "Convert the current buffer (written in Texinfo code) into an Info file.
321The Info file output is generated in a buffer visiting the Info file
322names specified in the @setfilename command.
323
324This function automatically updates all node pointers and menus, and
325creates a master menu. This work is done on a temporary buffer that
326is automatically removed when the Info file is created. The original
327Texinfo source buffer is not changed.
328
1c87ab31
RS
329Non-nil argument (prefix, if interactive) means don't split the file
330if large. You can use Info-split to do this manually."
92f62199
RS
331 (interactive "P")
332 (let ((temp-buffer (concat "*--" (buffer-name) "--temporary-buffer*" )))
333 (message "First updating nodes and menus, then creating Info file.")
334 ;; (sit-for 2)
335 (copy-to-buffer temp-buffer (point-min) (point-max))
336 (switch-to-buffer temp-buffer)
337 (texinfo-master-menu t)
338 (message "Now creating Info file.")
339 (sit-for 2)
1c87ab31 340 (texinfo-format-buffer nosplit)
92f62199
RS
341 (save-buffer)
342 (kill-buffer temp-buffer)))
343
4dd29d03 344\f
7f3e80e3
RS
345;;; Primary internal formatting function for the whole buffer.
346
4dd29d03
BP
347(defun texinfo-format-buffer-1 ()
348 (let (texinfo-format-filename
349 texinfo-example-start
350 texinfo-command-start
351 texinfo-command-end
352 texinfo-command-name
353 texinfo-last-node
7f3e80e3 354 texinfo-last-node-pos
4dd29d03
BP
355 texinfo-vindex
356 texinfo-findex
357 texinfo-cindex
358 texinfo-pindex
359 texinfo-tindex
360 texinfo-kindex
361 texinfo-stack
362 texinfo-node-names
7f3e80e3 363 (texinfo-footnote-number 0)
4dd29d03
BP
364 last-input-buffer
365 outfile
7f3e80e3 366 (fill-column-for-info fill-column)
4dd29d03
BP
367 (input-buffer (current-buffer))
368 (input-directory default-directory))
7f3e80e3 369 (setq texinfo-enclosure-list nil)
dc7deb17 370 (setq texinfo-alias-list nil)
4dd29d03
BP
371 (save-excursion
372 (goto-char (point-min))
7f3e80e3 373 (or (search-forward "@setfilename" nil t)
e8af40ee 374 (error "Texinfo file needs an `@setfilename FILENAME' line"))
4dd29d03
BP
375 (setq texinfo-command-end (point))
376 (setq outfile (texinfo-parse-line-arg)))
d0970585 377
4dd29d03
BP
378 (find-file outfile)
379 (texinfo-mode)
d0970585
RS
380 (erase-buffer)
381
382 (message "Formatting Info file: %s" outfile)
383 (setq texinfo-format-filename
384 (file-name-nondirectory (expand-file-name outfile)))
385
7f3e80e3 386 (setq fill-column fill-column-for-info)
4dd29d03 387 (set-syntax-table texinfo-format-syntax-table)
d0970585 388
4dd29d03 389 (insert-buffer-substring input-buffer)
01cf96d5 390 (run-hook-with-args 'texinfo-pre-format-hook input-buffer)
7f3e80e3 391 (message "Converting %s to Info format..." (buffer-name input-buffer))
db95369b 392
7f3e80e3
RS
393 ;; Insert @include files so `texinfo-raise-lower-sections' can
394 ;; work on them without losing track of multiple
db95369b 395 ;; @raise/@lowersections commands.
7f3e80e3
RS
396 (goto-char (point-min))
397 (while (re-search-forward "^@include" nil t)
398 (setq texinfo-command-end (point))
399 (let ((filename (concat input-directory
400 (texinfo-parse-line-arg))))
214b69d9 401 (re-search-backward "^@include")
6147e725 402 (delete-region (point) (line-beginning-position 2))
7f3e80e3
RS
403 (message "Reading included file: %s" filename)
404 (save-excursion
405 (save-restriction
406 (narrow-to-region
407 (point)
408 (+ (point) (car (cdr (insert-file-contents filename)))))
409 (goto-char (point-min))
410 ;; Remove `@setfilename' line from included file, if any,
411 ;; so @setfilename command not duplicated.
6147e725
SM
412 (if (re-search-forward "^@setfilename" (line-end-position 100) t)
413 (delete-region (line-beginning-position 1)
414 (line-beginning-position 2)))))))
7f3e80e3
RS
415 ;; Raise or lower level of each section, if necessary.
416 (goto-char (point-min))
417 (texinfo-raise-lower-sections)
418 ;; Append @refill to appropriate paragraphs
419 (goto-char (point-min))
420 (texinfo-append-refill)
4dd29d03
BP
421 (goto-char (point-min))
422 (search-forward "@setfilename")
423 (beginning-of-line)
424 (delete-region (point-min) (point))
425 ;; Remove @bye at end of file, if it is there.
426 (goto-char (point-max))
427 (if (search-backward "@bye" nil t)
428 (delete-region (point) (point-max)))
429 ;; Make sure buffer ends in a newline.
430 (or (= (preceding-char) ?\n)
431 (insert "\n"))
432 ;; Scan the whole buffer, converting to Info format.
433 (texinfo-format-scan)
4dd29d03 434 (goto-char (point-min))
d0970585
RS
435 ;; Insert info about how this file was made.
436 (insert "Info file: "
437 texinfo-format-filename ", -*-Text-*-\n"
438 "produced by `texinfo-format-buffer'\n"
439 ;; Date string removed so that regression testing is easier.
440 ;; "on "
441 ;; (insert (format-time-string "%e %b %Y")) " "
442 "from file"
443 (if (buffer-file-name input-buffer)
444 (concat " `"
445 (file-name-sans-versions
446 (file-name-nondirectory
447 (buffer-file-name input-buffer)))
448 "'")
449 (concat "buffer `" (buffer-name input-buffer) "'"))
450 "\nusing `texinfmt.el' version "
451 texinfmt-version
452 ".\n\n")
453 ;; Return data for indices.
4dd29d03
BP
454 (list outfile
455 texinfo-vindex texinfo-findex texinfo-cindex
456 texinfo-pindex texinfo-tindex texinfo-kindex)))
457
7f3e80e3
RS
458\f
459;;; Perform non-@-command file conversions: quotes and hyphens
460
461(defun texinfo-format-convert (min max)
462 ;; Convert left and right quotes to typewriter font quotes.
463 (goto-char min)
464 (while (search-forward "``" max t)
465 (replace-match "\""))
466 (goto-char min)
467 (while (search-forward "''" max t)
468 (replace-match "\""))
469 ;; Convert three hyphens in a row to two.
470 (goto-char min)
471 (while (re-search-forward "\\( \\|\\w\\)\\(---\\)\\( \\|\\w\\)" max t)
6147e725 472 (delete-region (1+ (match-beginning 2)) (+ 2 (match-beginning 2)))))
4dd29d03 473
7f3e80e3
RS
474\f
475;;; Handle paragraph filling
476
92f62199
RS
477;; Keep as concatinated lists for ease of maintenance
478
7f3e80e3 479(defvar texinfo-no-refill-regexp
92f62199
RS
480 (concat
481 "^@"
482 "\\("
2a64dfce 483 ;; add "itemize\\|" (from experiment of 2001 Nov 28)
db95369b 484 ;; because of a problem with @end itemize@refill
2a64dfce
RC
485 ;; I don't know if this causes other problems.
486 ;; I suspect itemized lists don't get filled properly and a
487 ;; more precise fix is required. Bob
488 "itemize\\|"
149f002e 489 "direntry\\|"
92f62199
RS
490 "lisp\\|"
491 "smalllisp\\|"
1c87ab31
RS
492 "example\\|"
493 "smallexample\\|"
92f62199 494 "display\\|"
1c87ab31 495 "smalldisplay\\|"
92f62199 496 "format\\|"
1c87ab31 497 "smallformat\\|"
92f62199
RS
498 "flushleft\\|"
499 "flushright\\|"
500 "menu\\|"
501 "multitable\\|"
502 "titlepage\\|"
503 "iftex\\|"
504 "ifhtml\\|"
505 "tex\\|"
506 "html"
507 "\\)")
7f3e80e3
RS
508 "Regexp specifying environments in which paragraphs are not filled.")
509
92f62199
RS
510(defvar texinfo-accent-commands
511 (concat
512 "@^\\|"
513 "@`\\|"
514 "@'\\|"
515 "@\"\\|"
516 "@,\\|"
517 "@=\\|"
518 "@~\\|"
519 "@OE{\\|"
520 "@oe{\\|"
521 "@AA{\\|"
522 "@aa{\\|"
523 "@AE{\\|"
524 "@ae{\\|"
525 "@ss{\\|"
526 "@questiondown{\\|"
527 "@exclamdown{\\|"
528 "@L{\\|"
529 "@l{\\|"
530 "@O{\\|"
531 "@o{\\|"
532 "@dotaccent{\\|"
533 "@ubaraccent{\\|"
534 "@d{\\|"
535 "@H{\\|"
536 "@ringaccent{\\|"
537 "@tieaccent{\\|"
538 "@u{\\|"
539 "@v{\\|"
540 "@dotless{"
541 ))
542
7f3e80e3 543(defvar texinfo-part-of-para-regexp
92f62199
RS
544 (concat
545 "^@"
546 "\\("
547 "b{\\|"
548 "bullet{\\|"
549 "cite{\\|"
550 "code{\\|"
551 "email{\\|"
552 "emph{\\|"
553 "equiv{\\|"
554 "error{\\|"
555 "expansion{\\|"
556 "file{\\|"
557 "i{\\|"
558 "inforef{\\|"
559 "kbd{\\|"
560 "key{\\|"
561 "lisp{\\|"
562 "minus{\\|"
563 "point{\\|"
564 "print{\\|"
565 "pxref{\\|"
566 "r{\\|"
567 "ref{\\|"
568 "result{\\|"
569 "samp{\\|"
570 "sc{\\|"
571 "t{\\|"
572 "TeX{\\|"
573 "today{\\|"
574 "url{\\|"
575 "var{\\|"
576 "w{\\|"
577 "xref{\\|"
578 "@-\\|" ; @- is a descretionary hyphen (not an accent) (a noop).
579 texinfo-accent-commands
580 "\\)"
581 )
7f3e80e3
RS
582 "Regexp specifying @-commands found within paragraphs.")
583
584(defun texinfo-append-refill ()
585 "Append @refill at end of each paragraph that should be filled.
db95369b 586Do not append @refill to paragraphs within @example and similar environments.
7f3e80e3
RS
587Do not append @refill to paragraphs containing @w{TEXT} or @*."
588
589 ;; It is necessary to append @refill before other processing because
590 ;; the other processing removes information that tells Texinfo
591 ;; whether the text should or should not be filled.
db95369b 592
7f3e80e3
RS
593 (while (< (point) (point-max))
594 (let ((refill-blank-lines "^[ \t\n]*$")
595 (case-fold-search nil)) ; Don't confuse @TeX and @tex....
596 (beginning-of-line)
597 ;; 1. Skip over blank lines;
db95369b 598 ;; skip over lines beginning with @-commands,
7f3e80e3
RS
599 ;; but do not skip over lines
600 ;; that are no-refill environments such as @example or
601 ;; that begin with within-paragraph @-commands such as @code.
602 (while (and (looking-at (concat "^@\\|^\\\\\\|" refill-blank-lines))
db95369b 603 (not (looking-at
7f3e80e3 604 (concat
db95369b 605 "\\("
7f3e80e3 606 texinfo-no-refill-regexp
db95369b 607 "\\|"
7f3e80e3
RS
608 texinfo-part-of-para-regexp
609 "\\)")))
610 (< (point) (point-max)))
611 (forward-line 1))
612 ;; 2. Skip over @example and similar no-refill environments.
613 (if (looking-at texinfo-no-refill-regexp)
6147e725 614 (let ((environment (match-string-no-properties 1)))
7f3e80e3
RS
615 (progn (re-search-forward (concat "^@end " environment) nil t)
616 (forward-line 1)))
92f62199
RS
617 ;; Else
618 ;; 3. Do not refill a paragraph containing @w or @*, or ending
619 ;; with @<newline> followed by a newline.
6147e725
SM
620 (if (or (>= (point) (point-max))
621 (re-search-forward
622 "@w{\\|@\\*\\|@\n\n"
623 (save-excursion (forward-paragraph) (forward-line 1) (point))
624 t))
7f3e80e3 625 ;; Go to end of paragraph and do nothing.
db95369b 626 (forward-paragraph)
7f3e80e3
RS
627 ;; 4. Else go to end of paragraph and insert @refill
628 (forward-paragraph)
629 (forward-line -1)
f66f0ee8
KH
630 (let ((line-beg (point)))
631 (end-of-line)
632 (delete-region
633 (point)
634 (save-excursion (skip-chars-backward " \t") (point)))
ec81e97a
KH
635 (forward-char 1)
636 (unless (re-search-backward "@c[ \t\n]\\|@comment[ \t\n]" line-beg t)
637 (forward-char -1))
f66f0ee8
KH
638 (unless (re-search-backward "@refill\\|@bye" line-beg t)
639 (insert "@refill")))
7f3e80e3 640 (forward-line 1))))))
4dd29d03 641
7f3e80e3
RS
642\f
643;;; Handle `@raisesections' and `@lowersections' commands
644
645;; These commands change the hierarchical level of chapter structuring
db95369b
JB
646;; commands.
647;;
7f3e80e3
RS
648;; @raisesections changes @subsection to @section,
649;; @section to @chapter,
650;; etc.
651;;
652;; @lowersections changes @chapter to @section
653;; @subsection to @subsubsection,
654;; etc.
655;;
656;; An @raisesections/@lowersections command changes only those
657;; structuring commands that follow the @raisesections/@lowersections
658;; command.
659;;
660;; Repeated @raisesections/@lowersections continue to raise or lower
661;; the heading level.
db95369b 662;;
7f3e80e3
RS
663;; An @lowersections command cancels an @raisesections command, and
664;; vice versa.
665;;
666;; You cannot raise or lower "beyond" chapters or subsubsections, but
667;; trying to do so does not elicit an error---you just get more
668;; headings that mean the same thing as you keep raising or lowering
669;; (for example, after a single @raisesections, both @chapter and
670;; @section produce chapter headings).
671
672(defun texinfo-raise-lower-sections ()
db95369b 673 "Raise or lower the hierarchical level of chapters, sections, etc.
7f3e80e3
RS
674
675This function acts according to `@raisesections' and `@lowersections'
676commands in the Texinfo file.
677
678For example, an `@lowersections' command is useful if you wish to
679include what is written as an outer or standalone Texinfo file in
680another Texinfo file as an inner, included file. The `@lowersections'
681command changes chapters to sections, sections to subsections and so
682on.
683
684@raisesections changes @subsection to @section,
685 @section to @chapter,
686 @heading to @chapheading,
687 etc.
688
689@lowersections changes @chapter to @section,
690 @subsection to @subsubsection,
691 @heading to @subheading,
692 etc.
693
694An `@raisesections' or `@lowersections' command changes only those
695structuring commands that follow the `@raisesections' or
696`@lowersections' command.
697
698An `@lowersections' command cancels an `@raisesections' command, and
699vice versa.
700
701Repeated use of the commands continue to raise or lower the hierarchical
702level a step at a time.
703
704An attempt to raise above `chapters' reproduces chapter commands; an
705attempt to lower below subsubsections reproduces subsubsection
706commands."
db95369b 707
7f3e80e3
RS
708 ;; `texinfo-section-types-regexp' is defined in `texnfo-upd.el';
709 ;; it is a regexp matching chapter, section, other headings
710 ;; (but not the top node).
711
712 (let (type (level 0))
db95369b 713 (while
7f3e80e3
RS
714 (re-search-forward
715 (concat
716 "\\(\\(^@\\(raise\\|lower\\)sections\\)\\|\\("
717 texinfo-section-types-regexp
718 "\\)\\)")
719 nil t)
720 (beginning-of-line)
721 (save-excursion (setq type (read (current-buffer))))
db95369b
JB
722 (cond
723
7f3e80e3
RS
724 ;; 1. Increment level
725 ((eq type '@raisesections)
726 (setq level (1+ level))
727 (delete-region
728 (point) (save-excursion (forward-line 1) (point))))
db95369b 729
7f3e80e3
RS
730 ;; 2. Decrement level
731 ((eq type '@lowersections)
732 (setq level (1- level))
733 (delete-region
734 (point) (save-excursion (forward-line 1) (point))))
db95369b 735
7f3e80e3
RS
736 ;; Now handle structuring commands
737 ((cond
db95369b 738
7f3e80e3
RS
739 ;; 3. Raise level when positive
740 ((> level 0)
741 (let ((count level)
742 (new-level type))
743 (while (> count 0)
744 (setq new-level
745 (cdr (assq new-level texinfo-raisesections-alist)))
746 (setq count (1- count)))
747 (kill-word 1)
748 (insert (symbol-name new-level))))
db95369b 749
7f3e80e3
RS
750 ;; 4. Do nothing except move point when level is zero
751 ((= level 0) (forward-line 1))
db95369b 752
7f3e80e3
RS
753 ;; 5. Lower level when positive
754 ((< level 0)
755 (let ((count level)
756 (new-level type))
757 (while (< count 0)
758 (setq new-level
759 (cdr (assq new-level texinfo-lowersections-alist)))
760 (setq count (1+ count)))
761 (kill-word 1)
762 (insert (symbol-name new-level))))))))))
763
764(defvar texinfo-raisesections-alist
765 '((@chapter . @chapter) ; Cannot go higher
766 (@unnumbered . @unnumbered)
92f62199 767 (@centerchap . @unnumbered)
7f3e80e3
RS
768
769 (@majorheading . @majorheading)
770 (@chapheading . @chapheading)
771 (@appendix . @appendix)
db95369b 772
7f3e80e3
RS
773 (@section . @chapter)
774 (@unnumberedsec . @unnumbered)
775 (@heading . @chapheading)
776 (@appendixsec . @appendix)
db95369b 777
7f3e80e3
RS
778 (@subsection . @section)
779 (@unnumberedsubsec . @unnumberedsec)
780 (@subheading . @heading)
781 (@appendixsubsec . @appendixsec)
db95369b 782
7f3e80e3
RS
783 (@subsubsection . @subsection)
784 (@unnumberedsubsubsec . @unnumberedsubsec)
785 (@subsubheading . @subheading)
786 (@appendixsubsubsec . @appendixsubsec))
787 "*An alist of next higher levels for chapters, sections. etc.
788For example, section to chapter, subsection to section.
789Used by `texinfo-raise-lower-sections'.
790The keys specify types of section; the values correspond to the next
791higher types.")
792
793(defvar texinfo-lowersections-alist
db95369b 794 '((@chapter . @section)
7f3e80e3 795 (@unnumbered . @unnumberedsec)
92f62199 796 (@centerchap . @unnumberedsec)
7f3e80e3
RS
797 (@majorheading . @heading)
798 (@chapheading . @heading)
799 (@appendix . @appendixsec)
db95369b 800
7f3e80e3
RS
801 (@section . @subsection)
802 (@unnumberedsec . @unnumberedsubsec)
803 (@heading . @subheading)
804 (@appendixsec . @appendixsubsec)
db95369b 805
7f3e80e3
RS
806 (@subsection . @subsubsection)
807 (@unnumberedsubsec . @unnumberedsubsubsec)
808 (@subheading . @subsubheading)
809 (@appendixsubsec . @appendixsubsubsec)
db95369b 810
7f3e80e3
RS
811 (@subsubsection . @subsubsection) ; Cannot go lower.
812 (@unnumberedsubsubsec . @unnumberedsubsubsec)
813 (@subsubheading . @subsubheading)
814 (@appendixsubsubsec . @appendixsubsubsec))
815 "*An alist of next lower levels for chapters, sections. etc.
816For example, chapter to section, section to subsection.
817Used by `texinfo-raise-lower-sections'.
818The keys specify types of section; the values correspond to the next
819lower types.")
4dd29d03
BP
820
821\f
7f3e80e3
RS
822;;; Perform those texinfo-to-info conversions that apply to the whole input
823;;; uniformly.
824
4dd29d03 825(defun texinfo-format-scan ()
7f3e80e3 826 (texinfo-format-convert (point-min) (point-max))
a66ccdcf
RC
827 ;; Search for @copying, which has to be first since the
828 ;; @insertcopying command then inserts the text elsewhere.
829 (goto-char (point-min))
830 (when (search-forward "@copying" nil t)
831 (texinfo-copying))
832 (while (search-forward "@insertcopying" nil t)
833 (delete-region (match-beginning 0) (match-end 0))
834
835 (texinfo-insertcopying))
836 ;; Scan for other @-commands.
7f3e80e3
RS
837 (goto-char (point-min))
838 (while (search-forward "@" nil t)
92f62199
RS
839 ;;
840 ;; These are the single-character accent commands: @^ @` @' @" @= @~
841 ;; In Info, they are simply quoted and the @ deleted.
842 ;; Other single-character commands:
db95369b 843 ;; @* forces a line break,
92f62199
RS
844 ;; @- is a discretionary hyphenation point; does nothing in Info.
845 ;; @<space>, @<tab>, @<newline> each produce a single space,
846 ;; unless followed by a newline.
db95369b 847 ;;
92f62199
RS
848 ;; Old version 2.34 expression: (looking-at "[@{}^'` *\"?!]")
849 (if (looking-at "[@{}^'`\"=~ \t\n*?!-]")
850 ;; @*, causes a line break.
db95369b 851 (cond
92f62199
RS
852 ;; @*, a line break
853 ((= (following-char) ?*)
854 ;; remove command
855 (delete-region (1- (point)) (1+ (point)))
856 ;; insert return if not at end of line;
857 ;; else line is already broken.
858 (if (not (= (following-char) ?\n))
db95369b 859 (insert ?\n)))
92f62199
RS
860 ;; @-, deleted
861 ((= (following-char) ?-)
862 (delete-region (1- (point)) (1+ (point))))
863 ;; @<space>, @<tab>, @<newline>: produce a single space,
864 ;; unless followed by a newline.
865 ((= (following-char) ? )
866 (delete-region (1- (point)) (1+ (point)))
867 ;; insert single space if not at end of line;
868 ;; else line is already broken.
869 (if (not (= (following-char) ?\n))
db95369b 870 (insert ? )))
92f62199
RS
871 ((= (following-char) ?\t)
872 (delete-region (1- (point)) (1+ (point)))
873 ;; insert single space if not at end of line;
874 ;; else line is already broken.
875 (if (not (= (following-char) ?\n))
876 (insert ? )))
877 ;; following char is a carriage return
9ed79f5d 878 ((= (following-char) ?\n)
92f62199
RS
879 ;; remove command
880 (delete-region (1- (point)) (1+ (point)))
881 ;; insert single space if not at end of line;
882 ;; else line is already broken.
883 (if (not (= (following-char) ?\n))
884 (insert ? )))
885 ;; Otherwise: the other characters are simply quoted. Delete the @.
886 (t
887 (delete-char -1)
4ff163fd 888 ;; Be compatible with makeinfo: if @' and its ilk are
9238a8df
EZ
889 ;; followed by a @ without a brace, barf.
890 (if (looking-at "[\"'^`~=]")
891 (progn
892 (if (= (char-after (1+ (point))) ?@)
893 (error "Use braces to give a command as an argument to @%c"
894 (following-char)))
895 (forward-char 1)
896 ;; @' etc. can optionally accept their argument in
897 ;; braces (makeinfo supports that).
898 (when (looking-at "{")
899 (let ((start (point)))
900 (forward-list 1)
901 (delete-char -1)
902 (goto-char start)
903 (delete-char 1))))
904 (forward-char 1))))
7f3e80e3
RS
905 ;; @ is followed by a command-word; find the end of the word.
906 (setq texinfo-command-start (1- (point)))
907 (if (= (char-syntax (following-char)) ?w)
908 (forward-word 1)
909 (forward-char 1))
910 (setq texinfo-command-end (point))
f66f0ee8
KH
911 ;; Detect the case of two @-commands in a row;
912 ;; process just the first one.
913 (goto-char (1+ texinfo-command-start))
914 (skip-chars-forward "^@" texinfo-command-end)
915 (setq texinfo-command-end (point))
dc7deb17 916 ;; Handle let aliasing
7f3e80e3 917 (setq texinfo-command-name
1c87ab31 918 (let (trial
db95369b 919 (cmdname
289df0fc 920 (buffer-substring-no-properties
1c87ab31
RS
921 (1+ texinfo-command-start) texinfo-command-end)))
922 (while (setq trial (assoc cmdname texinfo-alias-list))
923 (setq cmdname (cdr trial)))
dc7deb17
RS
924 (intern cmdname)))
925 ;; Call the handler for this command.
7f3e80e3
RS
926 (let ((enclosure-type
927 (assoc
928 (symbol-name texinfo-command-name)
929 texinfo-enclosure-list)))
930 (if enclosure-type
931 (progn
932 (insert
db95369b 933 (car (car (cdr enclosure-type)))
7f3e80e3
RS
934 (texinfo-parse-arg-discard)
935 (car (cdr (car (cdr enclosure-type)))))
936 (goto-char texinfo-command-start))
937 (let ((cmd (get texinfo-command-name 'texinfo-format)))
938 (if cmd (funcall cmd) (texinfo-unsupported)))))))
db95369b 939
7f3e80e3
RS
940 (cond (texinfo-stack
941 (goto-char (nth 2 (car texinfo-stack)))
a66ccdcf
RC
942 (error "Unterminated @%s" (car (car texinfo-stack)))))
943
944 ;; Remove excess whitespace
4a15fdc6
JB
945 (let ((whitespace-silent t))
946 (whitespace-cleanup)))
a66ccdcf 947
db95369b 948(defvar texinfo-copying-text ""
a66ccdcf
RC
949 "Text of the copyright notice and copying permissions.")
950
951(defun texinfo-copying ()
db95369b
JB
952 "Copy the copyright notice and copying permissions from the Texinfo file,
953as indicated by the @copying ... @end copying command;
a66ccdcf
RC
954insert the text with the @insertcopying command."
955 (let ((beg (progn (beginning-of-line) (point)))
956 (end (progn (re-search-forward "^@end copying[ \t]*\n") (point))))
957 (setq texinfo-copying-text
958 (buffer-substring-no-properties
959 (save-excursion (goto-char beg) (forward-line 1) (point))
960 (save-excursion (goto-char end) (forward-line -1) (point))))
961 (delete-region beg end)))
962
963(defun texinfo-insertcopying ()
db95369b 964 "Insert the copyright notice and copying permissions from the Texinfo file,
a66ccdcf
RC
965which are indicated by the @copying ... @end copying command."
966 (insert (concat "\n" texinfo-copying-text)))
4dd29d03
BP
967
968(put 'begin 'texinfo-format 'texinfo-format-begin)
969(defun texinfo-format-begin ()
970 (texinfo-format-begin-end 'texinfo-format))
971
972(put 'end 'texinfo-format 'texinfo-format-end)
973(defun texinfo-format-end ()
974 (texinfo-format-begin-end 'texinfo-end))
975
976(defun texinfo-format-begin-end (prop)
977 (setq texinfo-command-name (intern (texinfo-parse-line-arg)))
64c8498a
RS
978 (let ((cmd (get texinfo-command-name prop)))
979 (if cmd (funcall cmd)
980 (texinfo-unsupported))))
4dd29d03 981\f
7f3e80e3
RS
982;;; Parsing functions
983
4dd29d03 984(defun texinfo-parse-line-arg ()
92f62199 985 "Return argument of @-command as string.
db95369b 986Argument is separated from command either by a space or by a brace.
92f62199
RS
987If a space, return rest of line, with beginning and ending white
988space removed. If a brace, return string between braces.
989Leave point after argument."
4dd29d03
BP
990 (goto-char texinfo-command-end)
991 (let ((start (point)))
992 (cond ((looking-at " ")
7f3e80e3
RS
993 (skip-chars-forward " ")
994 (setq start (point))
995 (end-of-line)
4dd29d03 996 (skip-chars-backward " ")
7f3e80e3
RS
997 (delete-region (point) (progn (end-of-line) (point)))
998 (setq texinfo-command-end (1+ (point))))
999 ((looking-at "{")
1000 (setq start (1+ (point)))
1001 (forward-list 1)
1002 (setq texinfo-command-end (point))
1003 (forward-char -1))
1004 (t
1005 (error "Invalid texinfo command arg format")))
289df0fc 1006 (prog1 (buffer-substring-no-properties start (point))
7f3e80e3 1007 (if (eolp) (forward-char 1)))))
4dd29d03
BP
1008
1009(defun texinfo-parse-expanded-arg ()
1010 (goto-char texinfo-command-end)
1011 (let ((start (point))
7f3e80e3 1012 marker)
4dd29d03 1013 (cond ((looking-at " ")
7f3e80e3
RS
1014 (skip-chars-forward " ")
1015 (setq start (point))
1016 (end-of-line)
1017 (setq texinfo-command-end (1+ (point))))
1018 ((looking-at "{")
1019 (setq start (1+ (point)))
1020 (forward-list 1)
1021 (setq texinfo-command-end (point))
1022 (forward-char -1))
1023 (t
1024 (error "Invalid texinfo command arg format")))
4dd29d03
BP
1025 (setq marker (move-marker (make-marker) texinfo-command-end))
1026 (texinfo-format-expand-region start (point))
1027 (setq texinfo-command-end (marker-position marker))
1028 (move-marker marker nil)
289df0fc 1029 (prog1 (buffer-substring-no-properties start (point))
7f3e80e3 1030 (if (eolp) (forward-char 1)))))
4dd29d03
BP
1031
1032(defun texinfo-format-expand-region (start end)
1033 (save-restriction
1034 (narrow-to-region start end)
1035 (let (texinfo-command-start
7f3e80e3
RS
1036 texinfo-command-end
1037 texinfo-command-name
1038 texinfo-stack)
4dd29d03
BP
1039 (texinfo-format-scan))
1040 (goto-char (point-max))))
1041
1042(defun texinfo-parse-arg-discard ()
92f62199 1043 "Delete command and argument; return argument of command."
4dd29d03 1044 (prog1 (texinfo-parse-line-arg)
7f3e80e3 1045 (texinfo-discard-command)))
4dd29d03
BP
1046
1047(defun texinfo-discard-command ()
1048 (delete-region texinfo-command-start texinfo-command-end))
1049
1050(defun texinfo-optional-braces-discard ()
1051 "Discard braces following command, if any."
1052 (goto-char texinfo-command-end)
1053 (let ((start (point)))
1054 (cond ((looking-at "[ \t]*\n")) ; do nothing
1055 ((looking-at "{") ; remove braces, if any
7f3e80e3
RS
1056 (forward-list 1)
1057 (setq texinfo-command-end (point)))
1058 (t
4dd29d03
BP
1059 (error
1060 "Invalid `texinfo-optional-braces-discard' format \(need braces?\)")))
1061 (delete-region texinfo-command-start texinfo-command-end)))
1062
1063(defun texinfo-format-parse-line-args ()
1064 (let ((start (1- (point)))
7f3e80e3
RS
1065 next beg end
1066 args)
4dd29d03
BP
1067 (skip-chars-forward " ")
1068 (while (not (eolp))
1069 (setq beg (point))
1070 (re-search-forward "[\n,]")
1071 (setq next (point))
1072 (if (bolp) (setq next (1- next)))
1073 (forward-char -1)
1074 (skip-chars-backward " ")
1075 (setq end (point))
289df0fc 1076 (setq args (cons (if (> end beg) (buffer-substring-no-properties beg end))
7f3e80e3 1077 args))
4dd29d03
BP
1078 (goto-char next)
1079 (skip-chars-forward " "))
1080 (if (eolp) (forward-char 1))
1081 (setq texinfo-command-end (point))
1082 (nreverse args)))
1083
1084(defun texinfo-format-parse-args ()
1085 (let ((start (1- (point)))
7f3e80e3
RS
1086 next beg end
1087 args)
4dd29d03
BP
1088 (search-forward "{")
1089 (save-excursion
db95369b 1090 (texinfo-format-expand-region
4dd29d03
BP
1091 (point)
1092 (save-excursion (up-list 1) (1- (point)))))
7f3e80e3
RS
1093 ;; The following does not handle cross references of the form:
1094 ;; `@xref{bullet, , @code{@@bullet}@{@}}.' because the
1095 ;; re-search-forward finds the first right brace after the second
db95369b 1096 ;; comma.
4dd29d03
BP
1097 (while (/= (preceding-char) ?\})
1098 (skip-chars-forward " \t\n")
1099 (setq beg (point))
1100 (re-search-forward "[},]")
1101 (setq next (point))
1102 (forward-char -1)
1103 (skip-chars-backward " \t\n")
1104 (setq end (point))
1105 (cond ((< beg end)
7f3e80e3
RS
1106 (goto-char beg)
1107 (while (search-forward "\n" end t)
1108 (replace-match " "))))
289df0fc 1109 (setq args (cons (if (> end beg) (buffer-substring-no-properties beg end))
7f3e80e3 1110 args))
4dd29d03 1111 (goto-char next))
8bb6eb14 1112 ;;(if (eolp) (forward-char 1))
4dd29d03
BP
1113 (setq texinfo-command-end (point))
1114 (nreverse args)))
1115
1116(defun texinfo-format-parse-defun-args ()
1117 (goto-char texinfo-command-end)
1118 (let ((start (point)))
1119 (end-of-line)
1120 (setq texinfo-command-end (1+ (point)))
1121 (let ((marker (move-marker (make-marker) texinfo-command-end)))
1122 (texinfo-format-expand-region start (point))
1123 (setq texinfo-command-end (marker-position marker))
1124 (move-marker marker nil))
1125 (goto-char start)
1126 (let ((args '())
7f3e80e3 1127 beg end)
4dd29d03
BP
1128 (skip-chars-forward " ")
1129 (while (not (eolp))
7f3e80e3
RS
1130 (cond ((looking-at "{")
1131 (setq beg (1+ (point)))
1132 (forward-list 1)
1133 (setq end (1- (point))))
1134 (t
1135 (setq beg (point))
1136 (re-search-forward "[\n ]")
1137 (forward-char -1)
1138 (setq end (point))))
289df0fc 1139 (setq args (cons (buffer-substring-no-properties beg end) args))
7f3e80e3 1140 (skip-chars-forward " "))
4dd29d03
BP
1141 (forward-char 1)
1142 (nreverse args))))
4dd29d03 1143
7f3e80e3
RS
1144(defun texinfo-discard-line ()
1145 (goto-char texinfo-command-end)
1146 (skip-chars-forward " \t")
1147 (or (eolp)
e8af40ee 1148 (error "Extraneous text at end of command line"))
7f3e80e3
RS
1149 (goto-char texinfo-command-start)
1150 (or (bolp)
e8af40ee 1151 (error "Extraneous text at beginning of command line"))
7f3e80e3
RS
1152 (delete-region (point) (progn (forward-line 1) (point))))
1153
1154(defun texinfo-discard-line-with-args ()
1155 (goto-char texinfo-command-start)
1156 (delete-region (point) (progn (forward-line 1) (point))))
1157
1158\f
1159;;; @setfilename
4dd29d03 1160
7f3e80e3
RS
1161;; Only `texinfo-format-buffer' handles @setfilename with this
1162;; definition; `texinfo-format-region' handles @setfilename, if any,
db95369b 1163;; specially.
4dd29d03
BP
1164(put 'setfilename 'texinfo-format 'texinfo-format-setfilename)
1165(defun texinfo-format-setfilename ()
d0970585 1166 (texinfo-parse-arg-discard))
7f3e80e3 1167\f
92f62199 1168;;; @node, @menu, @detailmenu
4dd29d03
BP
1169
1170(put 'node 'texinfo-format 'texinfo-format-node)
7f3e80e3 1171(put 'nwnode 'texinfo-format 'texinfo-format-node)
4dd29d03
BP
1172(defun texinfo-format-node ()
1173 (let* ((args (texinfo-format-parse-line-args))
7f3e80e3
RS
1174 (name (nth 0 args))
1175 (next (nth 1 args))
1176 (prev (nth 2 args))
1177 (up (nth 3 args)))
4dd29d03
BP
1178 (texinfo-discard-command)
1179 (setq texinfo-last-node name)
8d66d13d 1180 (let ((tem (if texinfo-fold-nodename-case (downcase name) name)))
4dd29d03 1181 (if (assoc tem texinfo-node-names)
7f3e80e3
RS
1182 (error "Duplicate node name: %s" name)
1183 (setq texinfo-node-names (cons (list tem) texinfo-node-names))))
4dd29d03 1184 (setq texinfo-footnote-number 0)
25450668
RS
1185 ;; insert "\n\^_" unconditionally since this is what info is looking for
1186 (insert "\n\^_\nFile: " texinfo-format-filename
7f3e80e3
RS
1187 ", Node: " name)
1188 (if next
1189 (insert ", Next: " next))
4dd29d03 1190 (if prev
7f3e80e3 1191 (insert ", Prev: " prev))
4dd29d03 1192 (if up
7f3e80e3
RS
1193 (insert ", Up: " up))
1194 (insert ?\n)
1195 (setq texinfo-last-node-pos (point))))
4dd29d03 1196
007be42a
RS
1197(put 'anchor 'texinfo-format 'texinfo-anchor)
1198(defun texinfo-anchor ()
db95369b 1199 (let (anchor-string
007be42a
RS
1200 (here (- (point) 7)) ; save location of beginning of `@anchor'
1201 (arg (texinfo-parse-arg-discard)))
294500f2
RS
1202 (if (looking-at " ") ; since a space may be left after -discard
1203 (delete-char 1))
db95369b 1204 (forward-paragraph)
007be42a 1205 (let ((end (point)))
db95369b 1206 (if (save-excursion
007be42a
RS
1207 (backward-word 1)
1208 (search-forward "@refill" end t))
1209 (setq anchor-string "@anchor-yes-refill")
1210 (setq anchor-string "@anchor-no-refill")))
1211 (goto-char here)
1212 (insert anchor-string "{" arg "}")))
1213
4dd29d03
BP
1214(put 'menu 'texinfo-format 'texinfo-format-menu)
1215(defun texinfo-format-menu ()
1216 (texinfo-discard-line)
1217 (insert "* Menu:\n\n"))
1218
1219(put 'menu 'texinfo-end 'texinfo-discard-command)
7f3e80e3 1220
92f62199
RS
1221;; The @detailmenu should be removed eventually.
1222
1223;; According to Karl Berry, 31 August 1996:
db95369b 1224;;
92f62199
RS
1225;; You don't like, I don't like it. I agree, it would be better just to
1226;; fix the bug [in `makeinfo']. .. At this point, since inserting those
1227;; two commands in the Elisp fn is trivial, I don't especially want to
1228;; expend more effort...
db95369b 1229;;
92f62199
RS
1230;; I added a couple sentences of documentation to the manual (putting the
1231;; blame on makeinfo where it belongs :-().
1232
1233(put 'detailmenu 'texinfo-format 'texinfo-discard-line)
1234(put 'detailmenu 'texinfo-end 'texinfo-discard-command)
1235
1236;; (Also see `texnfo-upd.el')
1237
7f3e80e3
RS
1238\f
1239;;; Cross references
4dd29d03 1240
92f62199
RS
1241;; @xref {NODE, FNAME, NAME, FILE, DOCUMENT}
1242;; -> *Note FNAME: (FILE)NODE
1243;; If FILE is missing,
1244;; *Note FNAME: NODE
1245;; If FNAME is empty and NAME is present
1246;; *Note NAME: Node
1247;; If both NAME and FNAME are missing
1248;; *Note NODE::
1249;; texinfo ignores the DOCUMENT argument.
1250;; -> See section <xref to NODE> [NAME, else NODE], page <xref to NODE>
1251;; If FILE is specified, (FILE)NODE is used for xrefs.
1252;; If fifth argument DOCUMENT is specified, produces
1253;; See section <xref to NODE> [NAME, else NODE], page <xref to NODE>
1254;; of DOCUMENT
1255
1256;; @ref a reference that does not put `See' or `see' in
1257;; the hardcopy and is the same as @xref in Info
4dd29d03
BP
1258(put 'ref 'texinfo-format 'texinfo-format-xref)
1259
1260(put 'xref 'texinfo-format 'texinfo-format-xref)
1261(defun texinfo-format-xref ()
1262 (let ((args (texinfo-format-parse-args)))
1263 (texinfo-discard-command)
1264 (insert "*Note ")
1265 (let ((fname (or (nth 1 args) (nth 2 args))))
1266 (if (null (or fname (nth 3 args)))
7f3e80e3
RS
1267 (insert (car args) "::")
1268 (insert (or fname (car args)) ": ")
1269 (if (nth 3 args)
1270 (insert "(" (nth 3 args) ")"))
11595aa9 1271 (and (car args) (insert (car args)))))))
4dd29d03
BP
1272
1273(put 'pxref 'texinfo-format 'texinfo-format-pxref)
1274(defun texinfo-format-pxref ()
1275 (texinfo-format-xref)
1276 (or (save-excursion
7f3e80e3
RS
1277 (forward-char -2)
1278 (looking-at "::"))
4dd29d03
BP
1279 (insert ".")))
1280
92f62199
RS
1281;; @inforef{NODE, FNAME, FILE}
1282;; Like @xref{NODE, FNAME,,FILE} in texinfo.
1283;; In Tex, generates "See Info file FILE, node NODE"
4dd29d03
BP
1284(put 'inforef 'texinfo-format 'texinfo-format-inforef)
1285(defun texinfo-format-inforef ()
1286 (let ((args (texinfo-format-parse-args)))
1287 (texinfo-discard-command)
1288 (if (nth 1 args)
1289 (insert "*Note " (nth 1 args) ": (" (nth 2 args) ")" (car args))
1290 (insert "*Note " "(" (nth 2 args) ")" (car args) "::"))))
1291
7f3e80e3 1292\f
1c87ab31
RS
1293;;; URL Reference: @uref
1294
db95369b
JB
1295;; @uref produces a reference to a uniform resource locator (URL).
1296;; It takes one mandatory argument, the URL, and one optional argument,
1297;; the text to display (the default is the URL itself).
1c87ab31
RS
1298
1299(put 'uref 'texinfo-format 'texinfo-format-uref)
1300(defun texinfo-format-uref ()
1301 "Format URL and optional URL-TITLE.
db95369b 1302Insert ` ... ' around URL if no URL-TITLE argument;
1c87ab31
RS
1303otherwise, insert URL-TITLE followed by URL in parentheses."
1304 (let ((args (texinfo-format-parse-args)))
1305 (texinfo-discard-command)
db95369b 1306 ;; if url-title
1c87ab31
RS
1307 (if (nth 1 args)
1308 (insert (nth 1 args) " (" (nth 0 args) ")")
1309 (insert "`" (nth 0 args) "'"))
1310 (goto-char texinfo-command-start)))
1311
1312\f
7f3e80e3
RS
1313;;; Section headings
1314
1315(put 'majorheading 'texinfo-format 'texinfo-format-chapter)
4dd29d03
BP
1316(put 'chapheading 'texinfo-format 'texinfo-format-chapter)
1317(put 'ichapter 'texinfo-format 'texinfo-format-chapter)
1318(put 'chapter 'texinfo-format 'texinfo-format-chapter)
1319(put 'iappendix 'texinfo-format 'texinfo-format-chapter)
1320(put 'appendix 'texinfo-format 'texinfo-format-chapter)
1321(put 'iunnumbered 'texinfo-format 'texinfo-format-chapter)
7f3e80e3 1322(put 'top 'texinfo-format 'texinfo-format-chapter)
4dd29d03 1323(put 'unnumbered 'texinfo-format 'texinfo-format-chapter)
92f62199 1324(put 'centerchap 'texinfo-format 'texinfo-format-chapter)
4dd29d03
BP
1325(defun texinfo-format-chapter ()
1326 (texinfo-format-chapter-1 ?*))
1327
1328(put 'heading 'texinfo-format 'texinfo-format-section)
1329(put 'isection 'texinfo-format 'texinfo-format-section)
1330(put 'section 'texinfo-format 'texinfo-format-section)
1331(put 'iappendixsection 'texinfo-format 'texinfo-format-section)
1332(put 'appendixsection 'texinfo-format 'texinfo-format-section)
1333(put 'iappendixsec 'texinfo-format 'texinfo-format-section)
1334(put 'appendixsec 'texinfo-format 'texinfo-format-section)
1335(put 'iunnumberedsec 'texinfo-format 'texinfo-format-section)
1336(put 'unnumberedsec 'texinfo-format 'texinfo-format-section)
1337(defun texinfo-format-section ()
1338 (texinfo-format-chapter-1 ?=))
1339
1340(put 'subheading 'texinfo-format 'texinfo-format-subsection)
1341(put 'isubsection 'texinfo-format 'texinfo-format-subsection)
1342(put 'subsection 'texinfo-format 'texinfo-format-subsection)
1343(put 'iappendixsubsec 'texinfo-format 'texinfo-format-subsection)
1344(put 'appendixsubsec 'texinfo-format 'texinfo-format-subsection)
1345(put 'iunnumberedsubsec 'texinfo-format 'texinfo-format-subsection)
1346(put 'unnumberedsubsec 'texinfo-format 'texinfo-format-subsection)
1347(defun texinfo-format-subsection ()
1348 (texinfo-format-chapter-1 ?-))
1349
1350(put 'subsubheading 'texinfo-format 'texinfo-format-subsubsection)
1351(put 'isubsubsection 'texinfo-format 'texinfo-format-subsubsection)
1352(put 'subsubsection 'texinfo-format 'texinfo-format-subsubsection)
1353(put 'iappendixsubsubsec 'texinfo-format 'texinfo-format-subsubsection)
1354(put 'appendixsubsubsec 'texinfo-format 'texinfo-format-subsubsection)
1355(put 'iunnumberedsubsubsec 'texinfo-format 'texinfo-format-subsubsection)
1356(put 'unnumberedsubsubsec 'texinfo-format 'texinfo-format-subsubsection)
1357(defun texinfo-format-subsubsection ()
1358 (texinfo-format-chapter-1 ?.))
1359
1360(defun texinfo-format-chapter-1 (belowchar)
1361 (let ((arg (texinfo-parse-arg-discard)))
1362 (message "Formatting: %s ... " arg) ; So we can see where we are.
1363 (insert ?\n arg ?\n "@SectionPAD " belowchar ?\n)
1364 (forward-line -2)))
1365
1366(put 'SectionPAD 'texinfo-format 'texinfo-format-sectionpad)
1367(defun texinfo-format-sectionpad ()
1368 (let ((str (texinfo-parse-arg-discard)))
1369 (forward-char -1)
1370 (let ((column (current-column)))
1371 (forward-char 1)
1372 (while (> column 0)
7f3e80e3
RS
1373 (insert str)
1374 (setq column (1- column))))
4dd29d03
BP
1375 (insert ?\n)))
1376
7f3e80e3 1377\f
5ec5330e
RS
1378;;; Space controlling commands: @. and @:, and the soft hyphen.
1379
4dd29d03
BP
1380(put '\. 'texinfo-format 'texinfo-format-\.)
1381(defun texinfo-format-\. ()
1382 (texinfo-discard-command)
1383 (insert "."))
1384
1385(put '\: 'texinfo-format 'texinfo-format-\:)
1386(defun texinfo-format-\: ()
1387 (texinfo-discard-command))
1388
5ec5330e
RS
1389(put '\- 'texinfo-format 'texinfo-format-soft-hyphen)
1390(defun texinfo-format-soft-hyphen ()
1391 (texinfo-discard-command))
1392
7f3e80e3 1393\f
d79abb69
RC
1394;;; @kbdinputstyle, @vskip, headings & footings
1395;; These commands for not for Info and should never
db95369b
JB
1396;; appear in an Info environment; but if they do,
1397;; this causes them to be discarded.
d79abb69
RC
1398
1399;; @kbdinputstyle
1400(put 'kbdinputstyle 'texinfo-format 'texinfo-discard-line-with-args)
1401
1402;; @vskip
1403(put 'vskip 'texinfo-format 'texinfo-discard-line-with-args)
1404
1405;; headings & footings
1406(put 'evenfooting 'texinfo-format 'texinfo-discard-line-with-args)
1407(put 'evenheading 'texinfo-format 'texinfo-discard-line-with-args)
1408(put 'oddfooting 'texinfo-format 'texinfo-discard-line-with-args)
1409(put 'oddheading 'texinfo-format 'texinfo-discard-line-with-args)
1410(put 'everyfooting 'texinfo-format 'texinfo-discard-line-with-args)
1411(put 'everyheading 'texinfo-format 'texinfo-discard-line-with-args)
1412
1413\f
1414;;; @documentdescription ... @end documentdescription
1415;; This command is for HTML output and should never
db95369b
JB
1416;; appear in an Info environment; but if it does,
1417;; this causes it to be discarded.
d79abb69
RC
1418
1419(put 'documentdescription 'texinfo-format 'texinfo-format-documentdescription)
1420(defun texinfo-format-documentdescription ()
1421 (delete-region texinfo-command-start
1422 (progn (re-search-forward "^@end documentdescription[ \t]*\n")
1423 (point))))
1424
1425
1426\f
7f3e80e3
RS
1427;;; @center, @sp, and @br
1428
4dd29d03
BP
1429(put 'center 'texinfo-format 'texinfo-format-center)
1430(defun texinfo-format-center ()
7f3e80e3
RS
1431 (let ((arg (texinfo-parse-expanded-arg)))
1432 (texinfo-discard-command)
1433 (insert arg)
1434 (insert ?\n)
1435 (save-restriction
1436 (goto-char (1- (point)))
1437 (let ((indent-tabs-mode nil))
1438 (center-line)))))
4dd29d03
BP
1439
1440(put 'sp 'texinfo-format 'texinfo-format-sp)
1441(defun texinfo-format-sp ()
1442 (let* ((arg (texinfo-parse-arg-discard))
7f3e80e3 1443 (num (read arg)))
4dd29d03
BP
1444 (insert-char ?\n num)))
1445
1446(put 'br 'texinfo-format 'texinfo-format-paragraph-break)
1447(defun texinfo-format-paragraph-break ()
1448 "Force a paragraph break.
1449If used within a line, follow `@br' with braces."
1450 (texinfo-optional-braces-discard)
1451 ;; insert one return if at end of line;
1452 ;; else insert two returns, to generate a blank line.
1453 (if (= (following-char) ?\n)
1454 (insert ?\n)
1455 (insert-char ?\n 2)))
1456
1457\f
7f3e80e3 1458;;; @footnote and @footnotestyle
4dd29d03 1459
92f62199
RS
1460;; In Texinfo, footnotes are created with the `@footnote' command.
1461;; This command is followed immediately by a left brace, then by the text of
1462;; the footnote, and then by a terminating right brace. The
1463;; template for a footnote is:
db95369b 1464;;
92f62199
RS
1465;; @footnote{TEXT}
1466;;
1467;; Info has two footnote styles:
db95369b 1468;;
92f62199
RS
1469;; * In the End of node style, all the footnotes for a single node
1470;; are placed at the end of that node. The footnotes are
1471;; separated from the rest of the node by a line of dashes with
1472;; the word `Footnotes' within it.
db95369b 1473;;
92f62199
RS
1474;; * In the Separate node style, all the footnotes for a single node
1475;; are placed in an automatically constructed node of their own.
1476
1477;; Footnote style is specified by the @footnotestyle command, either
1478;; @footnotestyle separate
1479;; or
1480;; @footnotestyle end
db95369b 1481;;
92f62199 1482;; The default is separate
7f3e80e3 1483
db95369b 1484(defvar texinfo-footnote-style "separate"
7f3e80e3 1485 "Footnote style, either separate or end.")
4dd29d03 1486
7f3e80e3
RS
1487(put 'footnotestyle 'texinfo-format 'texinfo-footnotestyle)
1488(defun texinfo-footnotestyle ()
1489 "Specify whether footnotes are at end of node or in separate nodes.
1490Argument is either end or separate."
1491 (setq texinfo-footnote-style (texinfo-parse-arg-discard)))
4dd29d03
BP
1492
1493(defvar texinfo-footnote-number)
1494
7f3e80e3 1495(put 'footnote 'texinfo-format 'texinfo-format-footnote)
4dd29d03 1496(defun texinfo-format-footnote ()
7f3e80e3
RS
1497 "Format a footnote in either end of node or separate node style.
1498The texinfo-footnote-style variable controls which style is used."
4dd29d03 1499 (setq texinfo-footnote-number (1+ texinfo-footnote-number))
7f3e80e3
RS
1500 (cond ((string= texinfo-footnote-style "end")
1501 (texinfo-format-end-node))
1502 ((string= texinfo-footnote-style "separate")
1503 (texinfo-format-separate-node))))
4dd29d03 1504
7f3e80e3
RS
1505(defun texinfo-format-separate-node ()
1506 "Format footnote in Separate node style, with notes in own node.
4dd29d03
BP
1507The node is constructed automatically."
1508 (let* (start
7f3e80e3 1509 (arg (texinfo-parse-line-arg))
4dd29d03
BP
1510 (node-name-beginning
1511 (save-excursion
1512 (re-search-backward
7f3e80e3 1513 "^File: \\w+\\(\\w\\|\\s_\\|\\.\\|,\\)*[ \t]+Node:")
4dd29d03
BP
1514 (match-end 0)))
1515 (node-name
1516 (save-excursion
289df0fc 1517 (buffer-substring-no-properties
4dd29d03
BP
1518 (progn (goto-char node-name-beginning) ; skip over node command
1519 (skip-chars-forward " \t") ; and over spaces
1520 (point))
1521 (if (search-forward
1522 ","
1523 (save-excursion (end-of-line) (point)) t) ; bound search
1524 (1- (point))
1525 (end-of-line) (point))))))
7f3e80e3
RS
1526 (texinfo-discard-command) ; remove or insert whitespace, as needed
1527 (delete-region (save-excursion (skip-chars-backward " \t\n") (point))
1528 (point))
1529 (insert (format " (%d) (*Note %s-Footnotes::)"
1530 texinfo-footnote-number node-name))
4dd29d03
BP
1531 (fill-paragraph nil)
1532 (save-excursion
1533 (if (re-search-forward "^@node" nil 'move)
1534 (forward-line -1))
1535
1536 ;; two cases: for the first footnote, we must insert a node header;
db95369b 1537 ;; for the second and subsequent footnotes, we need only insert
4dd29d03
BP
1538 ;; the text of the footnote.
1539
1540 (if (save-excursion
289df0fc 1541 (search-backward
4dd29d03
BP
1542 (concat node-name "-Footnotes, Up: ")
1543 node-name-beginning
1544 t))
1545 (progn ; already at least one footnote
1546 (setq start (point))
1547 (insert (format "\n(%d) %s\n" texinfo-footnote-number arg))
1548 (fill-region start (point)))
1549 ;; else not yet a footnote
1550 (insert "\n\^_\nFile: " texinfo-format-filename
1551 " Node: " node-name "-Footnotes, Up: " node-name "\n")
1552 (setq start (point))
1553 (insert (format "\n(%d) %s\n" texinfo-footnote-number arg))
1554 (fill-region start (point))))))
1555
1556(defun texinfo-format-end-node ()
7f3e80e3 1557 "Format footnote in the End of node style, with notes at end of node."
4dd29d03 1558 (let (start
7f3e80e3
RS
1559 (arg (texinfo-parse-line-arg)))
1560 (texinfo-discard-command) ; remove or insert whitespace, as needed
1561 (delete-region (save-excursion (skip-chars-backward " \t\n") (point))
1562 (point))
1563 (insert (format " (%d) " texinfo-footnote-number))
4dd29d03
BP
1564 (fill-paragraph nil)
1565 (save-excursion
1566 (if (search-forward "\n--------- Footnotes ---------\n" nil t)
1567 (progn ; already have footnote, put new one before end of node
1568 (if (re-search-forward "^@node" nil 'move)
1569 (forward-line -1))
1570 (setq start (point))
1571 (insert (format "\n(%d) %s\n" texinfo-footnote-number arg))
1572 (fill-region start (point)))
1573 ;; else no prior footnote
1574 (if (re-search-forward "^@node" nil 'move)
1575 (forward-line -1))
1576 (insert "\n--------- Footnotes ---------\n")
1577 (setq start (point))
7f3e80e3 1578 (insert (format "\n(%d) %s\n" texinfo-footnote-number arg))))))
4dd29d03
BP
1579
1580\f
7f3e80e3
RS
1581;;; @itemize, @enumerate, and similar commands
1582
4dd29d03
BP
1583;; @itemize pushes (itemize "COMMANDS" STARTPOS) on texinfo-stack.
1584;; @enumerate pushes (enumerate 0 STARTPOS).
1585;; @item dispatches to the texinfo-item prop of the first elt of the list.
1586;; For itemize, this puts in and rescans the COMMANDS.
1587;; For enumerate, this increments the number and puts it in.
1588;; In either case, it puts a Backspace at the front of the line
1589;; which marks it not to be indented later.
1590;; All other lines get indented by 5 when the @end is reached.
1591
7f3e80e3
RS
1592(defvar texinfo-stack-depth 0
1593 "Count of number of unpopped texinfo-push-stack calls.
1594Used by @refill indenting command to avoid indenting within lists, etc.")
1595
4dd29d03 1596(defun texinfo-push-stack (check arg)
7f3e80e3 1597 (setq texinfo-stack-depth (1+ texinfo-stack-depth))
4dd29d03 1598 (setq texinfo-stack
7f3e80e3
RS
1599 (cons (list check arg texinfo-command-start)
1600 texinfo-stack)))
4dd29d03
BP
1601
1602(defun texinfo-pop-stack (check)
7f3e80e3 1603 (setq texinfo-stack-depth (1- texinfo-stack-depth))
4dd29d03
BP
1604 (if (null texinfo-stack)
1605 (error "Unmatched @end %s" check))
1606 (if (not (eq (car (car texinfo-stack)) check))
1607 (error "@end %s matches @%s"
7f3e80e3 1608 check (car (car texinfo-stack))))
4dd29d03 1609 (prog1 (cdr (car texinfo-stack))
7f3e80e3 1610 (setq texinfo-stack (cdr texinfo-stack))))
4dd29d03
BP
1611
1612(put 'itemize 'texinfo-format 'texinfo-itemize)
1613(defun texinfo-itemize ()
7f3e80e3
RS
1614 (texinfo-push-stack
1615 'itemize
1616 (progn (skip-chars-forward " \t")
1617 (if (eolp)
1618 "@bullet"
1619 (texinfo-parse-line-arg))))
1620 (texinfo-discard-line-with-args)
4dd29d03
BP
1621 (setq fill-column (- fill-column 5)))
1622
1623(put 'itemize 'texinfo-end 'texinfo-end-itemize)
1624(defun texinfo-end-itemize ()
1625 (setq fill-column (+ fill-column 5))
1626 (texinfo-discard-command)
1627 (let ((stacktop
7f3e80e3 1628 (texinfo-pop-stack 'itemize)))
4dd29d03
BP
1629 (texinfo-do-itemize (nth 1 stacktop))))
1630
1631(put 'enumerate 'texinfo-format 'texinfo-enumerate)
1632(defun texinfo-enumerate ()
7f3e80e3 1633 (texinfo-push-stack
db95369b 1634 'enumerate
7f3e80e3
RS
1635 (progn (skip-chars-forward " \t")
1636 (if (eolp)
1637 1
1638 (read (current-buffer)))))
1639 (if (and (symbolp (car (cdr (car texinfo-stack))))
1640 (> 1 (length (symbol-name (car (cdr (car texinfo-stack)))))))
1641 (error
1642 "@enumerate: Use a number or letter, eg: 1, A, a, 3, B, or d." ))
1643 (texinfo-discard-line-with-args)
1644 (setq fill-column (- fill-column 5)))
4dd29d03
BP
1645
1646(put 'enumerate 'texinfo-end 'texinfo-end-enumerate)
1647(defun texinfo-end-enumerate ()
1648 (setq fill-column (+ fill-column 5))
1649 (texinfo-discard-command)
1650 (let ((stacktop
7f3e80e3 1651 (texinfo-pop-stack 'enumerate)))
4dd29d03
BP
1652 (texinfo-do-itemize (nth 1 stacktop))))
1653
7f3e80e3
RS
1654;; @alphaenumerate never became a standard part of Texinfo
1655(put 'alphaenumerate 'texinfo-format 'texinfo-alphaenumerate)
1656(defun texinfo-alphaenumerate ()
1657 (texinfo-push-stack 'alphaenumerate (1- ?a))
4dd29d03
BP
1658 (setq fill-column (- fill-column 5))
1659 (texinfo-discard-line))
1660
7f3e80e3
RS
1661(put 'alphaenumerate 'texinfo-end 'texinfo-end-alphaenumerate)
1662(defun texinfo-end-alphaenumerate ()
1663 (setq fill-column (+ fill-column 5))
1664 (texinfo-discard-command)
1665 (let ((stacktop
1666 (texinfo-pop-stack 'alphaenumerate)))
1667 (texinfo-do-itemize (nth 1 stacktop))))
1668
1669;; @capsenumerate never became a standard part of Texinfo
1670(put 'capsenumerate 'texinfo-format 'texinfo-capsenumerate)
1671(defun texinfo-capsenumerate ()
1672 (texinfo-push-stack 'capsenumerate (1- ?A))
4dd29d03
BP
1673 (setq fill-column (- fill-column 5))
1674 (texinfo-discard-line))
1675
7f3e80e3
RS
1676(put 'capsenumerate 'texinfo-end 'texinfo-end-capsenumerate)
1677(defun texinfo-end-capsenumerate ()
4dd29d03
BP
1678 (setq fill-column (+ fill-column 5))
1679 (texinfo-discard-command)
1680 (let ((stacktop
7f3e80e3 1681 (texinfo-pop-stack 'capsenumerate)))
4dd29d03
BP
1682 (texinfo-do-itemize (nth 1 stacktop))))
1683
1684;; At the @end, indent all the lines within the construct
1685;; except those marked with backspace. FROM says where
1686;; construct started.
1687(defun texinfo-do-itemize (from)
1688 (save-excursion
1689 (while (progn (forward-line -1)
7f3e80e3 1690 (>= (point) from))
4dd29d03 1691 (if (= (following-char) ?\b)
7f3e80e3
RS
1692 (save-excursion
1693 (delete-char 1)
1694 (end-of-line)
1695 (delete-char 6))
4dd29d03 1696 (if (not (looking-at "[ \t]*$"))
7f3e80e3 1697 (save-excursion (insert " ")))))))
4dd29d03
BP
1698
1699(put 'item 'texinfo-format 'texinfo-item)
1700(put 'itemx 'texinfo-format 'texinfo-item)
1701(defun texinfo-item ()
1702 (funcall (get (car (car texinfo-stack)) 'texinfo-item)))
1703
1704(put 'itemize 'texinfo-item 'texinfo-itemize-item)
1705(defun texinfo-itemize-item ()
7f3e80e3
RS
1706 ;; (texinfo-discard-line) ; Did not handle text on same line as @item.
1707 (delete-region (1+ (point)) (save-excursion (beginning-of-line) (point)))
1708 (if (looking-at "[ \t]*[^ \t\n]+")
1709 ;; Text on same line as @item command.
1710 (insert "\b " (nth 1 (car texinfo-stack)) " \n")
1711 ;; Else text on next line.
1712 (insert "\b " (nth 1 (car texinfo-stack)) " "))
4dd29d03
BP
1713 (forward-line -1))
1714
1715(put 'enumerate 'texinfo-item 'texinfo-enumerate-item)
1716(defun texinfo-enumerate-item ()
7f3e80e3
RS
1717 (texinfo-discard-line)
1718 (let (enumerating-symbol)
1719 (cond ((integerp (car (cdr (car texinfo-stack))))
1720 (setq enumerating-symbol (car (cdr (car texinfo-stack))))
1721 (insert ?\b (format "%3d. " enumerating-symbol) ?\n)
1722 (setcar (cdr (car texinfo-stack)) (1+ enumerating-symbol)))
1723 ((symbolp (car (cdr (car texinfo-stack))))
1724 (setq enumerating-symbol
1725 (symbol-name (car (cdr (car texinfo-stack)))))
1726 (if (or (equal ?\[ (string-to-char enumerating-symbol))
1727 (equal ?\{ (string-to-char enumerating-symbol)))
1728 (error
1729 "Too many items in enumerated list; alphabet ends at Z."))
1730 (insert ?\b (format "%3s. " enumerating-symbol) ?\n)
1731 (setcar (cdr (car texinfo-stack))
1732 (make-symbol
1733 (char-to-string
db95369b 1734 (1+
7f3e80e3
RS
1735 (string-to-char enumerating-symbol))))))
1736 (t
1737 (error
1738 "@enumerate: Use a number or letter, eg: 1, A, a, 3, B or d." )))
1739 (forward-line -1)))
1740
1741(put 'alphaenumerate 'texinfo-item 'texinfo-alphaenumerate-item)
1742(defun texinfo-alphaenumerate-item ()
1743 (texinfo-discard-line)
1744 (let ((next (1+ (car (cdr (car texinfo-stack))))))
1745 (if (> next ?z)
e8af40ee 1746 (error "More than 26 items in @alphaenumerate; get a bigger alphabet"))
7f3e80e3
RS
1747 (setcar (cdr (car texinfo-stack)) next)
1748 (insert "\b " next ". \n"))
1749 (forward-line -1))
1750
1751(put 'capsenumerate 'texinfo-item 'texinfo-capsenumerate-item)
1752(defun texinfo-capsenumerate-item ()
4dd29d03
BP
1753 (texinfo-discard-line)
1754 (let ((next (1+ (car (cdr (car texinfo-stack))))))
7f3e80e3 1755 (if (> next ?Z)
e8af40ee 1756 (error "More than 26 items in @capsenumerate; get a bigger alphabet"))
4dd29d03 1757 (setcar (cdr (car texinfo-stack)) next)
7f3e80e3 1758 (insert "\b " next ". \n"))
4dd29d03
BP
1759 (forward-line -1))
1760
7f3e80e3
RS
1761\f
1762;;; @table
1763
92f62199 1764;; The `@table' command produces two-column tables.
7f3e80e3
RS
1765
1766(put 'table 'texinfo-format 'texinfo-table)
1767(defun texinfo-table ()
db95369b
JB
1768 (texinfo-push-stack
1769 'table
7f3e80e3
RS
1770 (progn (skip-chars-forward " \t")
1771 (if (eolp)
1772 "@asis"
1773 (texinfo-parse-line-arg))))
1774 (texinfo-discard-line-with-args)
1775 (setq fill-column (- fill-column 5)))
1776
4dd29d03
BP
1777(put 'table 'texinfo-item 'texinfo-table-item)
1778(defun texinfo-table-item ()
1779 (let ((arg (texinfo-parse-arg-discard))
7f3e80e3 1780 (itemfont (car (cdr (car texinfo-stack)))))
4dd29d03
BP
1781 (insert ?\b itemfont ?\{ arg "}\n \n"))
1782 (forward-line -2))
1783
7f3e80e3
RS
1784(put 'table 'texinfo-end 'texinfo-end-table)
1785(defun texinfo-end-table ()
1786 (setq fill-column (+ fill-column 5))
1787 (texinfo-discard-command)
1788 (let ((stacktop
1789 (texinfo-pop-stack 'table)))
1790 (texinfo-do-itemize (nth 1 stacktop))))
1791
1792;; @description appears to be an undocumented variant on @table that
1793;; does not require an arg. It fails in texinfo.tex 2.58 and is not
1794;; part of makeinfo.c The command appears to be a relic of the past.
1795(put 'description 'texinfo-end 'texinfo-end-table)
1796(put 'description 'texinfo-format 'texinfo-description)
1797(defun texinfo-description ()
1798 (texinfo-push-stack 'table "@asis")
1799 (setq fill-column (- fill-column 5))
1800 (texinfo-discard-line))
1801
4dd29d03 1802\f
7f3e80e3
RS
1803;;; @ftable, @vtable
1804
92f62199
RS
1805;; The `@ftable' and `@vtable' commands are like the `@table' command
1806;; but they also insert each entry in the first column of the table
1807;; into the function or variable index.
4dd29d03 1808
7f3e80e3 1809;; Handle the @ftable and @vtable commands:
4dd29d03
BP
1810
1811(put 'ftable 'texinfo-format 'texinfo-ftable)
7f3e80e3 1812(put 'vtable 'texinfo-format 'texinfo-vtable)
4dd29d03 1813
7f3e80e3
RS
1814(defun texinfo-ftable () (texinfo-indextable 'ftable))
1815(defun texinfo-vtable () (texinfo-indextable 'vtable))
4dd29d03 1816
7f3e80e3
RS
1817(defun texinfo-indextable (table-type)
1818 (texinfo-push-stack table-type (texinfo-parse-arg-discard))
4dd29d03
BP
1819 (setq fill-column (- fill-column 5)))
1820
7f3e80e3
RS
1821;; Handle the @item commands within ftable and vtable:
1822
4dd29d03 1823(put 'ftable 'texinfo-item 'texinfo-ftable-item)
7f3e80e3
RS
1824(put 'vtable 'texinfo-item 'texinfo-vtable-item)
1825
1826(defun texinfo-ftable-item () (texinfo-indextable-item 'texinfo-findex))
1827(defun texinfo-vtable-item () (texinfo-indextable-item 'texinfo-vindex))
1828
1829(defun texinfo-indextable-item (index-type)
4dd29d03
BP
1830 (let ((item (texinfo-parse-arg-discard))
1831 (itemfont (car (cdr (car texinfo-stack))))
7f3e80e3 1832 (indexvar index-type))
4dd29d03
BP
1833 (insert ?\b itemfont ?\{ item "}\n \n")
1834 (set indexvar
1835 (cons
1836 (list item texinfo-last-node)
1837 (symbol-value indexvar)))
1838 (forward-line -2)))
1839
7f3e80e3
RS
1840;; Handle @end ftable, @end vtable
1841
4dd29d03 1842(put 'ftable 'texinfo-end 'texinfo-end-ftable)
7f3e80e3
RS
1843(put 'vtable 'texinfo-end 'texinfo-end-vtable)
1844
1845(defun texinfo-end-ftable () (texinfo-end-indextable 'ftable))
1846(defun texinfo-end-vtable () (texinfo-end-indextable 'vtable))
1847
1848(defun texinfo-end-indextable (table-type)
4dd29d03
BP
1849 (setq fill-column (+ fill-column 5))
1850 (texinfo-discard-command)
1851 (let ((stacktop
7f3e80e3 1852 (texinfo-pop-stack table-type)))
4dd29d03
BP
1853 (texinfo-do-itemize (nth 1 stacktop))))
1854
1855\f
92f62199
RS
1856;;; @multitable ... @end multitable
1857
1858;; Produce a multi-column table, with as many columns as desired.
1859;;
1860;; A multi-column table has this template:
1861;;
1862;; @multitable {A1} {A2} {A3}
1863;; @item A1 @tab A2 @tab A3
1864;; @item B1 @tab B2 @tab B3
1865;; @item C1 @tab C2 @tab C3
1866;; @end multitable
1867;;
1868;; where the width of the text in brackets specifies the width of the
1869;; respective column.
1870;;
1871;; Or else:
1872;;
1873;; @multitable @columnfractions .25 .3 .45
1874;; @item A1 @tab A2 @tab A3
1875;; @item B1 @tab B2 @tab B3
1876;; @end multitable
1877;;
1878;; where the fractions specify the width of each column as a percent
1879;; of the current width of the text (i.e., of the fill-column).
1880;;
1881;; Long lines of text are filled within columns.
1882;;
db95369b 1883;; Using the Emacs Lisp formatter, texinfmt.el,
92f62199 1884;; the whitespace between columns can be increased by setting
c988a68a 1885;; `texinfo-extra-inter-column-width' to a value greater than 0. By default,
92f62199
RS
1886;; there is at least one blank space between columns.
1887;;
1888;; The Emacs Lisp formatter, texinfmt.el, ignores the following four
1889;; commands that are defined in texinfo.tex for printed output.
db95369b 1890;;
92f62199
RS
1891;; @multitableparskip,
1892;; @multitableparindent,
1893;; @multitablecolmargin,
1894;; @multitablelinespace.
1895
1896;; How @multitable works.
1897;; =====================
db95369b 1898;;
92f62199 1899;; `texinfo-multitable' reads the @multitable line and determines from it
db95369b
JB
1900;; how wide each column should be.
1901;;
92f62199
RS
1902;; Also, it pushes this information, along with an identifying symbol,
1903;; onto the `texinfo-stack'. At the @end multitable command, the stack
1904;; is checked for its matching @multitable command, and then popped, or
1905;; else an error is signaled. Also, this command pushes the location of
1906;; the start of the table onto the stack.
db95369b 1907;;
92f62199
RS
1908;; `texinfo-end-multitable' checks the `texinfo-stack' that the @end
1909;; multitable truly is ending a corresponding beginning, and if it is,
1910;; pops the stack.
db95369b
JB
1911;;
1912;; `texinfo-multitable-widths' is called by `texinfo-multitable'.
92f62199
RS
1913;; The function returns a list of the widths of each column in a
1914;; multi-column table, based on the information supplied by the arguments
1915;; to the @multitable command (by arguments, I mean the text on the rest
1916;; of the @multitable line, not the remainder of the multi-column table
1917;; environment).
db95369b 1918;;
92f62199
RS
1919;; `texinfo-multitable-item' formats a row within a multicolumn table.
1920;; This command is executed when texinfmt sees @item inside @multitable.
1921;; Cells in row are separated by `@tab's. Widths of cells are specified
1922;; by the arguments in the @multitable line. Cells are filled. All cells
1923;; are made to be the same height by padding their bottoms, as needed,
1924;; with blanks.
db95369b
JB
1925;;
1926;; `texinfo-multitable-extract-row' is called by `texinfo-multitable-item'.
92f62199
RS
1927;; This function returns the text in a multitable row, as a string.
1928;; The start of a row is marked by an @item and the end of row is the
1929;; beginning of next @item or beginning of the @end multitable line.
1930;; Cells within a row are separated by @tab.
db95369b 1931;;
92f62199
RS
1932;; Note that @tab, the cell separators, are not treated as independent
1933;; Texinfo commands.
1934
c988a68a
RS
1935(defvar texinfo-extra-inter-column-width 0
1936 "*Number of extra spaces between entries (columns) in @multitable.")
92f62199 1937
c988a68a
RS
1938(defvar texinfo-multitable-buffer-name "*multitable-temporary-buffer*")
1939(defvar texinfo-multitable-rectangle-name "texinfo-multitable-temp-")
92f62199
RS
1940
1941;; These commands are defined in texinfo.tex for printed output.
1942(put 'multitableparskip 'texinfo-format 'texinfo-discard-line-with-args)
1943(put 'multitableparindent 'texinfo-format 'texinfo-discard-line-with-args)
1944(put 'multitablecolmargin 'texinfo-format 'texinfo-discard-line-with-args)
1945(put 'multitablelinespace 'texinfo-format 'texinfo-discard-line-with-args)
1946
1947(put 'multitable 'texinfo-format 'texinfo-multitable)
c988a68a 1948
92f62199
RS
1949(defun texinfo-multitable ()
1950 "Produce multi-column tables.
1951
1952A multi-column table has this template:
1953
1954 @multitable {A1} {A2} {A3}
1955 @item A1 @tab A2 @tab A3
1956 @item B1 @tab B2 @tab B3
1957 @item C1 @tab C2 @tab C3
1958 @end multitable
1959
1960where the width of the text in brackets specifies the width of the
1961respective column.
1962
1963Or else:
1964
1965 @multitable @columnfractions .25 .3 .45
1966 @item A1 @tab A2 @tab A3
1967 @item B1 @tab B2 @tab B3
1968 @end multitable
1969
1970where the fractions specify the width of each column as a percent
1971of the current width of the text (i.e., of the fill-column).
1972
1973Long lines of text are filled within columns.
1974
db95369b 1975Using the Emacs Lisp formatter, texinfmt.el,
92f62199 1976the whitespace between columns can be increased by setting
c988a68a 1977`texinfo-extra-inter-column-width' to a value greater than 0. By default,
92f62199
RS
1978there is at least one blank space between columns.
1979
1980The Emacs Lisp formatter, texinfmt.el, ignores the following four
1981commands that are defined in texinfo.tex for printed output.
1982
1983 @multitableparskip,
1984 @multitableparindent,
1985 @multitablecolmargin,
1986 @multitablelinespace."
1987
1988;; This function pushes information onto the `texinfo-stack'.
1989;; A stack element consists of:
1990;; - type-of-command, i.e., multitable
1991;; - the information about column widths, and
1992;; - the position of texinfo-command-start.
1993;; e.g., ('multitable (1 2 3 4) 123)
1994;; The command line is then deleted.
1995 (texinfo-push-stack
1996 'multitable
1997 ;; push width information on stack
1998 (texinfo-multitable-widths))
1999 (texinfo-discard-line-with-args))
2000
2001(put 'multitable 'texinfo-end 'texinfo-end-multitable)
2002(defun texinfo-end-multitable ()
2003 "Discard the @end multitable line and pop the stack of multitable."
2004 (texinfo-discard-command)
2005 (texinfo-pop-stack 'multitable))
2006
2007(defun texinfo-multitable-widths ()
2008 "Return list of widths of each column in a multi-column table."
2009 (let (texinfo-multitable-width-list)
2010 ;; Fractions format:
2011 ;; @multitable @columnfractions .25 .3 .45
2012 ;;
2013 ;; Template format:
2014 ;; @multitable {Column 1 template} {Column 2} {Column 3 example}
2015 ;; Place point before first argument
2016 (skip-chars-forward " \t")
db95369b 2017 (cond
92f62199
RS
2018 ;; Check for common misspelling
2019 ((looking-at "@columnfraction ")
2020 (error "In @multitable, @columnfractions misspelled"))
2021 ;; Case 1: @columnfractions .25 .3 .45
2022 ((looking-at "@columnfractions")
2023 (forward-word 1)
2024 (while (not (eolp))
2025 (setq texinfo-multitable-width-list
2026 (cons
2027 (truncate
2028 (1-
2029 (* fill-column (read (get-buffer (current-buffer))))))
2030 texinfo-multitable-width-list))))
2031 ;;
2032 ;; Case 2: {Column 1 template} {Column 2} {Column 3 example}
2033 ((looking-at "{")
2034 (let ((start-of-templates (point)))
2035 (while (not (eolp))
2036 (skip-chars-forward " \t")
2037 (let* ((start-of-template (1+ (point)))
2038 (end-of-template
2039 ;; forward-sexp works with braces in Texinfo mode
2040 (progn (forward-sexp 1) (1- (point)))))
2041 (setq texinfo-multitable-width-list
2042 (cons (- end-of-template start-of-template)
2043 texinfo-multitable-width-list))
2044 ;; Remove carriage return from within a template, if any.
2045 ;; This helps those those who want to use more than
2046 ;; one line's worth of words in @multitable line.
2047 (narrow-to-region start-of-template end-of-template)
2048 (goto-char (point-min))
2049 (while (search-forward "
2050" nil t)
2051 (delete-char -1))
2052 (goto-char (point-max))
2053 (widen)
2054 (forward-char 1)))))
2055 ;;
2056 ;; Case 3: Trouble
2057 (t
2058 (error
2059 "You probably need to specify column widths for @multitable correctly.")))
2060 ;; Check whether columns fit on page.
2061 (let ((desired-columns
2062 (+
2063 ;; between column spaces
2064 (length texinfo-multitable-width-list)
2065 ;; additional between column spaces, if any
c988a68a 2066 texinfo-extra-inter-column-width
92f62199
RS
2067 ;; sum of spaces for each entry
2068 (apply '+ texinfo-multitable-width-list))))
2069 (if (> desired-columns fill-column)
2070 (error
2071 (format
2072 "Multi-column table width, %d chars, is greater than page width, %d chars."
2073 desired-columns fill-column))))
2074 texinfo-multitable-width-list))
2075
2076;; @item A1 @tab A2 @tab A3
2077(defun texinfo-multitable-extract-row ()
2078 "Return multitable row, as a string.
2079End of row is beginning of next @item or beginning of @end.
2080Cells within rows are separated by @tab."
2081 (skip-chars-forward " \t")
2082 (let* ((start (point))
2083 (end (progn
2084 (re-search-forward "@item\\|@end")
2085 (match-beginning 0)))
2086 (row (progn (goto-char end)
2087 (skip-chars-backward " ")
2088 ;; remove whitespace at end of argument
2089 (delete-region (point) end)
289df0fc 2090 (buffer-substring-no-properties start (point)))))
92f62199
RS
2091 (delete-region texinfo-command-start end)
2092 row))
2093
2094(put 'multitable 'texinfo-item 'texinfo-multitable-item)
2095(defun texinfo-multitable-item ()
2096 "Format a row within a multicolumn table.
2097Cells in row are separated by @tab.
2098Widths of cells are specified by the arguments in the @multitable line.
2099All cells are made to be the same height.
2100This command is executed when texinfmt sees @item inside @multitable."
2101 (let ((original-buffer (current-buffer))
2102 (table-widths (reverse (car (cdr (car texinfo-stack)))))
2103 (existing-fill-column fill-column)
2104 start
2105 end
2106 (table-column 0)
2107 (table-entry-height 0)
2108 ;; unformatted row looks like: A1 @tab A2 @tab A3
2109 ;; extract-row command deletes the source line in the table.
2110 (unformated-row (texinfo-multitable-extract-row)))
2111 ;; Use a temporary buffer
c988a68a 2112 (set-buffer (get-buffer-create texinfo-multitable-buffer-name))
92f62199
RS
2113 (delete-region (point-min) (point-max))
2114 (insert unformated-row)
2115 (goto-char (point-min))
2116;; 1. Check for correct number of @tab in line.
2117 (let ((tab-number 1)) ; one @tab between two columns
2118 (while (search-forward "@tab" nil t)
2119 (setq tab-number (1+ tab-number)))
2120 (if (/= tab-number (length table-widths))
e8af40ee 2121 (error "Wrong number of @tab's in a @multitable row")))
92f62199
RS
2122 (goto-char (point-min))
2123;; 2. Format each cell, and copy to a rectangle
2124 ;; buffer looks like this: A1 @tab A2 @tab A3
2125 ;; Cell #1: format up to @tab
2126 ;; Cell #2: format up to @tab
2127 ;; Cell #3: format up to eob
2128 (while (not (eobp))
2129 (setq start (point))
2130 (setq end (save-excursion
2131 (if (search-forward "@tab" nil 'move)
2132 ;; Delete the @tab command, including the @-sign
2133 (delete-region
2134 (point)
2135 (progn (forward-word -1) (1- (point)))))
2136 (point)))
2137 ;; Set fill-column *wider* than needed to produce inter-column space
2138 (setq fill-column (+ 1
c988a68a 2139 texinfo-extra-inter-column-width
92f62199
RS
2140 (nth table-column table-widths)))
2141 (narrow-to-region start end)
2142 ;; Remove whitespace before and after entry.
2143 (skip-chars-forward " ")
2144 (delete-region (point) (save-excursion (beginning-of-line) (point)))
2145 (goto-char (point-max))
2146 (skip-chars-backward " ")
2147 (delete-region (point) (save-excursion (end-of-line) (point)))
124ff501 2148 ;; Temporarily set texinfo-stack to nil so texinfo-format-scan
92f62199
RS
2149 ;; does not see an unterminated @multitable.
2150 (let (texinfo-stack) ; nil
2151 (texinfo-format-scan))
2152 (let (fill-prefix) ; no fill prefix
2153 (fill-region (point-min) (point-max)))
2154 (setq table-entry-height
2155 (max table-entry-height (count-lines (point-min) (point-max))))
2156;; 3. Move point to end of bottom line, and pad that line to fill column.
2157 (goto-char (point-min))
2158 (forward-line (1- table-entry-height))
2159 (let* ((beg (point)) ; beginning of line
2160 ;; add one more space for inter-column spacing
2161 (needed-whitespace
2162 (1+
2163 (- fill-column
2164 (-
2165 (progn (end-of-line) (point)) ; end of existing line
2166 beg)))))
2167 (insert (make-string
2168 (if (> needed-whitespace 0) needed-whitespace 1)
2169 ? )))
2170 ;; now, put formatted cell into a rectangle
c988a68a 2171 (set (intern (concat texinfo-multitable-rectangle-name
92f62199
RS
2172 (int-to-string table-column)))
2173 (extract-rectangle (point-min) (point)))
2174 (delete-region (point-min) (point))
2175 (goto-char (point-max))
2176 (setq table-column (1+ table-column))
2177 (widen))
2178;; 4. Add extra lines to rectangles so all are of same height
2179 (let ((total-number-of-columns table-column)
2180 (column-number 0)
2181 here)
2182 (while (> table-column 0)
2183 (let ((this-rectangle (int-to-string table-column)))
2184 (while (< (length this-rectangle) table-entry-height)
2185 (setq this-rectangle (append this-rectangle '("")))))
2186 (setq table-column (1- table-column)))
2187;; 5. Insert formatted rectangles in original buffer
2188 (switch-to-buffer original-buffer)
2189 (open-line table-entry-height)
2190 (while (< column-number total-number-of-columns)
2191 (setq here (point))
2192 (insert-rectangle
2193 (eval (intern
c988a68a 2194 (concat texinfo-multitable-rectangle-name
92f62199
RS
2195 (int-to-string column-number)))))
2196 (goto-char here)
2197 (end-of-line)
2198 (setq column-number (1+ column-number))))
c988a68a 2199 (kill-buffer texinfo-multitable-buffer-name)
92f62199
RS
2200 (setq fill-column existing-fill-column)))
2201
2202\f
d79abb69
RC
2203;;; @image
2204;; Use only the FILENAME argument to the command.
2205;; In Info, ignore the other arguments.
2206
2207(put 'image 'texinfo-format 'texinfo-format-image)
2208(defun texinfo-format-image ()
2209 "Insert an image from an an file ending in .txt.
2210Use only the FILENAME arg; for Info, ignore the other arguments to @image."
2211 (let ((args (texinfo-format-parse-args))
2212 filename)
2213 (when (null (nth 0 args))
2214 (error "Invalid image command"))
2215 (texinfo-discard-command)
2216 ;; makeinfo uses FILENAME.txt
2217 (setq filename (format "%s.txt" (nth 0 args)))
2218 (message "Reading included file: %s" filename)
2219 ;; verbatim for Info output
2220 (goto-char (+ (point) (cadr (insert-file-contents filename))))
2221 (message "Reading included file: %s...done" filename)))
2222
2223\f
a66ccdcf
RC
2224;;; @ifinfo, @iftex, @tex, @ifhtml, @html, @ifplaintext, @ifxml, @xml
2225;; @ifnottex, @ifnotinfo, @ifnothtml, @ifnotplaintext, @ifnotxml
7f3e80e3 2226
4dd29d03
BP
2227(put 'ifinfo 'texinfo-format 'texinfo-discard-line)
2228(put 'ifinfo 'texinfo-end 'texinfo-discard-command)
2229
2230(put 'iftex 'texinfo-format 'texinfo-format-iftex)
2231(defun texinfo-format-iftex ()
2232 (delete-region texinfo-command-start
6147e725 2233 (re-search-forward "@end iftex[ \t]*\n")))
4dd29d03 2234
c5928db2
RS
2235(put 'ifhtml 'texinfo-format 'texinfo-format-ifhtml)
2236(defun texinfo-format-ifhtml ()
2237 (delete-region texinfo-command-start
6147e725 2238 (re-search-forward "@end ifhtml[ \t]*\n")))
c5928db2 2239
2b6a2afe
JB
2240(put 'ifplaintext 'texinfo-format 'texinfo-format-ifplaintext)
2241(defun texinfo-format-ifplaintext ()
2242 (delete-region texinfo-command-start
6147e725 2243 (re-search-forward "@end ifplaintext[ \t]*\n")))
2b6a2afe 2244
a66ccdcf
RC
2245(put 'ifxml 'texinfo-format 'texinfo-format-ifxml)
2246(defun texinfo-format-ifxml ()
2247 (delete-region texinfo-command-start
2248 (progn (re-search-forward "^@end ifxml[ \t]*\n")
2249 (point))))
2250
4dd29d03
BP
2251(put 'tex 'texinfo-format 'texinfo-format-tex)
2252(defun texinfo-format-tex ()
2253 (delete-region texinfo-command-start
6147e725 2254 (re-search-forward "@end tex[ \t]*\n")))
7f3e80e3 2255
c5928db2
RS
2256(put 'html 'texinfo-format 'texinfo-format-html)
2257(defun texinfo-format-html ()
2258 (delete-region texinfo-command-start
6147e725 2259 (re-search-forward "@end html[ \t]*\n")))
c5928db2 2260
a66ccdcf
RC
2261(put 'xml 'texinfo-format 'texinfo-format-xml)
2262(defun texinfo-format-xml ()
2263 (delete-region texinfo-command-start
2264 (progn (re-search-forward "^@end xml[ \t]*\n")
2265 (point))))
2266
25cacfa7
EZ
2267(put 'ifnotinfo 'texinfo-format 'texinfo-format-ifnotinfo)
2268(defun texinfo-format-ifnotinfo ()
2269 (delete-region texinfo-command-start
6147e725 2270 (re-search-forward "@end ifnotinfo[ \t]*\n")))
25cacfa7 2271
2b6a2afe
JB
2272(put 'ifnotplaintext 'texinfo-format 'texinfo-discard-line)
2273(put 'ifnotplaintext 'texinfo-end 'texinfo-discard-command)
2274
7220ca11
KH
2275(put 'ifnottex 'texinfo-format 'texinfo-discard-line)
2276(put 'ifnottex 'texinfo-end 'texinfo-discard-command)
2277
25cacfa7
EZ
2278(put 'ifnothtml 'texinfo-format 'texinfo-discard-line)
2279(put 'ifnothtml 'texinfo-end 'texinfo-discard-command)
2280
a66ccdcf
RC
2281(put 'ifnotxml 'texinfo-format 'texinfo-discard-line)
2282(put 'ifnotxml 'texinfo-end 'texinfo-discard-command)
2283
7f3e80e3
RS
2284\f
2285;;; @titlepage
4dd29d03
BP
2286
2287(put 'titlepage 'texinfo-format 'texinfo-format-titlepage)
2288(defun texinfo-format-titlepage ()
2289 (delete-region texinfo-command-start
6147e725 2290 (re-search-forward "@end titlepage[ \t]*\n")))
4dd29d03
BP
2291
2292(put 'endtitlepage 'texinfo-format 'texinfo-discard-line)
2293
92f62199 2294;; @titlespec an alternative titling command; ignored by Info
4dd29d03
BP
2295
2296(put 'titlespec 'texinfo-format 'texinfo-format-titlespec)
2297(defun texinfo-format-titlespec ()
2298 (delete-region texinfo-command-start
6147e725 2299 (re-search-forward "@end titlespec[ \t]*\n")))
4dd29d03
BP
2300
2301(put 'endtitlespec 'texinfo-format 'texinfo-discard-line)
2302
7f3e80e3
RS
2303\f
2304;;; @today
4dd29d03
BP
2305
2306(put 'today 'texinfo-format 'texinfo-format-today)
2307
92f62199
RS
2308;; Produces Day Month Year style of output. eg `1 Jan 1900'
2309;; The `@today{}' command requires a pair of braces, like `@dots{}'.
4dd29d03
BP
2310(defun texinfo-format-today ()
2311 (texinfo-parse-arg-discard)
a1cfbf35 2312 (insert (format-time-string "%e %b %Y")))
4dd29d03 2313
7f3e80e3 2314\f
92f62199 2315;;; @timestamp{}
db95369b 2316;; Produce `Day Month Year Hour:Min' style of output.
92f62199
RS
2317;; eg `1 Jan 1900 13:52'
2318
2319(put 'timestamp 'texinfo-format 'texinfo-format-timestamp)
2320
2321;; The `@timestamp{}' command requires a pair of braces, like `@dots{}'.
2322(defun texinfo-format-timestamp ()
2323 "Insert the current local time and date."
2324 (texinfo-parse-arg-discard)
2325 ;; For seconds and time zone, replace format string with "%e %b %Y %T %Z"
2326 (insert (format-time-string "%e %b %Y %R")))
2327
2328\f
7f3e80e3 2329;;; @ignore
4dd29d03
BP
2330
2331(put 'ignore 'texinfo-format 'texinfo-format-ignore)
2332(defun texinfo-format-ignore ()
2333 (delete-region texinfo-command-start
6147e725 2334 (re-search-forward "@end ignore[ \t]*\n")))
4dd29d03
BP
2335
2336(put 'endignore 'texinfo-format 'texinfo-discard-line)
2337
7f3e80e3
RS
2338\f
2339;;; Define the Info enclosure command: @definfoenclose
2340
92f62199
RS
2341;; A `@definfoenclose' command may be used to define a highlighting
2342;; command for Info, but not for TeX. A command defined using
2343;; `@definfoenclose' marks text by enclosing it in strings that precede
2344;; and follow the text.
db95369b 2345;;
92f62199
RS
2346;; Presumably, if you define a command with `@definfoenclose` for Info,
2347;; you will also define the same command in the TeX definitions file,
2348;; `texinfo.tex' in a manner appropriate for typesetting.
db95369b 2349;;
92f62199
RS
2350;; Write a `@definfoenclose' command on a line and follow it with three
2351;; arguments separated by commas (commas are used as separators in an
2352;; `@node' line in the same way). The first argument to
2353;; `@definfoenclose' is the @-command name \(without the `@'\); the
2354;; second argument is the Info start delimiter string; and the third
2355;; argument is the Info end delimiter string. The latter two arguments
2356;; enclose the highlighted text in the Info file. A delimiter string
2357;; may contain spaces. Neither the start nor end delimiter is
2358;; required. However, if you do not provide a start delimiter, you
2359;; must follow the command name with two commas in a row; otherwise,
2360;; the Info formatting commands will misinterpret the end delimiter
2361;; string as a start delimiter string.
2362;;
2363;; If you do a @definfoenclose{} on the name of a pre-defined macro (such
2364;; as @emph{}, @strong{}, @tt{}, or @i{}) the enclosure definition will
2365;; override the built-in definition.
db95369b 2366;;
92f62199
RS
2367;; An enclosure command defined this way takes one argument in braces.
2368;;
2369;; For example, you can write:
2370;;
2371;; @ifinfo
2372;; @definfoenclose phoo, //, \\
2373;; @end ifinfo
2374;;
2375;; near the beginning of a Texinfo file at the beginning of the lines
2376;; to define `@phoo' as an Info formatting command that inserts `//'
2377;; before and `\\' after the argument to `@phoo'. You can then write
2378;; `@phoo{bar}' wherever you want `//bar\\' highlighted in Info.
2379;;
db95369b 2380;; Also, for TeX formatting, you could write
92f62199
RS
2381;;
2382;; @iftex
2383;; @global@let@phoo=@i
2384;; @end iftex
2385;;
2386;; to define `@phoo' as a command that causes TeX to typeset
2387;; the argument to `@phoo' in italics.
2388;;
2389;; Note that each definition applies to its own formatter: one for TeX,
2390;; the other for texinfo-format-buffer or texinfo-format-region.
2391;;
2392;; Here is another example: write
2393;;
2394;; @definfoenclose headword, , :
2395;;
2396;; near the beginning of the file, to define `@headword' as an Info
2397;; formatting command that inserts nothing before and a colon after the
2398;; argument to `@headword'.
7f3e80e3
RS
2399
2400(put 'definfoenclose 'texinfo-format 'texinfo-define-info-enclosure)
2401(defun texinfo-define-info-enclosure ()
2402 (let* ((args (texinfo-format-parse-line-args))
2403 (command-name (nth 0 args))
2404 (beginning-delimiter (or (nth 1 args) ""))
2405 (end-delimiter (or (nth 2 args) "")))
2406 (texinfo-discard-command)
2407 (setq texinfo-enclosure-list
2408 (cons
2409 (list command-name
2410 (list
2411 beginning-delimiter
2412 end-delimiter))
2413 texinfo-enclosure-list))))
2414
2415\f
8d66d13d
RS
2416;;; @alias
2417
2418(put 'alias 'texinfo-format 'texinfo-alias)
2419(defun texinfo-alias ()
2420 (let ((start (1- (point)))
2421 args)
2422 (skip-chars-forward " ")
2423 (save-excursion (end-of-line) (setq texinfo-command-end (point)))
2424 (if (not (looking-at "\\([^=]+\\)=\\(.*\\)"))
2425 (error "Invalid alias command")
2426 (setq texinfo-alias-list
2427 (cons
2428 (cons
6147e725
SM
2429 (match-string-no-properties 1)
2430 (match-string-no-properties 2))
8d66d13d
RS
2431 texinfo-alias-list))
2432 (texinfo-discard-command))
2433 )
2434 )
2435
2436\f
7f3e80e3
RS
2437;;; @var, @code and the like
2438
4dd29d03 2439(put 'var 'texinfo-format 'texinfo-format-var)
92f62199 2440;; @sc a small caps font for TeX; formatted as `var' in Info
4dd29d03 2441(put 'sc 'texinfo-format 'texinfo-format-var)
1c87ab31
RS
2442;; @acronym for abbreviations in all caps, such as `NASA'.
2443;; Convert all letters to uppercase if they are not already.
2444(put 'acronym 'texinfo-format 'texinfo-format-var)
4dd29d03 2445(defun texinfo-format-var ()
69c6eff8
RS
2446 (let ((arg (texinfo-parse-expanded-arg)))
2447 (texinfo-discard-command)
2448 (insert (upcase arg))))
4dd29d03 2449
7f3e80e3 2450(put 'cite 'texinfo-format 'texinfo-format-code)
4dd29d03 2451(put 'code 'texinfo-format 'texinfo-format-code)
1c87ab31
RS
2452;; @command (for command names)
2453(put 'command 'texinfo-format 'texinfo-format-code)
2454;; @env (for environment variables)
2455(put 'env 'texinfo-format 'texinfo-format-code)
4dd29d03 2456(put 'file 'texinfo-format 'texinfo-format-code)
7f3e80e3 2457(put 'samp 'texinfo-format 'texinfo-format-code)
1c87ab31 2458(put 'url 'texinfo-format 'texinfo-format-code)
4dd29d03
BP
2459(defun texinfo-format-code ()
2460 (insert "`" (texinfo-parse-arg-discard) "'")
2461 (goto-char texinfo-command-start))
2462
1c87ab31
RS
2463;; @option (for command-line options) must be different from @code
2464;; because of its special formatting in @table; namely that it does
2465;; not lead to inserted ` ... ' in a table, but does elsewhere.
2466(put 'option 'texinfo-format 'texinfo-format-option)
2467(defun texinfo-format-option ()
2468 "Insert ` ... ' around arg unless inside a table; in that case, no quotes."
2469 ;; `looking-at-backward' not available in v. 18.57, 20.2
2470 (if (not (search-backward "\b" ; searched-for character is a control-H
2471 (save-excursion (beginning-of-line) (point))
2472 t))
2473 (insert "`" (texinfo-parse-arg-discard) "'")
2474 (insert (texinfo-parse-arg-discard)))
2475 (goto-char texinfo-command-start))
2476
4dd29d03
BP
2477(put 'emph 'texinfo-format 'texinfo-format-emph)
2478(put 'strong 'texinfo-format 'texinfo-format-emph)
2479(defun texinfo-format-emph ()
2480 (insert "*" (texinfo-parse-arg-discard) "*")
2481 (goto-char texinfo-command-start))
2482
4dd29d03 2483(put 'dfn 'texinfo-format 'texinfo-format-defn)
7f3e80e3 2484(put 'defn 'texinfo-format 'texinfo-format-defn)
4dd29d03
BP
2485(defun texinfo-format-defn ()
2486 (insert "\"" (texinfo-parse-arg-discard) "\"")
2487 (goto-char texinfo-command-start))
2488
8bb6eb14
GM
2489(put 'email 'texinfo-format 'texinfo-format-email)
2490(defun texinfo-format-email ()
2491 "Format email address and optional following full name.
2492Insert full name, if present, followed by email address
2493surrounded by in angle brackets."
2494 (let ((args (texinfo-format-parse-args)))
2495 (texinfo-discard-command)
2496 ;; if full-name
2497 (if (nth 1 args)
2498 (insert (nth 1 args) " "))
2499 (insert "<" (nth 0 args) ">")))
2500
92f62199 2501(put 'key 'texinfo-format 'texinfo-format-key)
c988a68a 2502;; I've decided not want to have angle brackets around these -- rms.
92f62199 2503(defun texinfo-format-key ()
c988a68a 2504 (insert (texinfo-parse-arg-discard))
92f62199
RS
2505 (goto-char texinfo-command-start))
2506
d79abb69
RC
2507;; @verb{<char>TEXT<char>} (in `makeinfo' 4.1 and later)
2508(put 'verb 'texinfo-format 'texinfo-format-verb)
2509(defun texinfo-format-verb ()
2510 "Format text between non-quoted unique delimiter characters verbatim.
2511Enclose the verbatim text, including the delimiters, in braces. Print
2512text exactly as written (but not the delimiters) in a fixed-width.
2513
db95369b 2514For example, @verb\{|@|\} results in @ and
d79abb69
RC
2515@verb\{+@'e?`!`+} results in @'e?`!`."
2516
2517 (let ((delimiter (buffer-substring-no-properties
2518 (1+ texinfo-command-end) (+ 2 texinfo-command-end))))
2519 (unless (looking-at "{")
2520 (error "Not found: @verb start brace"))
2521 (delete-region texinfo-command-start (+ 2 texinfo-command-end))
2522 (search-forward delimiter))
2523 (delete-backward-char 1)
2524 (unless (looking-at "}")
2525 (error "Not found: @verb end brace"))
2526 (delete-char 1))
2527
2528;; as of 2002 Dec 10
2529;; see (texinfo)Block Enclosing Commands
2530;; need: @verbatim
2531
2532;; as of 2002 Dec 10
2533;; see (texinfo)verbatiminclude
2534;; need: @verbatiminclude FILENAME
2535
4dd29d03
BP
2536(put 'bullet 'texinfo-format 'texinfo-format-bullet)
2537(defun texinfo-format-bullet ()
2538 "Insert an asterisk.
2539If used within a line, follow `@bullet' with braces."
2540 (texinfo-optional-braces-discard)
2541 (insert "*"))
2542
7f3e80e3 2543\f
92f62199
RS
2544;;; @kbd
2545
db95369b 2546;; Inside of @example ... @end example and similar environments,
92f62199 2547;; @kbd does nothing; but outside of such environments, it places
124ff501 2548;; single quotation marks around its argument.
92f62199
RS
2549
2550(defvar texinfo-format-kbd-regexp
2551 (concat
2552 "^@"
2553 "\\("
8bb6eb14 2554 "display\\|"
92f62199
RS
2555 "example\\|"
2556 "smallexample\\|"
2557 "lisp\\|"
2558 "smalllisp"
2559 "\\)")
2560 "Regexp specifying environments in which @kbd does not put `...'
2561 around argument.")
2562
2563(defvar texinfo-format-kbd-end-regexp
2564 (concat
2565 "^@end "
2566 "\\("
8bb6eb14 2567 "display\\|"
92f62199
RS
2568 "example\\|"
2569 "smallexample\\|"
2570 "lisp\\|"
2571 "smalllisp"
2572 "\\)")
2573 "Regexp specifying end of environments in which @kbd does not put `...'
2574 around argument. (See `texinfo-format-kbd-regexp')")
2575
2576(put 'kbd 'texinfo-format 'texinfo-format-kbd)
2577(defun texinfo-format-kbd ()
2578 "Place single quote marks around arg, except in @example and similar."
2579 ;; Search forward for @end example closer than an @example.
2580 ;; Can stop search at nearest @node or texinfo-section-types-regexp
db95369b 2581 (let* ((stop
92f62199
RS
2582 (save-excursion
2583 (re-search-forward
2584 (concat "^@node\\|\\(" texinfo-section-types-regexp "\\)")
2585 nil
2586 'move-to-end) ; if necessary, return point at end of buffer
2587 (point)))
2588 (example-location
2589 (save-excursion
2590 (re-search-forward texinfo-format-kbd-regexp stop 'move-to-end)
2591 (point)))
2592 (end-example-location
2593 (save-excursion
2594 (re-search-forward texinfo-format-kbd-end-regexp stop 'move-to-end)
2595 (point))))
2596 ;; If inside @example, @end example will be closer than @example
2597 ;; or end of search i.e., end-example-location less than example-location
2598 (if (>= end-example-location example-location)
2599 ;; outside an @example or equivalent
2600 (insert "`" (texinfo-parse-arg-discard) "'")
2601 ;; else, in @example; do not surround with `...'
2602 (insert (texinfo-parse-arg-discard)))
2603 (goto-char texinfo-command-start)))
2604
2605\f
1c87ab31
RS
2606;;; @example, @lisp, @quotation, @display, @smalllisp, @smallexample,
2607;; @smalldisplay
7f3e80e3
RS
2608
2609(put 'display 'texinfo-format 'texinfo-format-example)
1c87ab31 2610(put 'smalldisplay 'texinfo-format 'texinfo-format-example)
4dd29d03 2611(put 'example 'texinfo-format 'texinfo-format-example)
4dd29d03 2612(put 'lisp 'texinfo-format 'texinfo-format-example)
7f3e80e3
RS
2613(put 'quotation 'texinfo-format 'texinfo-format-example)
2614(put 'smallexample 'texinfo-format 'texinfo-format-example)
2615(put 'smalllisp 'texinfo-format 'texinfo-format-example)
4dd29d03
BP
2616(defun texinfo-format-example ()
2617 (texinfo-push-stack 'example nil)
2618 (setq fill-column (- fill-column 5))
2619 (texinfo-discard-line))
2620
4dd29d03 2621(put 'example 'texinfo-end 'texinfo-end-example)
4dd29d03 2622(put 'display 'texinfo-end 'texinfo-end-example)
1c87ab31 2623(put 'smalldisplay 'texinfo-end 'texinfo-end-example)
7f3e80e3
RS
2624(put 'lisp 'texinfo-end 'texinfo-end-example)
2625(put 'quotation 'texinfo-end 'texinfo-end-example)
2626(put 'smallexample 'texinfo-end 'texinfo-end-example)
2627(put 'smalllisp 'texinfo-end 'texinfo-end-example)
4dd29d03
BP
2628(defun texinfo-end-example ()
2629 (setq fill-column (+ fill-column 5))
2630 (texinfo-discard-command)
2631 (let ((stacktop
7f3e80e3 2632 (texinfo-pop-stack 'example)))
4dd29d03
BP
2633 (texinfo-do-itemize (nth 1 stacktop))))
2634
2635(put 'exdent 'texinfo-format 'texinfo-format-exdent)
2636(defun texinfo-format-exdent ()
2637 (texinfo-discard-command)
2638 (delete-region (point)
7f3e80e3
RS
2639 (progn
2640 (skip-chars-forward " ")
2641 (point)))
4dd29d03
BP
2642 (insert ?\b)
2643 ;; Cancel out the deletion that texinfo-do-itemize
2644 ;; is going to do at the end of this line.
2645 (save-excursion
2646 (end-of-line)
2647 (insert "\n ")))
2648
2649\f
149f002e
RS
2650;; @direntry and @dircategory
2651
2652(put 'direntry 'texinfo-format 'texinfo-format-direntry)
2653(defun texinfo-format-direntry ()
2654 (texinfo-push-stack 'direntry nil)
2655 (texinfo-discard-line)
95012c62 2656 (insert "START-INFO-DIR-ENTRY\n"))
149f002e
RS
2657
2658(put 'direntry 'texinfo-end 'texinfo-end-direntry)
2659(defun texinfo-end-direntry ()
2660 (texinfo-discard-command)
caf4bf36 2661 (insert "END-INFO-DIR-ENTRY\n\n")
149f002e
RS
2662 (texinfo-pop-stack 'direntry))
2663
2664(put 'dircategory 'texinfo-format 'texinfo-format-dircategory)
2665(defun texinfo-format-dircategory ()
caf4bf36
RS
2666 (let ((str (texinfo-parse-arg-discard)))
2667 (delete-region (point)
1c87ab31
RS
2668 (progn
2669 (skip-chars-forward " ")
2670 (point)))
caf4bf36 2671 (insert "INFO-DIR-SECTION " str "\n")))
149f002e 2672\f
db95369b 2673;;; @cartouche
7f3e80e3 2674
92f62199
RS
2675;; The @cartouche command is a noop in Info; in a printed manual,
2676;; it makes a box with rounded corners.
7f3e80e3
RS
2677
2678(put 'cartouche 'texinfo-format 'texinfo-discard-line)
2679(put 'cartouche 'texinfo-end 'texinfo-discard-command)
2680
2681\f
2682;;; @flushleft and @format
2683
92f62199
RS
2684;; The @flushleft command left justifies every line but leaves the
2685;; right end ragged. As far as Info is concerned, @flushleft is a
2686;; `do-nothing' command
7f3e80e3 2687
92f62199
RS
2688;; The @format command is similar to @example except that it does not
2689;; indent; this means that in Info, @format is similar to @flushleft.
7f3e80e3
RS
2690
2691(put 'format 'texinfo-format 'texinfo-format-flushleft)
1c87ab31 2692(put 'smallformat 'texinfo-format 'texinfo-format-flushleft)
7f3e80e3
RS
2693(put 'flushleft 'texinfo-format 'texinfo-format-flushleft)
2694(defun texinfo-format-flushleft ()
2695 (texinfo-discard-line))
2696
2697(put 'format 'texinfo-end 'texinfo-end-flushleft)
1c87ab31 2698(put 'smallformat 'texinfo-end 'texinfo-end-flushleft)
7f3e80e3
RS
2699(put 'flushleft 'texinfo-end 'texinfo-end-flushleft)
2700(defun texinfo-end-flushleft ()
2701 (texinfo-discard-command))
2702
2703\f
2704;;; @flushright
4dd29d03 2705
92f62199
RS
2706;; The @flushright command right justifies every line but leaves the
2707;; left end ragged. Spaces and tabs at the right ends of lines are
2708;; removed so that visible text lines up on the right side.
4dd29d03
BP
2709
2710(put 'flushright 'texinfo-format 'texinfo-format-flushright)
2711(defun texinfo-format-flushright ()
2712 (texinfo-push-stack 'flushright nil)
2713 (texinfo-discard-line))
2714
2715(put 'flushright 'texinfo-end 'texinfo-end-flushright)
2716(defun texinfo-end-flushright ()
2717 (texinfo-discard-command)
2718
2719 (let ((stacktop
2720 (texinfo-pop-stack 'flushright)))
2721
2722 (texinfo-do-flushright (nth 1 stacktop))))
2723
2724(defun texinfo-do-flushright (from)
2725 (save-excursion
2726 (while (progn (forward-line -1)
2727 (>= (point) from))
2728
2729 (beginning-of-line)
2730 (insert
2731 (make-string
2732 (- fill-column
2733 (save-excursion
db95369b 2734 (end-of-line)
7f3e80e3
RS
2735 (skip-chars-backward " \t")
2736 (delete-region (point) (progn (end-of-line) (point)))
db95369b 2737 (current-column)))
4dd29d03
BP
2738 ? )))))
2739
2740\f
92f62199 2741;;; @ctrl, @TeX, @copyright, @minus, @dots, @enddots, @pounds
7f3e80e3 2742
4dd29d03
BP
2743(put 'ctrl 'texinfo-format 'texinfo-format-ctrl)
2744(defun texinfo-format-ctrl ()
2745 (let ((str (texinfo-parse-arg-discard)))
2746 (insert (logand 31 (aref str 0)))))
2747
2748(put 'TeX 'texinfo-format 'texinfo-format-TeX)
2749(defun texinfo-format-TeX ()
2750 (texinfo-parse-arg-discard)
2751 (insert "TeX"))
2752
2753(put 'copyright 'texinfo-format 'texinfo-format-copyright)
2754(defun texinfo-format-copyright ()
2755 (texinfo-parse-arg-discard)
2756 (insert "(C)"))
2757
2758(put 'minus 'texinfo-format 'texinfo-format-minus)
2759(defun texinfo-format-minus ()
2760 "Insert a minus sign.
2761If used within a line, follow `@minus' with braces."
2762 (texinfo-optional-braces-discard)
2763 (insert "-"))
2764
2765(put 'dots 'texinfo-format 'texinfo-format-dots)
2766(defun texinfo-format-dots ()
2767 (texinfo-parse-arg-discard)
2768 (insert "..."))
2769
c5928db2
RS
2770(put 'enddots 'texinfo-format 'texinfo-format-enddots)
2771(defun texinfo-format-enddots ()
2772 (texinfo-parse-arg-discard)
2773 (insert "...."))
2774
92f62199
RS
2775(put 'pounds 'texinfo-format 'texinfo-format-pounds)
2776(defun texinfo-format-pounds ()
2777 (texinfo-parse-arg-discard)
2778 (insert "#"))
2779
7f3e80e3
RS
2780\f
2781;;; Refilling and indenting: @refill, @paragraphindent, @noindent
2782
2783;;; Indent only those paragraphs that are refilled as a result of an
db95369b 2784;;; @refill command.
7f3e80e3 2785
92f62199
RS
2786;; * If the value is `asis', do not change the existing indentation at
2787;; the starts of paragraphs.
7f3e80e3 2788
92f62199 2789;; * If the value zero, delete any existing indentation.
7f3e80e3 2790
92f62199
RS
2791;; * If the value is greater than zero, indent each paragraph by that
2792;; number of spaces.
7f3e80e3
RS
2793
2794;;; But do not refill paragraphs with an @refill command that are
2795;;; preceded by @noindent or are part of a table, list, or deffn.
2796
2797(defvar texinfo-paragraph-indent "asis"
2798 "Number of spaces for @refill to indent a paragraph; else to leave as is.")
2799
2800(put 'paragraphindent 'texinfo-format 'texinfo-paragraphindent)
2801
2802(defun texinfo-paragraphindent ()
2803 "Specify the number of spaces for @refill to indent a paragraph.
2804Default is to leave the number of spaces as is."
2805 (let ((arg (texinfo-parse-arg-discard)))
2806 (if (string= "asis" arg)
2807 (setq texinfo-paragraph-indent "asis")
2808 (setq texinfo-paragraph-indent (string-to-int arg)))))
2809
4dd29d03
BP
2810(put 'refill 'texinfo-format 'texinfo-format-refill)
2811(defun texinfo-format-refill ()
7f3e80e3
RS
2812 "Refill paragraph. Also, indent first line as set by @paragraphindent.
2813Default is to leave paragraph indentation as is."
4dd29d03 2814 (texinfo-discard-command)
f66f0ee8 2815 (let ((position (point-marker)))
db95369b 2816 (forward-paragraph -1)
f66f0ee8
KH
2817 (if (looking-at "[ \t\n]*$") (forward-line 1))
2818 ;; Do not indent if an entry in a list, table, or deffn,
2819 ;; or if paragraph is preceded by @noindent.
2820 ;; Otherwise, indent
db95369b 2821 (cond
f66f0ee8
KH
2822 ;; delete a @noindent line and do not indent paragraph
2823 ((save-excursion (forward-line -1)
db95369b 2824 (looking-at "^@noindent"))
f66f0ee8
KH
2825 (forward-line -1)
2826 (delete-region (point) (progn (forward-line 1) (point))))
2827 ;; do nothing if "asis"
2828 ((equal texinfo-paragraph-indent "asis"))
2829 ;; do no indenting in list, etc.
db95369b 2830 ((> texinfo-stack-depth 0))
f66f0ee8 2831 ;; otherwise delete existing whitespace and indent
db95369b 2832 (t
f66f0ee8
KH
2833 (delete-region (point) (progn (skip-chars-forward " \t") (point)))
2834 (insert (make-string texinfo-paragraph-indent ? ))))
db95369b 2835 (forward-paragraph 1)
7f3e80e3 2836 (forward-line -1)
f66f0ee8
KH
2837 (end-of-line)
2838 ;; Do not fill a section title line with asterisks, hyphens, etc. that
2839 ;; are used to underline it. This could occur if the line following
2840 ;; the underlining is not an index entry and has text within it.
2841 (let* ((previous-paragraph-separate paragraph-separate)
2842 (paragraph-separate
2843 (concat paragraph-separate "\\|[-=.]+\\|\\*\\*+"))
2844 (previous-paragraph-start paragraph-start)
db95369b 2845 (paragraph-start
f66f0ee8
KH
2846 (concat paragraph-start "\\|[-=.]+\\|\\*\\*+")))
2847 (unwind-protect
2848 (fill-paragraph nil)
2849 (setq paragraph-separate previous-paragraph-separate)
2850 (setq paragraph-start previous-paragraph-start)))
2851 (goto-char position)))
7f3e80e3
RS
2852
2853(put 'noindent 'texinfo-format 'texinfo-noindent)
db95369b
JB
2854(defun texinfo-noindent ()
2855 (save-excursion
7f3e80e3
RS
2856 (forward-paragraph 1)
2857 (if (search-backward "@refill"
2858 (save-excursion (forward-line -1) (point)) t)
2859 () ; leave @noindent command so @refill command knows not to indent
2860 ;; else
2861 (texinfo-discard-line))))
4dd29d03
BP
2862
2863\f
2864;;; Index generation
2865
2866(put 'vindex 'texinfo-format 'texinfo-format-vindex)
2867(defun texinfo-format-vindex ()
2868 (texinfo-index 'texinfo-vindex))
2869
2870(put 'cindex 'texinfo-format 'texinfo-format-cindex)
2871(defun texinfo-format-cindex ()
2872 (texinfo-index 'texinfo-cindex))
2873
2874(put 'findex 'texinfo-format 'texinfo-format-findex)
2875(defun texinfo-format-findex ()
2876 (texinfo-index 'texinfo-findex))
2877
2878(put 'pindex 'texinfo-format 'texinfo-format-pindex)
2879(defun texinfo-format-pindex ()
2880 (texinfo-index 'texinfo-pindex))
2881
2882(put 'tindex 'texinfo-format 'texinfo-format-tindex)
2883(defun texinfo-format-tindex ()
2884 (texinfo-index 'texinfo-tindex))
2885
2886(put 'kindex 'texinfo-format 'texinfo-format-kindex)
2887(defun texinfo-format-kindex ()
2888 (texinfo-index 'texinfo-kindex))
2889
2890(defun texinfo-index (indexvar)
2891 (let ((arg (texinfo-parse-expanded-arg)))
2892 (texinfo-discard-command)
2893 (set indexvar
7f3e80e3
RS
2894 (cons (list arg
2895 texinfo-last-node
2896 ;; Region formatting may not provide last node position.
2897 (if texinfo-last-node-pos
2898 (1+ (count-lines texinfo-last-node-pos (point)))
2899 1))
2900 (symbol-value indexvar)))))
4dd29d03 2901
62c2539e 2902(defvar texinfo-indexvar-alist
4dd29d03
BP
2903 '(("cp" . texinfo-cindex)
2904 ("fn" . texinfo-findex)
2905 ("vr" . texinfo-vindex)
2906 ("tp" . texinfo-tindex)
2907 ("pg" . texinfo-pindex)
2908 ("ky" . texinfo-kindex)))
2909
2910\f
2911;;; @defindex @defcodeindex
2912(put 'defindex 'texinfo-format 'texinfo-format-defindex)
2913(put 'defcodeindex 'texinfo-format 'texinfo-format-defindex)
2914
2915(defun texinfo-format-defindex ()
2916 (let* ((index-name (texinfo-parse-arg-discard)) ; eg: `aa'
2917 (indexing-command (intern (concat index-name "index")))
2918 (index-formatting-command ; eg: `texinfo-format-aaindex'
2919 (intern (concat "texinfo-format-" index-name "index")))
2920 (index-alist-name ; eg: `texinfo-aaindex'
2921 (intern (concat "texinfo-" index-name "index"))))
2922
2923 (set index-alist-name nil)
2924
2925 (put indexing-command ; eg, aaindex
2926 'texinfo-format
2927 index-formatting-command) ; eg, texinfo-format-aaindex
2928
2929 ;; eg: "aa" . texinfo-aaindex
2930 (or (assoc index-name texinfo-indexvar-alist)
2931 (setq texinfo-indexvar-alist
2932 (cons
2933 (cons index-name
2934 index-alist-name)
2935 texinfo-indexvar-alist)))
2936
2937 (fset index-formatting-command
2938 (list 'lambda 'nil
db95369b 2939 (list 'texinfo-index
4dd29d03
BP
2940 (list 'quote index-alist-name))))))
2941
2942\f
2943;;; @synindex @syncodeindex
2944
2945(put 'synindex 'texinfo-format 'texinfo-format-synindex)
2946(put 'syncodeindex 'texinfo-format 'texinfo-format-synindex)
2947
2948(defun texinfo-format-synindex ()
2949 (let* ((args (texinfo-parse-arg-discard))
2950 (second (cdr (read-from-string args)))
2951 (joiner (symbol-name (car (read-from-string args))))
2952 (joined (symbol-name (car (read-from-string args second)))))
2953
2954 (if (assoc joiner texinfo-short-index-cmds-alist)
2955 (put
2956 (cdr (assoc joiner texinfo-short-index-cmds-alist))
2957 'texinfo-format
2958 (or (cdr (assoc joined texinfo-short-index-format-cmds-alist))
2959 (intern (concat "texinfo-format-" joined "index"))))
2960 (put
2961 (intern (concat joiner "index"))
2962 'texinfo-format
2963 (or (cdr(assoc joined texinfo-short-index-format-cmds-alist))
2964 (intern (concat "texinfo-format-" joined "index")))))))
2965
2966(defconst texinfo-short-index-cmds-alist
2967 '(("cp" . cindex)
2968 ("fn" . findex)
2969 ("vr" . vindex)
2970 ("tp" . tindex)
2971 ("pg" . pindex)
2972 ("ky" . kindex)))
2973
2974(defconst texinfo-short-index-format-cmds-alist
2975 '(("cp" . texinfo-format-cindex)
2976 ("fn" . texinfo-format-findex)
2977 ("vr" . texinfo-format-vindex)
2978 ("tp" . texinfo-format-tindex)
2979 ("pg" . texinfo-format-pindex)
2980 ("ky" . texinfo-format-kindex)))
2981
2982\f
7f3e80e3
RS
2983;;; Sort and index (for VMS)
2984
2985;; Sort an index which is in the current buffer between START and END.
2986;; Used on VMS, where the `sort' utility is not available.
2987(defun texinfo-sort-region (start end)
2988 (require 'sort)
2989 (save-restriction
2990 (narrow-to-region start end)
8bb6eb14 2991 (goto-char (point-min))
7f3e80e3
RS
2992 (sort-subr nil 'forward-line 'end-of-line 'texinfo-sort-startkeyfun)))
2993
2994;; Subroutine for sorting an index.
2995;; At start of a line, return a string to sort the line under.
2996(defun texinfo-sort-startkeyfun ()
6147e725 2997 (let ((line (buffer-substring-no-properties (point) (line-end-position))))
7f3e80e3
RS
2998 ;; Canonicalize whitespace and eliminate funny chars.
2999 (while (string-match "[ \t][ \t]+\\|[^a-z0-9 ]+" line)
3000 (setq line (concat (substring line 0 (match-beginning 0))
3001 " "
6147e725 3002 (substring line (match-end 0)))))
7f3e80e3
RS
3003 line))
3004
3005\f
4dd29d03
BP
3006;;; @printindex
3007
3008(put 'printindex 'texinfo-format 'texinfo-format-printindex)
3009
3010(defun texinfo-format-printindex ()
3011 (let ((indexelts (symbol-value
7f3e80e3
RS
3012 (cdr (assoc (texinfo-parse-arg-discard)
3013 texinfo-indexvar-alist))))
3014 opoint)
4dd29d03
BP
3015 (insert "\n* Menu:\n\n")
3016 (setq opoint (point))
3017 (texinfo-print-index nil indexelts)
3018
b53e01dc 3019 (if (memq system-type '(vax-vms windows-nt ms-dos))
4dd29d03
BP
3020 (texinfo-sort-region opoint (point))
3021 (shell-command-on-region opoint (point) "sort -fd" 1))))
3022
3023(defun texinfo-print-index (file indexelts)
3024 (while indexelts
3025 (if (stringp (car (car indexelts)))
7f3e80e3
RS
3026 (progn
3027 (insert "* " (car (car indexelts)) ": " )
3028 (indent-to 32)
3029 (insert
3030 (if file (concat "(" file ")") "")
3031 (nth 1 (car indexelts)) ".")
3032 (indent-to 54)
3033 (insert
3034 (if (nth 2 (car indexelts))
28633019 3035 (format " (line %3d)" (1+ (nth 2 (car indexelts))))
7f3e80e3
RS
3036 "")
3037 "\n"))
4dd29d03
BP
3038 ;; index entries from @include'd file
3039 (texinfo-print-index (nth 1 (car indexelts))
7f3e80e3 3040 (nth 2 (car indexelts))))
4dd29d03
BP
3041 (setq indexelts (cdr indexelts))))
3042
3043\f
7f3e80e3 3044;;; Glyphs: @equiv, @error, etc
4dd29d03
BP
3045
3046;; @equiv to show that two expressions are equivalent
3047;; @error to show an error message
3048;; @expansion to show what a macro expands to
3049;; @point to show the location of point in an example
3050;; @print to show what an evaluated expression prints
3051;; @result to indicate the value returned by an expression
3052
3053(put 'equiv 'texinfo-format 'texinfo-format-equiv)
3054(defun texinfo-format-equiv ()
3055 (texinfo-parse-arg-discard)
3056 (insert "=="))
3057
3058(put 'error 'texinfo-format 'texinfo-format-error)
3059(defun texinfo-format-error ()
3060 (texinfo-parse-arg-discard)
3061 (insert "error-->"))
3062
3063(put 'expansion 'texinfo-format 'texinfo-format-expansion)
3064(defun texinfo-format-expansion ()
3065 (texinfo-parse-arg-discard)
3066 (insert "==>"))
3067
3068(put 'point 'texinfo-format 'texinfo-format-point)
3069(defun texinfo-format-point ()
3070 (texinfo-parse-arg-discard)
3071 (insert "-!-"))
3072
3073(put 'print 'texinfo-format 'texinfo-format-print)
3074(defun texinfo-format-print ()
3075 (texinfo-parse-arg-discard)
3076 (insert "-|"))
3077
3078(put 'result 'texinfo-format 'texinfo-format-result)
3079(defun texinfo-format-result ()
3080 (texinfo-parse-arg-discard)
3081 (insert "=>"))
3082
3083\f
92f62199
RS
3084;;; Accent commands
3085
3086;; Info presumes a plain ASCII output, so the accented characters do
3087;; not look as they would if typeset, or output with a different
3088;; character set.
3089
3090;; See the `texinfo-accent-commands' variable
3091;; in the section for `texinfo-append-refill'.
db95369b 3092;; Also, see the defun for `texinfo-format-scan'
92f62199
RS
3093;; for single-character accent commands.
3094
3095;; Command Info output Name
3096
3097;; These do not have braces:
3098;; @^ ==> ^ circumflex accent
3099;; @` ==> ` grave accent
3100;; @' ==> ' acute accent
3101;; @" ==> " umlaut accent
3102;; @= ==> = overbar accent
3103;; @~ ==> ~ tilde accent
3104
3105;; These have braces, but take no argument:
3106;; @OE{} ==> OE French-OE-ligature
3107;; @oe{} ==> oe
3108;; @AA{} ==> AA Scandinavian-A-with-circle
3109;; @aa{} ==> aa
3110;; @AE{} ==> AE Latin-Scandinavian-AE
3111;; @ae{} ==> ae
3112;; @ss{} ==> ss German-sharp-S
3113
3114;; @questiondown{} ==> ? upside-down-question-mark
3115;; @exclamdown{} ==> ! upside-down-exclamation-mark
3116;; @L{} ==> L/ Polish suppressed-L (Lslash)
3117;; @l{} ==> l/ Polish suppressed-L (Lslash) (lower case)
3118;; @O{} ==> O/ Scandinavian O-with-slash
3119;; @o{} ==> o/ Scandinavian O-with-slash (lower case)
3120
3121;; These have braces, and take an argument:
3122;; @,{c} ==> c, cedilla accent
3123;; @dotaccent{o} ==> .o overdot-accent
3124;; @ubaraccent{o} ==> _o underbar-accent
3125;; @udotaccent{o} ==> o-. underdot-accent
3126;; @H{o} ==> ""o long Hungarian umlaut
3127;; @ringaccent{o} ==> *o ring accent
3128;; @tieaccent{oo} ==> [oo tie after accent
3129;; @u{o} ==> (o breve accent
3130;; @v{o} ==> <o hacek accent
3131;; @dotless{i} ==> i dotless i and dotless j
3132
3133;; ==========
3134
3135;; Note: The defun texinfo-format-scan
3136;; looks at "[@{}^'`\",=~ *?!-]"
db95369b 3137;; In the case of @*, a line break is inserted;
92f62199
RS
3138;; in the other cases, the characters are simply quoted and the @ is deleted.
3139;; Thus, `texinfo-format-scan' handles the following
3140;; single-character accent commands: @^ @` @' @" @, @- @= @~
3141
3142;; @^ ==> ^ circumflex accent
3143;; (put '^ 'texinfo-format 'texinfo-format-circumflex-accent)
3144;; (defun texinfo-format-circumflex-accent ()
3145;; (texinfo-discard-command)
3146;; (insert "^"))
db95369b 3147;;
92f62199
RS
3148;; @` ==> ` grave accent
3149;; (put '\` 'texinfo-format 'texinfo-format-grave-accent)
3150;; (defun texinfo-format-grave-accent ()
3151;; (texinfo-discard-command)
3152;; (insert "\`"))
db95369b 3153;;
92f62199
RS
3154;; @' ==> ' acute accent
3155;; (put '\' 'texinfo-format 'texinfo-format-acute-accent)
3156;; (defun texinfo-format-acute-accent ()
3157;; (texinfo-discard-command)
3158;; (insert "'"))
db95369b 3159;;
92f62199
RS
3160;; @" ==> " umlaut accent
3161;; (put '\" 'texinfo-format 'texinfo-format-umlaut-accent)
3162;; (defun texinfo-format-umlaut-accent ()
3163;; (texinfo-discard-command)
3164;; (insert "\""))
3165;;
3166;; @= ==> = overbar accent
3167;; (put '= 'texinfo-format 'texinfo-format-overbar-accent)
3168;; (defun texinfo-format-overbar-accent ()
3169;; (texinfo-discard-command)
3170;; (insert "="))
db95369b 3171;;
92f62199
RS
3172;; @~ ==> ~ tilde accent
3173;; (put '~ 'texinfo-format 'texinfo-format-tilde-accent)
3174;; (defun texinfo-format-tilde-accent ()
3175;; (texinfo-discard-command)
3176;; (insert "~"))
3177
3178;; @OE{} ==> OE French-OE-ligature
3179(put 'OE 'texinfo-format 'texinfo-format-French-OE-ligature)
3180(defun texinfo-format-French-OE-ligature ()
3181 (insert "OE" (texinfo-parse-arg-discard))
3182 (goto-char texinfo-command-start))
3183
3184;; @oe{} ==> oe
3185(put 'oe 'texinfo-format 'texinfo-format-French-oe-ligature)
3186(defun texinfo-format-French-oe-ligature () ; lower case
3187 (insert "oe" (texinfo-parse-arg-discard))
3188 (goto-char texinfo-command-start))
3189
3190;; @AA{} ==> AA Scandinavian-A-with-circle
3191(put 'AA 'texinfo-format 'texinfo-format-Scandinavian-A-with-circle)
3192(defun texinfo-format-Scandinavian-A-with-circle ()
3193 (insert "AA" (texinfo-parse-arg-discard))
3194 (goto-char texinfo-command-start))
3195
3196;; @aa{} ==> aa
3197(put 'aa 'texinfo-format 'texinfo-format-Scandinavian-a-with-circle)
3198(defun texinfo-format-Scandinavian-a-with-circle () ; lower case
3199 (insert "aa" (texinfo-parse-arg-discard))
3200 (goto-char texinfo-command-start))
3201
3202;; @AE{} ==> AE Latin-Scandinavian-AE
3203(put 'AE 'texinfo-format 'texinfo-format-Latin-Scandinavian-AE)
3204(defun texinfo-format-Latin-Scandinavian-AE ()
3205 (insert "AE" (texinfo-parse-arg-discard))
3206 (goto-char texinfo-command-start))
3207
3208;; @ae{} ==> ae
3209(put 'ae 'texinfo-format 'texinfo-format-Latin-Scandinavian-ae)
3210(defun texinfo-format-Latin-Scandinavian-ae () ; lower case
3211 (insert "ae" (texinfo-parse-arg-discard))
3212 (goto-char texinfo-command-start))
3213
3214;; @ss{} ==> ss German-sharp-S
3215(put 'ss 'texinfo-format 'texinfo-format-German-sharp-S)
3216(defun texinfo-format-German-sharp-S ()
3217 (insert "ss" (texinfo-parse-arg-discard))
3218 (goto-char texinfo-command-start))
3219
3220;; @questiondown{} ==> ? upside-down-question-mark
3221(put 'questiondown 'texinfo-format 'texinfo-format-upside-down-question-mark)
3222(defun texinfo-format-upside-down-question-mark ()
3223 (insert "?" (texinfo-parse-arg-discard))
3224 (goto-char texinfo-command-start))
3225
3226;; @exclamdown{} ==> ! upside-down-exclamation-mark
3227(put 'exclamdown 'texinfo-format 'texinfo-format-upside-down-exclamation-mark)
3228(defun texinfo-format-upside-down-exclamation-mark ()
3229 (insert "!" (texinfo-parse-arg-discard))
3230 (goto-char texinfo-command-start))
3231
3232;; @L{} ==> L/ Polish suppressed-L (Lslash)
3233(put 'L 'texinfo-format 'texinfo-format-Polish-suppressed-L)
3234(defun texinfo-format-Polish-suppressed-L ()
3235 (insert (texinfo-parse-arg-discard) "/L")
3236 (goto-char texinfo-command-start))
3237
3238;; @l{} ==> l/ Polish suppressed-L (Lslash) (lower case)
3239(put 'l 'texinfo-format 'texinfo-format-Polish-suppressed-l-lower-case)
3240(defun texinfo-format-Polish-suppressed-l-lower-case ()
3241 (insert (texinfo-parse-arg-discard) "/l")
3242 (goto-char texinfo-command-start))
3243
3244
3245;; @O{} ==> O/ Scandinavian O-with-slash
3246(put 'O 'texinfo-format 'texinfo-format-Scandinavian-O-with-slash)
3247(defun texinfo-format-Scandinavian-O-with-slash ()
3248 (insert (texinfo-parse-arg-discard) "O/")
3249 (goto-char texinfo-command-start))
3250
3251;; @o{} ==> o/ Scandinavian O-with-slash (lower case)
3252(put 'o 'texinfo-format 'texinfo-format-Scandinavian-o-with-slash-lower-case)
3253(defun texinfo-format-Scandinavian-o-with-slash-lower-case ()
3254 (insert (texinfo-parse-arg-discard) "o/")
3255 (goto-char texinfo-command-start))
3256
3257;; Take arguments
3258
3259;; @,{c} ==> c, cedilla accent
3260(put ', 'texinfo-format 'texinfo-format-cedilla-accent)
3261(defun texinfo-format-cedilla-accent ()
3262 (insert (texinfo-parse-arg-discard) ",")
3263 (goto-char texinfo-command-start))
3264
3265
3266;; @dotaccent{o} ==> .o overdot-accent
3267(put 'dotaccent 'texinfo-format 'texinfo-format-overdot-accent)
3268(defun texinfo-format-overdot-accent ()
3269 (insert "." (texinfo-parse-arg-discard))
3270 (goto-char texinfo-command-start))
3271
3272;; @ubaraccent{o} ==> _o underbar-accent
3273(put 'ubaraccent 'texinfo-format 'texinfo-format-underbar-accent)
3274(defun texinfo-format-underbar-accent ()
3275 (insert "_" (texinfo-parse-arg-discard))
3276 (goto-char texinfo-command-start))
3277
3278;; @udotaccent{o} ==> o-. underdot-accent
3279(put 'udotaccent 'texinfo-format 'texinfo-format-underdot-accent)
3280(defun texinfo-format-underdot-accent ()
3281 (insert (texinfo-parse-arg-discard) "-.")
3282 (goto-char texinfo-command-start))
3283
3284;; @H{o} ==> ""o long Hungarian umlaut
3285(put 'H 'texinfo-format 'texinfo-format-long-Hungarian-umlaut)
3286(defun texinfo-format-long-Hungarian-umlaut ()
3287 (insert "\"\"" (texinfo-parse-arg-discard))
3288 (goto-char texinfo-command-start))
3289
3290;; @ringaccent{o} ==> *o ring accent
3291(put 'ringaccent 'texinfo-format 'texinfo-format-ring-accent)
3292(defun texinfo-format-ring-accent ()
3293 (insert "*" (texinfo-parse-arg-discard))
3294 (goto-char texinfo-command-start))
3295
3296;; @tieaccent{oo} ==> [oo tie after accent
3297(put 'tieaccent 'texinfo-format 'texinfo-format-tie-after-accent)
3298(defun texinfo-format-tie-after-accent ()
3299 (insert "[" (texinfo-parse-arg-discard))
3300 (goto-char texinfo-command-start))
3301
3302
3303;; @u{o} ==> (o breve accent
3304(put 'u 'texinfo-format 'texinfo-format-breve-accent)
3305(defun texinfo-format-breve-accent ()
3306 (insert "(" (texinfo-parse-arg-discard))
3307 (goto-char texinfo-command-start))
3308
3309;; @v{o} ==> <o hacek accent
3310(put 'v 'texinfo-format 'texinfo-format-hacek-accent)
3311(defun texinfo-format-hacek-accent ()
3312 (insert "<" (texinfo-parse-arg-discard))
3313 (goto-char texinfo-command-start))
3314
3315
3316;; @dotless{i} ==> i dotless i and dotless j
3317(put 'dotless 'texinfo-format 'texinfo-format-dotless)
3318(defun texinfo-format-dotless ()
3319 (insert (texinfo-parse-arg-discard))
3320 (goto-char texinfo-command-start))
3321
3322\f
7f3e80e3
RS
3323;;; Definition formatting: @deffn, @defun, etc
3324
3325;; What definition formatting produces:
3326;;
3327;; @deffn category name args...
3328;; In Info, `Category: name ARGS'
3329;; In index: name: node. line#.
3330;;
db95369b 3331;; @defvr category name
7f3e80e3
RS
3332;; In Info, `Category: name'
3333;; In index: name: node. line#.
3334;;
3335;; @deftp category name attributes...
3336;; `category name attributes...' Note: @deftp args in lower case.
3337;; In index: name: node. line#.
3338;;
3339;; Specialized function-like or variable-like entity:
3340;;
3341;; @defun, @defmac, @defspec, @defvar, @defopt
3342;;
3343;; @defun name args In Info, `Function: name ARGS'
3344;; @defmac name args In Info, `Macro: name ARGS'
3345;; @defvar name In Info, `Variable: name'
3346;; etc.
3347;; In index: name: node. line#.
3348;;
3349;; Generalized typed-function-like or typed-variable-like entity:
3350;; @deftypefn category data-type name args...
3351;; In Info, `Category: data-type name args...'
db95369b 3352;; @deftypevr category data-type name
7f3e80e3
RS
3353;; In Info, `Category: data-type name'
3354;; In index: name: node. line#.
3355;;
3356;; Specialized typed-function-like or typed-variable-like entity:
3357;; @deftypefun data-type name args...
3358;; In Info, `Function: data-type name ARGS'
db95369b 3359;; In index: name: node. line#.
7f3e80e3 3360;;
db95369b 3361;; @deftypevar data-type name
7f3e80e3
RS
3362;; In Info, `Variable: data-type name'
3363;; In index: name: node. line#. but include args after name!?
3364;;
db95369b 3365;; Generalized object oriented entity:
7f3e80e3
RS
3366;; @defop category class name args...
3367;; In Info, `Category on class: name ARG'
3368;; In index: name on class: node. line#.
3369;;
db95369b 3370;; @defcv category class name
7f3e80e3
RS
3371;; In Info, `Category of class: name'
3372;; In index: name of class: node. line#.
3373;;
3374;; Specialized object oriented entity:
db95369b 3375;; @defmethod class name args...
7f3e80e3
RS
3376;; In Info, `Method on class: name ARGS'
3377;; In index: name on class: node. line#.
3378;;
3379;; @defivar class name
3380;; In Info, `Instance variable of class: name'
3381;; In index: name of class: node. line#.
3382
3383\f
3384;;; The definition formatting functions
4dd29d03
BP
3385
3386(defun texinfo-format-defun ()
3387 (texinfo-push-stack 'defun nil)
3388 (setq fill-column (- fill-column 5))
3389 (texinfo-format-defun-1 t))
3390
4dd29d03
BP
3391(defun texinfo-end-defun ()
3392 (setq fill-column (+ fill-column 5))
3393 (texinfo-discard-command)
3394 (let ((start (nth 1 (texinfo-pop-stack 'defun))))
3395 (texinfo-do-itemize start)
3396 ;; Delete extra newline inserted after header.
3397 (save-excursion
3398 (goto-char start)
3399 (delete-char -1))))
3400
7f3e80e3
RS
3401(defun texinfo-format-defunx ()
3402 (texinfo-format-defun-1 nil))
4dd29d03 3403
7f3e80e3
RS
3404(defun texinfo-format-defun-1 (first-p)
3405 (let ((parse-args (texinfo-format-parse-defun-args))
64c8498a 3406 (texinfo-defun-type (get texinfo-command-name 'texinfo-defun-type)))
7f3e80e3
RS
3407 (texinfo-discard-command)
3408 ;; Delete extra newline inserted after previous header line.
3409 (if (not first-p)
3410 (delete-char -1))
3411 (funcall
3412 (get texinfo-command-name 'texinfo-deffn-formatting-property) parse-args)
3413 ;; Insert extra newline so that paragraph filling does not mess
3414 ;; with header line.
3415 (insert "\n\n")
3416 (rplaca (cdr (cdr (car texinfo-stack))) (point))
3417 (funcall
3418 (get texinfo-command-name 'texinfo-defun-indexing-property) parse-args)))
3419
3420;;; Formatting the first line of a definition
3421
3422;; @deffn, @defvr, @deftp
3423(put 'deffn 'texinfo-deffn-formatting-property 'texinfo-format-deffn)
3424(put 'deffnx 'texinfo-deffn-formatting-property 'texinfo-format-deffn)
3425(put 'defvr 'texinfo-deffn-formatting-property 'texinfo-format-deffn)
3426(put 'defvrx 'texinfo-deffn-formatting-property 'texinfo-format-deffn)
3427(put 'deftp 'texinfo-deffn-formatting-property 'texinfo-format-deffn)
3428(put 'deftpx 'texinfo-deffn-formatting-property 'texinfo-format-deffn)
3429(defun texinfo-format-deffn (parsed-args)
3430 ;; Generalized function-like, variable-like, or generic data-type entity:
3431 ;; @deffn category name args...
3432 ;; In Info, `Category: name ARGS'
3433 ;; @deftp category name attributes...
3434 ;; `category name attributes...' Note: @deftp args in lower case.
3435 (let ((category (car parsed-args))
3436 (name (car (cdr parsed-args)))
3437 (args (cdr (cdr parsed-args))))
3438 (insert " -- " category ": " name)
3439 (while args
3440 (insert " "
3441 (if (or (= ?& (aref (car args) 0))
64c8498a 3442 (eq (eval (car texinfo-defun-type)) 'deftp-type))
7f3e80e3
RS
3443 (car args)
3444 (upcase (car args))))
3445 (setq args (cdr args)))))
3446
3447;; @defun, @defmac, @defspec, @defvar, @defopt: Specialized, simple
3448(put 'defun 'texinfo-deffn-formatting-property
3449 'texinfo-format-specialized-defun)
3450(put 'defunx 'texinfo-deffn-formatting-property
3451 'texinfo-format-specialized-defun)
3452(put 'defmac 'texinfo-deffn-formatting-property
3453 'texinfo-format-specialized-defun)
3454(put 'defmacx 'texinfo-deffn-formatting-property
3455 'texinfo-format-specialized-defun)
3456(put 'defspec 'texinfo-deffn-formatting-property
3457 'texinfo-format-specialized-defun)
3458(put 'defspecx 'texinfo-deffn-formatting-property
3459 'texinfo-format-specialized-defun)
3460(put 'defvar 'texinfo-deffn-formatting-property
3461 'texinfo-format-specialized-defun)
3462(put 'defvarx 'texinfo-deffn-formatting-property
3463 'texinfo-format-specialized-defun)
3464(put 'defopt 'texinfo-deffn-formatting-property
3465 'texinfo-format-specialized-defun)
3466(put 'defoptx 'texinfo-deffn-formatting-property
3467 'texinfo-format-specialized-defun)
3468(defun texinfo-format-specialized-defun (parsed-args)
3469 ;; Specialized function-like or variable-like entity:
3470 ;; @defun name args In Info, `Function: Name ARGS'
3471 ;; @defmac name args In Info, `Macro: Name ARGS'
3472 ;; @defvar name In Info, `Variable: Name'
64c8498a
RS
3473 ;; Use cdr of texinfo-defun-type to determine category:
3474 (let ((category (car (cdr texinfo-defun-type)))
7f3e80e3
RS
3475 (name (car parsed-args))
3476 (args (cdr parsed-args)))
3477 (insert " -- " category ": " name)
3478 (while args
3479 (insert " "
3480 (if (= ?& (aref (car args) 0))
3481 (car args)
3482 (upcase (car args))))
3483 (setq args (cdr args)))))
3484
3485;; @deftypefn, @deftypevr: Generalized typed
3486(put 'deftypefn 'texinfo-deffn-formatting-property 'texinfo-format-deftypefn)
3487(put 'deftypefnx 'texinfo-deffn-formatting-property 'texinfo-format-deftypefn)
3488(put 'deftypevr 'texinfo-deffn-formatting-property 'texinfo-format-deftypefn)
3489(put 'deftypevrx 'texinfo-deffn-formatting-property 'texinfo-format-deftypefn)
3490(defun texinfo-format-deftypefn (parsed-args)
3491 ;; Generalized typed-function-like or typed-variable-like entity:
3492 ;; @deftypefn category data-type name args...
3493 ;; In Info, `Category: data-type name args...'
db95369b 3494 ;; @deftypevr category data-type name
7f3e80e3
RS
3495 ;; In Info, `Category: data-type name'
3496 ;; Note: args in lower case, unless modified in command line.
3497 (let ((category (car parsed-args))
3498 (data-type (car (cdr parsed-args)))
3499 (name (car (cdr (cdr parsed-args))))
3500 (args (cdr (cdr (cdr parsed-args)))))
3501 (insert " -- " category ": " data-type " " name)
3502 (while args
3503 (insert " " (car args))
3504 (setq args (cdr args)))))
3505
3506;; @deftypefun, @deftypevar: Specialized typed
3507(put 'deftypefun 'texinfo-deffn-formatting-property 'texinfo-format-deftypefun)
3508(put 'deftypefunx 'texinfo-deffn-formatting-property
3509 'texinfo-format-deftypefun)
3510(put 'deftypevar 'texinfo-deffn-formatting-property 'texinfo-format-deftypefun)
3511(put 'deftypevarx 'texinfo-deffn-formatting-property
3512 'texinfo-format-deftypefun)
3513(defun texinfo-format-deftypefun (parsed-args)
3514 ;; Specialized typed-function-like or typed-variable-like entity:
3515 ;; @deftypefun data-type name args...
3516 ;; In Info, `Function: data-type name ARGS'
db95369b 3517 ;; @deftypevar data-type name
7f3e80e3
RS
3518 ;; In Info, `Variable: data-type name'
3519 ;; Note: args in lower case, unless modified in command line.
64c8498a
RS
3520 ;; Use cdr of texinfo-defun-type to determine category:
3521 (let ((category (car (cdr texinfo-defun-type)))
7f3e80e3
RS
3522 (data-type (car parsed-args))
3523 (name (car (cdr parsed-args)))
3524 (args (cdr (cdr parsed-args))))
3525 (insert " -- " category ": " data-type " " name)
3526 (while args
3527 (insert " " (car args))
3528 (setq args (cdr args)))))
3529
3530;; @defop: Generalized object-oriented
3531(put 'defop 'texinfo-deffn-formatting-property 'texinfo-format-defop)
3532(put 'defopx 'texinfo-deffn-formatting-property 'texinfo-format-defop)
3533(defun texinfo-format-defop (parsed-args)
db95369b 3534 ;; Generalized object oriented entity:
7f3e80e3
RS
3535 ;; @defop category class name args...
3536 ;; In Info, `Category on class: name ARG'
3537 ;; Note: args in upper case; use of `on'
3538 (let ((category (car parsed-args))
3539 (class (car (cdr parsed-args)))
3540 (name (car (cdr (cdr parsed-args))))
3541 (args (cdr (cdr (cdr parsed-args)))))
3542 (insert " -- " category " on " class ": " name)
3543 (while args
3544 (insert " " (upcase (car args)))
3545 (setq args (cdr args)))))
3546
3547;; @defcv: Generalized object-oriented
3548(put 'defcv 'texinfo-deffn-formatting-property 'texinfo-format-defcv)
3549(put 'defcvx 'texinfo-deffn-formatting-property 'texinfo-format-defcv)
3550(defun texinfo-format-defcv (parsed-args)
db95369b
JB
3551 ;; Generalized object oriented entity:
3552 ;; @defcv category class name
7f3e80e3
RS
3553 ;; In Info, `Category of class: name'
3554 ;; Note: args in upper case; use of `of'
3555 (let ((category (car parsed-args))
3556 (class (car (cdr parsed-args)))
3557 (name (car (cdr (cdr parsed-args))))
3558 (args (cdr (cdr (cdr parsed-args)))))
3559 (insert " -- " category " of " class ": " name)
3560 (while args
3561 (insert " " (upcase (car args)))
3562 (setq args (cdr args)))))
3563
3564;; @defmethod: Specialized object-oriented
3565(put 'defmethod 'texinfo-deffn-formatting-property 'texinfo-format-defmethod)
3566(put 'defmethodx 'texinfo-deffn-formatting-property 'texinfo-format-defmethod)
3567(defun texinfo-format-defmethod (parsed-args)
3568 ;; Specialized object oriented entity:
db95369b 3569 ;; @defmethod class name args...
7f3e80e3
RS
3570 ;; In Info, `Method on class: name ARGS'
3571 ;; Note: args in upper case; use of `on'
64c8498a
RS
3572 ;; Use cdr of texinfo-defun-type to determine category:
3573 (let ((category (car (cdr texinfo-defun-type)))
7f3e80e3
RS
3574 (class (car parsed-args))
3575 (name (car (cdr parsed-args)))
3576 (args (cdr (cdr parsed-args))))
3577 (insert " -- " category " on " class ": " name)
3578 (while args
3579 (insert " " (upcase (car args)))
3580 (setq args (cdr args)))))
3581
3582;; @defivar: Specialized object-oriented
3583(put 'defivar 'texinfo-deffn-formatting-property 'texinfo-format-defivar)
3584(put 'defivarx 'texinfo-deffn-formatting-property 'texinfo-format-defivar)
3585(defun texinfo-format-defivar (parsed-args)
3586 ;; Specialized object oriented entity:
3587 ;; @defivar class name
3588 ;; In Info, `Instance variable of class: name'
3589 ;; Note: args in upper case; use of `of'
64c8498a
RS
3590 ;; Use cdr of texinfo-defun-type to determine category:
3591 (let ((category (car (cdr texinfo-defun-type)))
7f3e80e3
RS
3592 (class (car parsed-args))
3593 (name (car (cdr parsed-args)))
3594 (args (cdr (cdr parsed-args))))
3595 (insert " -- " category " of " class ": " name)
3596 (while args
3597 (insert " " (upcase (car args)))
3598 (setq args (cdr args)))))
4dd29d03 3599
7f3e80e3
RS
3600\f
3601;;; Indexing for definitions
3602
3603;; An index entry has three parts: the `entry proper', the node name, and the
3604;; line number. Depending on the which command is used, the entry is
3605;; formatted differently:
3606;;
db95369b
JB
3607;; @defun,
3608;; @defmac,
3609;; @defspec,
3610;; @defvar,
3611;; @defopt all use their 1st argument as the entry-proper
7f3e80e3 3612;;
db95369b
JB
3613;; @deffn,
3614;; @defvr,
3615;; @deftp
7f3e80e3
RS
3616;; @deftypefun
3617;; @deftypevar all use their 2nd argument as the entry-proper
3618;;
db95369b
JB
3619;; @deftypefn,
3620;; @deftypevr both use their 3rd argument as the entry-proper
7f3e80e3 3621;;
db95369b 3622;; @defmethod uses its 2nd and 1st arguments as an entry-proper
7f3e80e3
RS
3623;; formatted: NAME on CLASS
3624
db95369b 3625;; @defop uses its 3rd and 2nd arguments as an entry-proper
7f3e80e3 3626;; formatted: NAME on CLASS
db95369b 3627;;
7f3e80e3
RS
3628;; @defivar uses its 2nd and 1st arguments as an entry-proper
3629;; formatted: NAME of CLASS
3630;;
3631;; @defcv uses its 3rd and 2nd argument as an entry-proper
3632;; formatted: NAME of CLASS
3633
3634(put 'defun 'texinfo-defun-indexing-property 'texinfo-index-defun)
3635(put 'defunx 'texinfo-defun-indexing-property 'texinfo-index-defun)
3636(put 'defmac 'texinfo-defun-indexing-property 'texinfo-index-defun)
3637(put 'defmacx 'texinfo-defun-indexing-property 'texinfo-index-defun)
3638(put 'defspec 'texinfo-defun-indexing-property 'texinfo-index-defun)
3639(put 'defspecx 'texinfo-defun-indexing-property 'texinfo-index-defun)
3640(put 'defvar 'texinfo-defun-indexing-property 'texinfo-index-defun)
3641(put 'defvarx 'texinfo-defun-indexing-property 'texinfo-index-defun)
3642(put 'defopt 'texinfo-defun-indexing-property 'texinfo-index-defun)
3643(put 'defoptx 'texinfo-defun-indexing-property 'texinfo-index-defun)
3644(defun texinfo-index-defun (parsed-args)
3645 ;; use 1st parsed-arg as entry-proper
3646 ;; `index-list' will be texinfo-findex or the like
3647 (let ((index-list (get texinfo-command-name 'texinfo-defun-index)))
3648 (set index-list
db95369b 3649 (cons
7f3e80e3
RS
3650 ;; Three elements: entry-proper, node-name, line-number
3651 (list
3652 (car parsed-args)
3653 texinfo-last-node
3654 ;; Region formatting may not provide last node position.
3655 (if texinfo-last-node-pos
3656 (1+ (count-lines texinfo-last-node-pos (point)))
3657 1))
3658 (symbol-value index-list)))))
3659
3660(put 'deffn 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3661(put 'deffnx 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3662(put 'defvr 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3663(put 'defvrx 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3664(put 'deftp 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3665(put 'deftpx 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3666(put 'deftypefun 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3667(put 'deftypefunx 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3668(put 'deftypevar 'texinfo-defun-indexing-property 'texinfo-index-deffn)
3669(put 'deftypevarx 'texinfo-defun-indexing-property 'texinfo-index-deffn)
db95369b 3670(defun texinfo-index-deffn (parsed-args)
7f3e80e3
RS
3671 ;; use 2nd parsed-arg as entry-proper
3672 ;; `index-list' will be texinfo-findex or the like
3673 (let ((index-list (get texinfo-command-name 'texinfo-defun-index)))
3674 (set index-list
db95369b 3675 (cons
7f3e80e3
RS
3676 ;; Three elements: entry-proper, node-name, line-number
3677 (list
3678 (car (cdr parsed-args))
3679 texinfo-last-node
3680 ;; Region formatting may not provide last node position.
3681 (if texinfo-last-node-pos
3682 (1+ (count-lines texinfo-last-node-pos (point)))
3683 1))
3684 (symbol-value index-list)))))
3685
3686(put 'deftypefn 'texinfo-defun-indexing-property 'texinfo-index-deftypefn)
3687(put 'deftypefnx 'texinfo-defun-indexing-property 'texinfo-index-deftypefn)
3688(put 'deftypevr 'texinfo-defun-indexing-property 'texinfo-index-deftypefn)
3689(put 'deftypevrx 'texinfo-defun-indexing-property 'texinfo-index-deftypefn)
3690(defun texinfo-index-deftypefn (parsed-args)
3691 ;; use 3rd parsed-arg as entry-proper
3692 ;; `index-list' will be texinfo-findex or the like
3693 (let ((index-list (get texinfo-command-name 'texinfo-defun-index)))
3694 (set index-list
db95369b 3695 (cons
7f3e80e3
RS
3696 ;; Three elements: entry-proper, node-name, line-number
3697 (list
3698 (car (cdr (cdr parsed-args)))
3699 texinfo-last-node
3700 ;; Region formatting may not provide last node position.
3701 (if texinfo-last-node-pos
3702 (1+ (count-lines texinfo-last-node-pos (point)))
3703 1))
3704 (symbol-value index-list)))))
3705
3706(put 'defmethod 'texinfo-defun-indexing-property 'texinfo-index-defmethod)
3707(put 'defmethodx 'texinfo-defun-indexing-property 'texinfo-index-defmethod)
3708(defun texinfo-index-defmethod (parsed-args)
3709 ;; use 2nd on 1st parsed-arg as entry-proper
3710 ;; `index-list' will be texinfo-findex or the like
3711 (let ((index-list (get texinfo-command-name 'texinfo-defun-index)))
3712 (set index-list
db95369b 3713 (cons
7f3e80e3
RS
3714 ;; Three elements: entry-proper, node-name, line-number
3715 (list
db95369b 3716 (format "%s on %s"
7f3e80e3
RS
3717 (car (cdr parsed-args))
3718 (car parsed-args))
3719 texinfo-last-node
3720 ;; Region formatting may not provide last node position.
3721 (if texinfo-last-node-pos
3722 (1+ (count-lines texinfo-last-node-pos (point)))
3723 1))
3724 (symbol-value index-list)))))
3725
3726(put 'defop 'texinfo-defun-indexing-property 'texinfo-index-defop)
3727(put 'defopx 'texinfo-defun-indexing-property 'texinfo-index-defop)
3728(defun texinfo-index-defop (parsed-args)
3729 ;; use 3rd on 2nd parsed-arg as entry-proper
3730 ;; `index-list' will be texinfo-findex or the like
3731 (let ((index-list (get texinfo-command-name 'texinfo-defun-index)))
3732 (set index-list
db95369b 3733 (cons
7f3e80e3
RS
3734 ;; Three elements: entry-proper, node-name, line-number
3735 (list
db95369b 3736 (format "%s on %s"
7f3e80e3
RS
3737 (car (cdr (cdr parsed-args)))
3738 (car (cdr parsed-args)))
3739 texinfo-last-node
3740 ;; Region formatting may not provide last node position.
3741 (if texinfo-last-node-pos
3742 (1+ (count-lines texinfo-last-node-pos (point)))
3743 1))
3744 (symbol-value index-list)))))
3745
3746(put 'defivar 'texinfo-defun-indexing-property 'texinfo-index-defivar)
3747(put 'defivarx 'texinfo-defun-indexing-property 'texinfo-index-defivar)
3748(defun texinfo-index-defivar (parsed-args)
3749 ;; use 2nd of 1st parsed-arg as entry-proper
3750 ;; `index-list' will be texinfo-findex or the like
3751 (let ((index-list (get texinfo-command-name 'texinfo-defun-index)))
3752 (set index-list
db95369b 3753 (cons
7f3e80e3
RS
3754 ;; Three elements: entry-proper, node-name, line-number
3755 (list
db95369b 3756 (format "%s of %s"
7f3e80e3
RS
3757 (car (cdr parsed-args))
3758 (car parsed-args))
3759 texinfo-last-node
3760 ;; Region formatting may not provide last node position.
3761 (if texinfo-last-node-pos
3762 (1+ (count-lines texinfo-last-node-pos (point)))
3763 1))
3764 (symbol-value index-list)))))
3765
3766(put 'defcv 'texinfo-defun-indexing-property 'texinfo-index-defcv)
3767(put 'defcvx 'texinfo-defun-indexing-property 'texinfo-index-defcv)
3768(defun texinfo-index-defcv (parsed-args)
3769 ;; use 3rd of 2nd parsed-arg as entry-proper
3770 ;; `index-list' will be texinfo-findex or the like
3771 (let ((index-list (get texinfo-command-name 'texinfo-defun-index)))
3772 (set index-list
db95369b 3773 (cons
7f3e80e3
RS
3774 ;; Three elements: entry-proper, node-name, line-number
3775 (list
db95369b 3776 (format "%s of %s"
7f3e80e3
RS
3777 (car (cdr (cdr parsed-args)))
3778 (car (cdr parsed-args)))
3779 texinfo-last-node
3780 ;; Region formatting may not provide last node position.
3781 (if texinfo-last-node-pos
3782 (1+ (count-lines texinfo-last-node-pos (point)))
3783 1))
3784 (symbol-value index-list)))))
4dd29d03 3785
7f3e80e3
RS
3786\f
3787;;; Properties for definitions
3788
3789;; Each definition command has six properties:
3790;;
3791;; 1. texinfo-deffn-formatting-property to format definition line
3792;; 2. texinfo-defun-indexing-property to create index entry
3793;; 3. texinfo-format formatting command
3794;; 4. texinfo-end end formatting command
3795;; 5. texinfo-defun-type type of deffn to format
3796;; 6. texinfo-defun-index type of index to use
3797;;
3798;; The `x' forms of each definition command are used for the second
3799;; and subsequent header lines.
3800
3801;; The texinfo-deffn-formatting-property and texinfo-defun-indexing-property
3802;; are listed just before the appropriate formatting and indexing commands.
4dd29d03
BP
3803
3804(put 'deffn 'texinfo-format 'texinfo-format-defun)
3805(put 'deffnx 'texinfo-format 'texinfo-format-defunx)
3806(put 'deffn 'texinfo-end 'texinfo-end-defun)
3807(put 'deffn 'texinfo-defun-type '('deffn-type nil))
3808(put 'deffnx 'texinfo-defun-type '('deffn-type nil))
3809(put 'deffn 'texinfo-defun-index 'texinfo-findex)
3810(put 'deffnx 'texinfo-defun-index 'texinfo-findex)
3811
3812(put 'defun 'texinfo-format 'texinfo-format-defun)
3813(put 'defunx 'texinfo-format 'texinfo-format-defunx)
3814(put 'defun 'texinfo-end 'texinfo-end-defun)
3815(put 'defun 'texinfo-defun-type '('defun-type "Function"))
3816(put 'defunx 'texinfo-defun-type '('defun-type "Function"))
3817(put 'defun 'texinfo-defun-index 'texinfo-findex)
3818(put 'defunx 'texinfo-defun-index 'texinfo-findex)
3819
3820(put 'defmac 'texinfo-format 'texinfo-format-defun)
3821(put 'defmacx 'texinfo-format 'texinfo-format-defunx)
3822(put 'defmac 'texinfo-end 'texinfo-end-defun)
3823(put 'defmac 'texinfo-defun-type '('defun-type "Macro"))
3824(put 'defmacx 'texinfo-defun-type '('defun-type "Macro"))
3825(put 'defmac 'texinfo-defun-index 'texinfo-findex)
3826(put 'defmacx 'texinfo-defun-index 'texinfo-findex)
3827
3828(put 'defspec 'texinfo-format 'texinfo-format-defun)
3829(put 'defspecx 'texinfo-format 'texinfo-format-defunx)
3830(put 'defspec 'texinfo-end 'texinfo-end-defun)
3831(put 'defspec 'texinfo-defun-type '('defun-type "Special form"))
3832(put 'defspecx 'texinfo-defun-type '('defun-type "Special form"))
3833(put 'defspec 'texinfo-defun-index 'texinfo-findex)
3834(put 'defspecx 'texinfo-defun-index 'texinfo-findex)
3835
3836(put 'defvr 'texinfo-format 'texinfo-format-defun)
3837(put 'defvrx 'texinfo-format 'texinfo-format-defunx)
3838(put 'defvr 'texinfo-end 'texinfo-end-defun)
3839(put 'defvr 'texinfo-defun-type '('deffn-type nil))
3840(put 'defvrx 'texinfo-defun-type '('deffn-type nil))
3841(put 'defvr 'texinfo-defun-index 'texinfo-vindex)
3842(put 'defvrx 'texinfo-defun-index 'texinfo-vindex)
3843
3844(put 'defvar 'texinfo-format 'texinfo-format-defun)
3845(put 'defvarx 'texinfo-format 'texinfo-format-defunx)
3846(put 'defvar 'texinfo-end 'texinfo-end-defun)
3847(put 'defvar 'texinfo-defun-type '('defun-type "Variable"))
3848(put 'defvarx 'texinfo-defun-type '('defun-type "Variable"))
3849(put 'defvar 'texinfo-defun-index 'texinfo-vindex)
3850(put 'defvarx 'texinfo-defun-index 'texinfo-vindex)
3851
3852(put 'defconst 'texinfo-format 'texinfo-format-defun)
3853(put 'defconstx 'texinfo-format 'texinfo-format-defunx)
3854(put 'defconst 'texinfo-end 'texinfo-end-defun)
3855(put 'defconst 'texinfo-defun-type '('defun-type "Constant"))
3856(put 'defconstx 'texinfo-defun-type '('defun-type "Constant"))
3857(put 'defconst 'texinfo-defun-index 'texinfo-vindex)
3858(put 'defconstx 'texinfo-defun-index 'texinfo-vindex)
3859
3860(put 'defcmd 'texinfo-format 'texinfo-format-defun)
3861(put 'defcmdx 'texinfo-format 'texinfo-format-defunx)
3862(put 'defcmd 'texinfo-end 'texinfo-end-defun)
3863(put 'defcmd 'texinfo-defun-type '('defun-type "Command"))
3864(put 'defcmdx 'texinfo-defun-type '('defun-type "Command"))
3865(put 'defcmd 'texinfo-defun-index 'texinfo-findex)
3866(put 'defcmdx 'texinfo-defun-index 'texinfo-findex)
3867
3868(put 'defopt 'texinfo-format 'texinfo-format-defun)
3869(put 'defoptx 'texinfo-format 'texinfo-format-defunx)
3870(put 'defopt 'texinfo-end 'texinfo-end-defun)
3871(put 'defopt 'texinfo-defun-type '('defun-type "User Option"))
3872(put 'defoptx 'texinfo-defun-type '('defun-type "User Option"))
3873(put 'defopt 'texinfo-defun-index 'texinfo-vindex)
3874(put 'defoptx 'texinfo-defun-index 'texinfo-vindex)
3875
3876(put 'deftp 'texinfo-format 'texinfo-format-defun)
3877(put 'deftpx 'texinfo-format 'texinfo-format-defunx)
3878(put 'deftp 'texinfo-end 'texinfo-end-defun)
3879(put 'deftp 'texinfo-defun-type '('deftp-type nil))
3880(put 'deftpx 'texinfo-defun-type '('deftp-type nil))
3881(put 'deftp 'texinfo-defun-index 'texinfo-tindex)
3882(put 'deftpx 'texinfo-defun-index 'texinfo-tindex)
3883
3884;;; Object-oriented stuff is a little hairier.
3885
3886(put 'defop 'texinfo-format 'texinfo-format-defun)
3887(put 'defopx 'texinfo-format 'texinfo-format-defunx)
3888(put 'defop 'texinfo-end 'texinfo-end-defun)
3889(put 'defop 'texinfo-defun-type '('defop-type nil))
3890(put 'defopx 'texinfo-defun-type '('defop-type nil))
4dd29d03
BP
3891(put 'defop 'texinfo-defun-index 'texinfo-findex)
3892(put 'defopx 'texinfo-defun-index 'texinfo-findex)
4dd29d03
BP
3893
3894(put 'defmethod 'texinfo-format 'texinfo-format-defun)
3895(put 'defmethodx 'texinfo-format 'texinfo-format-defunx)
3896(put 'defmethod 'texinfo-end 'texinfo-end-defun)
7f3e80e3
RS
3897(put 'defmethod 'texinfo-defun-type '('defmethod-type "Method"))
3898(put 'defmethodx 'texinfo-defun-type '('defmethod-type "Method"))
4dd29d03
BP
3899(put 'defmethod 'texinfo-defun-index 'texinfo-findex)
3900(put 'defmethodx 'texinfo-defun-index 'texinfo-findex)
4dd29d03
BP
3901
3902(put 'defcv 'texinfo-format 'texinfo-format-defun)
3903(put 'defcvx 'texinfo-format 'texinfo-format-defunx)
3904(put 'defcv 'texinfo-end 'texinfo-end-defun)
3905(put 'defcv 'texinfo-defun-type '('defop-type nil))
3906(put 'defcvx 'texinfo-defun-type '('defop-type nil))
4dd29d03
BP
3907(put 'defcv 'texinfo-defun-index 'texinfo-vindex)
3908(put 'defcvx 'texinfo-defun-index 'texinfo-vindex)
4dd29d03
BP
3909
3910(put 'defivar 'texinfo-format 'texinfo-format-defun)
3911(put 'defivarx 'texinfo-format 'texinfo-format-defunx)
3912(put 'defivar 'texinfo-end 'texinfo-end-defun)
3913(put 'defivar 'texinfo-defun-type '('defmethod-type "Instance variable"))
3914(put 'defivarx 'texinfo-defun-type '('defmethod-type "Instance variable"))
4dd29d03
BP
3915(put 'defivar 'texinfo-defun-index 'texinfo-vindex)
3916(put 'defivarx 'texinfo-defun-index 'texinfo-vindex)
4dd29d03
BP
3917
3918;;; Typed functions and variables
3919
4dd29d03
BP
3920(put 'deftypefn 'texinfo-format 'texinfo-format-defun)
3921(put 'deftypefnx 'texinfo-format 'texinfo-format-defunx)
3922(put 'deftypefn 'texinfo-end 'texinfo-end-defun)
3923(put 'deftypefn 'texinfo-defun-type '('deftypefn-type nil))
3924(put 'deftypefnx 'texinfo-defun-type '('deftypefn-type nil))
4dd29d03
BP
3925(put 'deftypefn 'texinfo-defun-index 'texinfo-findex)
3926(put 'deftypefnx 'texinfo-defun-index 'texinfo-findex)
4dd29d03
BP
3927
3928(put 'deftypefun 'texinfo-format 'texinfo-format-defun)
3929(put 'deftypefunx 'texinfo-format 'texinfo-format-defunx)
3930(put 'deftypefun 'texinfo-end 'texinfo-end-defun)
3931(put 'deftypefun 'texinfo-defun-type '('deftypefun-type "Function"))
3932(put 'deftypefunx 'texinfo-defun-type '('deftypefun-type "Function"))
4dd29d03
BP
3933(put 'deftypefun 'texinfo-defun-index 'texinfo-findex)
3934(put 'deftypefunx 'texinfo-defun-index 'texinfo-findex)
4dd29d03
BP
3935
3936(put 'deftypevr 'texinfo-format 'texinfo-format-defun)
3937(put 'deftypevrx 'texinfo-format 'texinfo-format-defunx)
3938(put 'deftypevr 'texinfo-end 'texinfo-end-defun)
3939(put 'deftypevr 'texinfo-defun-type '('deftypefn-type nil))
3940(put 'deftypevrx 'texinfo-defun-type '('deftypefn-type nil))
4dd29d03
BP
3941(put 'deftypevr 'texinfo-defun-index 'texinfo-vindex)
3942(put 'deftypevrx 'texinfo-defun-index 'texinfo-vindex)
4dd29d03
BP
3943
3944(put 'deftypevar 'texinfo-format 'texinfo-format-defun)
3945(put 'deftypevarx 'texinfo-format 'texinfo-format-defunx)
3946(put 'deftypevar 'texinfo-end 'texinfo-end-defun)
3947(put 'deftypevar 'texinfo-defun-type '('deftypevar-type "Variable"))
3948(put 'deftypevarx 'texinfo-defun-type '('deftypevar-type "Variable"))
4dd29d03
BP
3949(put 'deftypevar 'texinfo-defun-index 'texinfo-vindex)
3950(put 'deftypevarx 'texinfo-defun-index 'texinfo-vindex)
4dd29d03
BP
3951
3952\f
7f3e80e3
RS
3953;;; @set, @clear, @ifset, @ifclear
3954
3955;; If a flag is set with @set FLAG, then text between @ifset and @end
3956;; ifset is formatted normally, but if the flag is is cleared with
3957;; @clear FLAG, then the text is not formatted; it is ignored.
3958
3959;; If a flag is cleared with @clear FLAG, then text between @ifclear
3960;; and @end ifclear is formatted normally, but if the flag is is set with
3961;; @set FLAG, then the text is not formatted; it is ignored. @ifclear
3962;; is the opposite of @ifset.
3963
db95369b 3964;; If a flag is set to a string with @set FLAG,
7f3e80e3 3965;; replace @value{FLAG} with the string.
db95369b
JB
3966;; If a flag with a value is cleared,
3967;; @value{FLAG} is invalid,
7f3e80e3
RS
3968;; as if there had never been any @set FLAG previously.
3969
3970(put 'clear 'texinfo-format 'texinfo-clear)
3971(defun texinfo-clear ()
3972 "Clear the value of the flag."
3973 (let* ((arg (texinfo-parse-arg-discard))
3974 (flag (car (read-from-string arg)))
3975 (value (substring arg (cdr (read-from-string arg)))))
3976 (put flag 'texinfo-whether-setp 'flag-cleared)
3977 (put flag 'texinfo-set-value "")))
3978
3979(put 'set 'texinfo-format 'texinfo-set)
3980(defun texinfo-set ()
3981 "Set the value of the flag, optionally to a string.
3982The command `@set foo This is a string.'
3983sets flag foo to the value: `This is a string.'
3984The command `@value{foo}' expands to the value."
3985 (let* ((arg (texinfo-parse-arg-discard))
3986 (flag (car (read-from-string arg)))
3987 (value (substring arg (cdr (read-from-string arg)))))
8bb6eb14
GM
3988 (if (string-match "^[ \t]+" value)
3989 (setq value (substring value (match-end 0))))
7f3e80e3
RS
3990 (put flag 'texinfo-whether-setp 'flag-set)
3991 (put flag 'texinfo-set-value value)))
3992
3993(put 'value 'texinfo-format 'texinfo-value)
3994(defun texinfo-value ()
3995 "Insert the string to which the flag is set.
3996The command `@set foo This is a string.'
3997sets flag foo to the value: `This is a string.'
3998The command `@value{foo}' expands to the value."
3999 (let ((arg (texinfo-parse-arg-discard)))
4000 (cond ((and
4001 (eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
4002 'flag-set)
4003 (get (car (read-from-string arg)) 'texinfo-set-value))
4004 (insert (get (car (read-from-string arg)) 'texinfo-set-value)))
db95369b 4005 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
7f3e80e3
RS
4006 'flag-cleared)
4007 (insert (format "{No value for \"%s\"}" arg)))
4008 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp) nil)
4009 (insert (format "{No value for \"%s\"}" arg))))))
4010
4011(put 'ifset 'texinfo-end 'texinfo-discard-command)
4012(put 'ifset 'texinfo-format 'texinfo-if-set)
4013(defun texinfo-if-set ()
4014 "If set, continue formatting; else do not format region up to @end ifset"
4015 (let ((arg (texinfo-parse-arg-discard)))
4016 (cond
4017 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
4018 'flag-set)
4019 ;; Format the text (i.e., do not remove it); do nothing here.
4020 ())
4021 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
4022 'flag-cleared)
4023 ;; Clear region (i.e., cause the text to be ignored).
4024 (delete-region texinfo-command-start
6147e725 4025 (re-search-forward "@end ifset[ \t]*\n")))
7f3e80e3
RS
4026 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
4027 nil)
db95369b 4028 ;; In this case flag is neither set nor cleared.
acb93e31
RC
4029 ;; Act as if set, i.e. do nothing.
4030 ()))))
7f3e80e3
RS
4031
4032(put 'ifclear 'texinfo-end 'texinfo-discard-command)
4033(put 'ifclear 'texinfo-format 'texinfo-if-clear)
4034(defun texinfo-if-clear ()
4035 "If clear, continue formatting; if set, do not format up to @end ifset"
4036 (let ((arg (texinfo-parse-arg-discard)))
4037 (cond
4038 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
4039 'flag-set)
4040 ;; Clear region (i.e., cause the text to be ignored).
4041 (delete-region texinfo-command-start
6147e725 4042 (re-search-forward "@end ifclear[ \t]*\n")))
7f3e80e3
RS
4043 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
4044 'flag-cleared)
4045 ;; Format the text (i.e., do not remove it); do nothing here.
4046 ())
4047 ((eq (get (car (read-from-string arg)) 'texinfo-whether-setp)
4048 nil)
db95369b 4049 ;; In this case flag is neither set nor cleared.
acb93e31
RC
4050 ;; Act as if clear, i.e. do nothing.
4051 ()))))
7f3e80e3 4052\f
92f62199
RS
4053;;; @ifeq
4054
4055(put 'ifeq 'texinfo-format 'texinfo-format-ifeq)
4056(defun texinfo-format-ifeq ()
c988a68a 4057 "If ARG1 and ARG2 caselessly string compare to same string, perform COMMAND.
92f62199
RS
4058Otherwise produces no output.
4059
4060Thus:
4061 @ifeq{ arg1 , arg1 , @code{foo}} bar
4062
4063 ==> `foo' bar.
4064but
4065 @ifeq{ arg1 , arg2 , @code{foo}} bar
4066
4067 ==> bar
4068
4069Note that the Texinfo command and its arguments must be arguments to
4070the @ifeq command."
4071 ;; compare-buffer-substrings does not exist in version 18; don't use
4072 (goto-char texinfo-command-end)
4073 (let* ((case-fold-search t)
4074 (stop (save-excursion (forward-sexp 1) (point)))
4075 start end
4076 ;; @ifeq{arg1, arg2, @command{optional-args}}
4077 (arg1
4078 (progn
4079 (forward-char 1)
4080 (skip-chars-forward " ")
4081 (setq start (point))
4082 (search-forward "," stop t)
4083 (skip-chars-backward ", ")
289df0fc 4084 (buffer-substring-no-properties start (point))))
92f62199
RS
4085 (arg2
4086 (progn
4087 (search-forward "," stop t)
4088 (skip-chars-forward " ")
4089 (setq start (point))
4090 (search-forward "," stop t)
4091 (skip-chars-backward ", ")
289df0fc 4092 (buffer-substring-no-properties start (point))))
92f62199
RS
4093 (texinfo-command
4094 (progn
4095 (search-forward "," stop t)
4096 (skip-chars-forward " ")
4097 (setq start (point))
4098 (goto-char (1- stop))
4099 (skip-chars-backward " ")
289df0fc 4100 (buffer-substring-no-properties start (point)))))
92f62199
RS
4101 (delete-region texinfo-command-start stop)
4102 (if (equal arg1 arg2)
4103 (insert texinfo-command))
4104 (goto-char texinfo-command-start)))
4105
4106\f
7f3e80e3 4107;;; Process included files: `@include' command
4dd29d03
BP
4108
4109;; Updated 19 October 1990
4110;; In the original version, include files were ignored by Info but
4111;; incorporated in to the printed manual. To make references to the
4112;; included file, the Texinfo source file has to refer to the included
a7acbbe4 4113;; files using the `(filename)nodename' format for referring to other
4dd29d03
BP
4114;; Info files. Also, the included files had to be formatted on their
4115;; own. It was just like they were another file.
4116
4117;; Currently, include files are inserted into the buffer that is
4118;; formatted for Info. If large, the resulting info file is split and
4119;; tagified. For current include files to work, the master menu must
4120;; refer to all the nodes, and the highest level nodes in the include
4121;; files must have the correct next, prev, and up pointers.
4122
4123;; The included file may have an @setfilename and even an @settitle,
7f3e80e3
RS
4124;; but not an `\input texinfo' line.
4125
4126;; Updated 24 March 1993
4127;; In order for @raisesections and @lowersections to work, included
4128;; files must be inserted into the buffer holding the outer file
4129;; before other Info formatting takes place. So @include is no longer
4130;; is treated like other @-commands.
4131(put 'include 'texinfo-format 'texinfo-format-noop)
4dd29d03 4132
92f62199
RS
4133;; Original definition:
4134;; (defun texinfo-format-include ()
4135;; (let ((filename (texinfo-parse-arg-discard))
4136;; (default-directory input-directory)
4137;; subindex)
4138;; (setq subindex
4139;; (save-excursion
4140;; (progn (find-file
4141;; (cond ((file-readable-p (concat filename ".texinfo"))
4142;; (concat filename ".texinfo"))
4143;; ((file-readable-p (concat filename ".texi"))
4144;; (concat filename ".texi"))
4145;; ((file-readable-p (concat filename ".tex"))
4146;; (concat filename ".tex"))
4147;; ((file-readable-p filename)
4148;; filename)
4149;; (t (error "@include'd file %s not found"
4150;; filename))))
4151;; (texinfo-format-buffer-1))))
4152;; (texinfo-subindex 'texinfo-vindex (car subindex) (nth 1 subindex))
4153;; (texinfo-subindex 'texinfo-findex (car subindex) (nth 2 subindex))
4154;; (texinfo-subindex 'texinfo-cindex (car subindex) (nth 3 subindex))
4155;; (texinfo-subindex 'texinfo-pindex (car subindex) (nth 4 subindex))
4156;; (texinfo-subindex 'texinfo-tindex (car subindex) (nth 5 subindex))
4157;; (texinfo-subindex 'texinfo-kindex (car subindex) (nth 6 subindex))))
4158;;
4159;;(defun texinfo-subindex (indexvar file content)
4160;; (set indexvar (cons (list 'recurse file content)
4161;; (symbol-value indexvar))))
4162
4163;; Second definition:
4164;; (put 'include 'texinfo-format 'texinfo-format-include)
4165;; (defun texinfo-format-include ()
4166;; (let ((filename (concat input-directory
4167;; (texinfo-parse-arg-discard)))
4168;; (default-directory input-directory))
4169;; (message "Reading: %s" filename)
4170;; (save-excursion
4171;; (save-restriction
4172;; (narrow-to-region
4173;; (point)
4174;; (+ (point) (car (cdr (insert-file-contents filename)))))
4175;; (goto-char (point-min))
4176;; (texinfo-append-refill)
4177;; (texinfo-format-convert (point-min) (point-max))))
4178;; (setq last-input-buffer input-buffer) ; to bypass setfilename
4179;; ))
4dd29d03
BP
4180
4181\f
92f62199 4182;;; Numerous commands do nothing in Info
7f3e80e3
RS
4183;; These commands are defined in texinfo.tex for printed output.
4184
92f62199
RS
4185\f
4186;;; various noops, such as @b{foo}, that take arguments in braces
4187
4188(put 'b 'texinfo-format 'texinfo-format-noop)
4189(put 'i 'texinfo-format 'texinfo-format-noop)
4190(put 'r 'texinfo-format 'texinfo-format-noop)
4191(put 't 'texinfo-format 'texinfo-format-noop)
4192(put 'w 'texinfo-format 'texinfo-format-noop)
4193(put 'asis 'texinfo-format 'texinfo-format-noop)
4194(put 'dmn 'texinfo-format 'texinfo-format-noop)
4195(put 'math 'texinfo-format 'texinfo-format-noop)
4196(put 'titlefont 'texinfo-format 'texinfo-format-noop)
4197(defun texinfo-format-noop ()
4198 (insert (texinfo-parse-arg-discard))
4199 (goto-char texinfo-command-start))
4200
4201;; @hyphenation command discards an argument within braces
4202(put 'hyphenation 'texinfo-format 'texinfo-discard-command-and-arg)
4203(defun texinfo-discard-command-and-arg ()
4204 "Discard both @-command and its argument in braces."
4205 (goto-char texinfo-command-end)
4206 (forward-list 1)
4207 (setq texinfo-command-end (point))
4208 (delete-region texinfo-command-start texinfo-command-end))
4209
4210\f
4211;;; Do nothing commands, such as @smallbook, that have no args and no braces
4212;; These must appear on a line of their own
4213
7f3e80e3 4214(put 'bye 'texinfo-format 'texinfo-discard-line)
92f62199
RS
4215(put 'smallbook 'texinfo-format 'texinfo-discard-line)
4216(put 'finalout 'texinfo-format 'texinfo-discard-line)
4217(put 'overfullrule 'texinfo-format 'texinfo-discard-line)
4218(put 'smallbreak 'texinfo-format 'texinfo-discard-line)
4219(put 'medbreak 'texinfo-format 'texinfo-discard-line)
4220(put 'bigbreak 'texinfo-format 'texinfo-discard-line)
2b6a2afe 4221(put 'afourpaper 'texinfo-format 'texinfo-discard-line)
6b9bfa95
RC
4222(put 'afivepaper 'texinfo-format 'texinfo-discard-line)
4223(put 'afourlatex 'texinfo-format 'texinfo-discard-line)
4224(put 'afourwide 'texinfo-format 'texinfo-discard-line)
92f62199
RS
4225
4226\f
4227;;; These noop commands discard the rest of the line.
4228
4dd29d03
BP
4229(put 'c 'texinfo-format 'texinfo-discard-line-with-args)
4230(put 'comment 'texinfo-format 'texinfo-discard-line-with-args)
4dd29d03 4231(put 'contents 'texinfo-format 'texinfo-discard-line-with-args)
7f3e80e3
RS
4232(put 'group 'texinfo-end 'texinfo-discard-line-with-args)
4233(put 'group 'texinfo-format 'texinfo-discard-line-with-args)
4234(put 'headings 'texinfo-format 'texinfo-discard-line-with-args)
92f62199 4235(put 'setchapterstyle 'texinfo-format 'texinfo-discard-line-with-args)
4dd29d03 4236(put 'hsize 'texinfo-format 'texinfo-discard-line-with-args)
4dd29d03 4237(put 'itemindent 'texinfo-format 'texinfo-discard-line-with-args)
7f3e80e3 4238(put 'lispnarrowing 'texinfo-format 'texinfo-discard-line-with-args)
4dd29d03 4239(put 'need 'texinfo-format 'texinfo-discard-line-with-args)
7f3e80e3 4240(put 'nopara 'texinfo-format 'texinfo-discard-line-with-args)
1c87ab31
RS
4241
4242;; @novalidate suppresses cross-reference checking and auxiliary file
4243;; creation with TeX. The Info-validate command checks that every
4244;; node pointer points to an existing node. Since this Info command
4245;; is not invoked automatically, the @novalidate command is irrelevant
4246;; and not supported by texinfmt.el
4247(put 'novalidate 'texinfo-format 'texinfo-discard-line-with-args)
4248
7f3e80e3 4249(put 'page 'texinfo-format 'texinfo-discard-line-with-args)
1c87ab31 4250(put 'pagesizes 'texinfo-format 'texinfo-discard-line-with-args)
7f3e80e3
RS
4251(put 'parindent 'texinfo-format 'texinfo-discard-line-with-args)
4252(put 'setchapternewpage 'texinfo-format 'texinfo-discard-line-with-args)
4253(put 'setq 'texinfo-format 'texinfo-discard-line-with-args)
1c87ab31
RS
4254
4255(put 'setcontentsaftertitlepage
4256 'texinfo-format 'texinfo-discard-line-with-args)
4257(put 'setshortcontentsaftertitlepage
4258 'texinfo-format 'texinfo-discard-line-with-args)
4259
7f3e80e3
RS
4260(put 'settitle 'texinfo-format 'texinfo-discard-line-with-args)
4261(put 'setx 'texinfo-format 'texinfo-discard-line-with-args)
4262(put 'shortcontents 'texinfo-format 'texinfo-discard-line-with-args)
92f62199 4263(put 'shorttitlepage 'texinfo-format 'texinfo-discard-line-with-args)
7f3e80e3 4264(put 'summarycontents 'texinfo-format 'texinfo-discard-line-with-args)
92f62199 4265(put 'input 'texinfo-format 'texinfo-discard-line-with-args)
4dd29d03 4266
2b6a2afe
JB
4267(put 'documentlanguage 'texinfo-format 'texinfo-discard-line-with-args)
4268(put 'documentencoding 'texinfo-format 'texinfo-discard-line-with-args)
4269
4270
7f3e80e3
RS
4271\f
4272;;; Some commands cannot be handled
4dd29d03
BP
4273
4274(defun texinfo-unsupported ()
4275 (error "%s is not handled by texinfo"
289df0fc 4276 (buffer-substring-no-properties texinfo-command-start texinfo-command-end)))
4dd29d03 4277\f
7f3e80e3
RS
4278;;; Batch formatting
4279
4dd29d03 4280(defun batch-texinfo-format ()
7f3e80e3 4281 "Runs texinfo-format-buffer on the files remaining on the command line.
4dd29d03
BP
4282Must be used only with -batch, and kills emacs on completion.
4283Each file will be processed even if an error occurred previously.
4284For example, invoke
4285 \"emacs -batch -funcall batch-texinfo-format $docs/ ~/*.texinfo\"."
4286 (if (not noninteractive)
e8af40ee 4287 (error "batch-texinfo-format may only be used -batch"))
4dd29d03 4288 (let ((version-control t)
7f3e80e3
RS
4289 (auto-save-default nil)
4290 (find-file-run-dired nil)
4291 (kept-old-versions 259259)
4292 (kept-new-versions 259259))
4dd29d03 4293 (let ((error 0)
7f3e80e3
RS
4294 file
4295 (files ()))
4dd29d03 4296 (while command-line-args-left
7f3e80e3
RS
4297 (setq file (expand-file-name (car command-line-args-left)))
4298 (cond ((not (file-exists-p file))
4299 (message ">> %s does not exist!" file)
4300 (setq error 1
4301 command-line-args-left (cdr command-line-args-left)))
4302 ((file-directory-p file)
4303 (setq command-line-args-left
4304 (nconc (directory-files file)
4305 (cdr command-line-args-left))))
4306 (t
4307 (setq files (cons file files)
4308 command-line-args-left (cdr command-line-args-left)))))
4dd29d03 4309 (while files
7f3e80e3
RS
4310 (setq file (car files)
4311 files (cdr files))
4312 (condition-case err
4313 (progn
4314 (if buffer-file-name (kill-buffer (current-buffer)))
4315 (find-file file)
90a44351 4316 (buffer-disable-undo (current-buffer))
7f3e80e3
RS
4317 (set-buffer-modified-p nil)
4318 (texinfo-mode)
4319 (message "texinfo formatting %s..." file)
4320 (texinfo-format-buffer nil)
4321 (if (buffer-modified-p)
4322 (progn (message "Saving modified %s" (buffer-file-name))
4323 (save-buffer))))
4324 (error
4325 (message ">> Error: %s" (prin1-to-string err))
4326 (message ">> point at")
289df0fc 4327 (let ((s (buffer-substring-no-properties (point)
6147e725
SM
4328 (min (+ (point) 100)
4329 (point-max))))
7f3e80e3
RS
4330 (tem 0))
4331 (while (setq tem (string-match "\n+" s tem))
4332 (setq s (concat (substring s 0 (match-beginning 0))
4333 "\n>> "
4334 (substring s (match-end 0)))
4335 tem (1+ tem)))
4336 (message ">> %s" s))
4337 (setq error 1))))
4dd29d03 4338 (kill-emacs error))))
d501f516 4339
7f3e80e3
RS
4340\f
4341;;; Place `provide' at end of file.
6bf9133d
RS
4342(provide 'texinfmt)
4343
ab5796a9 4344;;; arch-tag: 1e8d9a2d-bca0-40a0-ac6c-dab01bc6f725
e8af40ee 4345;;; texinfmt.el ends here