142629Sobrien% texinfo.tex -- TeX macros to handle Texinfo files.
2310490Scy% 
342629Sobrien% Load plain if necessary, i.e., if running under initex.
438494Sobrien\expandafter\ifx\csname fmtname\endcsname\relax\input plain\fi
542629Sobrien%
6310490Scy\def\texinfoversion{2013-02-01.11}
742629Sobrien%
8310490Scy% Copyright 1985, 1986, 1988, 1990, 1991, 1992, 1993, 1994, 1995,
9310490Scy% 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006,
10310490Scy% 2007, 2008, 2009, 2010, 2011, 2012, 2013 Free Software Foundation, Inc.
1142629Sobrien%
12310490Scy% This texinfo.tex file is free software: you can redistribute it and/or
1342629Sobrien% modify it under the terms of the GNU General Public License as
14310490Scy% published by the Free Software Foundation, either version 3 of the
15310490Scy% License, or (at your option) any later version.
1642629Sobrien%
1742629Sobrien% This texinfo.tex file is distributed in the hope that it will be
1842629Sobrien% useful, but WITHOUT ANY WARRANTY; without even the implied warranty
1942629Sobrien% of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
2042629Sobrien% General Public License for more details.
2142629Sobrien%
2242629Sobrien% You should have received a copy of the GNU General Public License
23310490Scy% along with this program.  If not, see <http://www.gnu.org/licenses/>.
2442629Sobrien%
25174294Sobrien% As a special exception, when this file is read by TeX when processing
26174294Sobrien% a Texinfo source document, you may use the result without
27310490Scy% restriction. This Exception is an additional permission under section 7
28310490Scy% of the GNU General Public License, version 3 ("GPLv3").
2942629Sobrien%
3042629Sobrien% Please try the latest version of texinfo.tex before submitting bug
3142629Sobrien% reports; you can get the latest version from:
32310490Scy%   http://ftp.gnu.org/gnu/texinfo/ (the Texinfo release area), or
33310490Scy%   http://ftpmirror.gnu.org/texinfo/ (same, via a mirror), or
34310490Scy%   http://www.gnu.org/software/texinfo/ (the Texinfo home page)
35174294Sobrien% The texinfo.tex in any given distribution could well be out
3642629Sobrien% of date, so if that's what you're using, please check.
3782794Sobrien%
3882794Sobrien% Send bug reports to bug-texinfo@gnu.org.  Please include including a
3982794Sobrien% complete document in each bug report with which we can reproduce the
4082794Sobrien% problem.  Patches are, of course, greatly appreciated.
4182794Sobrien%
4242629Sobrien% To process a Texinfo manual with TeX, it's most reliable to use the
4382794Sobrien% texi2dvi shell script that comes with the distribution.  For a simple
4482794Sobrien% manual foo.texi, however, you can get away with this:
4542629Sobrien%   tex foo.texi
4642629Sobrien%   texindex foo.??
4742629Sobrien%   tex foo.texi
4842629Sobrien%   tex foo.texi
49119679Smbr%   dvips foo.dvi -o  # or whatever; this makes foo.ps.
50119679Smbr% The extra TeX runs get the cross-reference information correct.
5142629Sobrien% Sometimes one run after texindex suffices, and sometimes you need more
5242629Sobrien% than two; texi2dvi does it as many times as necessary.
5382794Sobrien%
54174294Sobrien% It is possible to adapt texinfo.tex for other languages, to some
55174294Sobrien% extent.  You can get the existing language-specific files from the
56174294Sobrien% full Texinfo distribution.
57174294Sobrien%
58174294Sobrien% The GNU Texinfo home page is http://www.gnu.org/software/texinfo.
5938494Sobrien
60174294Sobrien
6142629Sobrien\message{Loading texinfo [version \texinfoversion]:}
6238494Sobrien
6338494Sobrien% If in a .fmt file, print the version number
6438494Sobrien% and turn on active characters that we couldn't do earlier because
6538494Sobrien% they might have appeared in the input file name.
6642629Sobrien\everyjob{\message{[Texinfo version \texinfoversion]}%
6738494Sobrien  \catcode`+=\active \catcode`\_=\active}
6838494Sobrien
69174294Sobrien\chardef\other=12
70174294Sobrien
71174294Sobrien% We never want plain's \outer definition of \+ in Texinfo.
72174294Sobrien% For @tex, we can use \tabalign.
73174294Sobrien\let\+ = \relax
74174294Sobrien
75174294Sobrien% Save some plain tex macros whose names we will redefine.
7638494Sobrien\let\ptexb=\b
7738494Sobrien\let\ptexbullet=\bullet
7838494Sobrien\let\ptexc=\c
7938494Sobrien\let\ptexcomma=\,
8038494Sobrien\let\ptexdot=\.
8138494Sobrien\let\ptexdots=\dots
8238494Sobrien\let\ptexend=\end
8342629Sobrien\let\ptexequiv=\equiv
8442629Sobrien\let\ptexexclam=\!
85174294Sobrien\let\ptexfootnote=\footnote
86174294Sobrien\let\ptexgtr=>
87174294Sobrien\let\ptexhat=^
8838494Sobrien\let\ptexi=\i
89174294Sobrien\let\ptexindent=\indent
90174294Sobrien\let\ptexinsert=\insert
9138494Sobrien\let\ptexlbrace=\{
92174294Sobrien\let\ptexless=<
93310490Scy\let\ptexnewwrite\newwrite
94310490Scy\let\ptexnoindent=\noindent
95174294Sobrien\let\ptexplus=+
96310490Scy\let\ptexraggedright=\raggedright
9738494Sobrien\let\ptexrbrace=\}
98174294Sobrien\let\ptexslash=\/
9938494Sobrien\let\ptexstar=\*
10038494Sobrien\let\ptext=\t
101310490Scy\let\ptextop=\top
102310490Scy{\catcode`\'=\active \global\let\ptexquoteright'}% active in plain's math mode
10338494Sobrien
10438494Sobrien% If this character appears in an error message or help string, it
10538494Sobrien% starts a new line in the output.
10638494Sobrien\newlinechar = `^^J
10738494Sobrien
108174294Sobrien% Use TeX 3.0's \inputlineno to get the line number, for better error
109174294Sobrien% messages, but if we're using an old version of TeX, don't do anything.
110174294Sobrien%
111174294Sobrien\ifx\inputlineno\thisisundefined
112174294Sobrien  \let\linenumber = \empty % Pre-3.0.
113174294Sobrien\else
114174294Sobrien  \def\linenumber{l.\the\inputlineno:\space}
115174294Sobrien\fi
116174294Sobrien
11742629Sobrien% Set up fixed words for English if not already set.
11882794Sobrien\ifx\putwordAppendix\undefined  \gdef\putwordAppendix{Appendix}\fi
11982794Sobrien\ifx\putwordChapter\undefined   \gdef\putwordChapter{Chapter}\fi
120310490Scy\ifx\putworderror\undefined     \gdef\putworderror{error}\fi
12182794Sobrien\ifx\putwordfile\undefined      \gdef\putwordfile{file}\fi
12282794Sobrien\ifx\putwordin\undefined        \gdef\putwordin{in}\fi
123310490Scy\ifx\putwordIndexIsEmpty\undefined       \gdef\putwordIndexIsEmpty{(Index is empty)}\fi
124310490Scy\ifx\putwordIndexNonexistent\undefined   \gdef\putwordIndexNonexistent{(Index is nonexistent)}\fi
12582794Sobrien\ifx\putwordInfo\undefined      \gdef\putwordInfo{Info}\fi
12682794Sobrien\ifx\putwordInstanceVariableof\undefined \gdef\putwordInstanceVariableof{Instance Variable of}\fi
12782794Sobrien\ifx\putwordMethodon\undefined  \gdef\putwordMethodon{Method on}\fi
12882794Sobrien\ifx\putwordNoTitle\undefined   \gdef\putwordNoTitle{No Title}\fi
12982794Sobrien\ifx\putwordof\undefined        \gdef\putwordof{of}\fi
13082794Sobrien\ifx\putwordon\undefined        \gdef\putwordon{on}\fi
13182794Sobrien\ifx\putwordpage\undefined      \gdef\putwordpage{page}\fi
13282794Sobrien\ifx\putwordsection\undefined   \gdef\putwordsection{section}\fi
13382794Sobrien\ifx\putwordSection\undefined   \gdef\putwordSection{Section}\fi
13482794Sobrien\ifx\putwordsee\undefined       \gdef\putwordsee{see}\fi
13582794Sobrien\ifx\putwordSee\undefined       \gdef\putwordSee{See}\fi
13682794Sobrien\ifx\putwordShortTOC\undefined  \gdef\putwordShortTOC{Short Contents}\fi
13782794Sobrien\ifx\putwordTOC\undefined       \gdef\putwordTOC{Table of Contents}\fi
13882794Sobrien%
13982794Sobrien\ifx\putwordMJan\undefined \gdef\putwordMJan{January}\fi
14082794Sobrien\ifx\putwordMFeb\undefined \gdef\putwordMFeb{February}\fi
14182794Sobrien\ifx\putwordMMar\undefined \gdef\putwordMMar{March}\fi
14282794Sobrien\ifx\putwordMApr\undefined \gdef\putwordMApr{April}\fi
14382794Sobrien\ifx\putwordMMay\undefined \gdef\putwordMMay{May}\fi
14482794Sobrien\ifx\putwordMJun\undefined \gdef\putwordMJun{June}\fi
14582794Sobrien\ifx\putwordMJul\undefined \gdef\putwordMJul{July}\fi
14682794Sobrien\ifx\putwordMAug\undefined \gdef\putwordMAug{August}\fi
14782794Sobrien\ifx\putwordMSep\undefined \gdef\putwordMSep{September}\fi
14882794Sobrien\ifx\putwordMOct\undefined \gdef\putwordMOct{October}\fi
14982794Sobrien\ifx\putwordMNov\undefined \gdef\putwordMNov{November}\fi
15082794Sobrien\ifx\putwordMDec\undefined \gdef\putwordMDec{December}\fi
15182794Sobrien%
15282794Sobrien\ifx\putwordDefmac\undefined    \gdef\putwordDefmac{Macro}\fi
15382794Sobrien\ifx\putwordDefspec\undefined   \gdef\putwordDefspec{Special Form}\fi
15482794Sobrien\ifx\putwordDefvar\undefined    \gdef\putwordDefvar{Variable}\fi
15582794Sobrien\ifx\putwordDefopt\undefined    \gdef\putwordDefopt{User Option}\fi
15682794Sobrien\ifx\putwordDeffunc\undefined   \gdef\putwordDeffunc{Function}\fi
15738494Sobrien
158310490Scy% Since the category of space is not known, we have to be careful.
159310490Scy\chardef\spacecat = 10
160310490Scy\def\spaceisspace{\catcode`\ =\spacecat}
161310490Scy
162310490Scy% sometimes characters are active, so we need control sequences.
163310490Scy\chardef\ampChar   = `\&
164174294Sobrien\chardef\colonChar = `\:
165174294Sobrien\chardef\commaChar = `\,
166310490Scy\chardef\dashChar  = `\-
167174294Sobrien\chardef\dotChar   = `\.
168174294Sobrien\chardef\exclamChar= `\!
169310490Scy\chardef\hashChar  = `\#
170310490Scy\chardef\lquoteChar= `\`
171174294Sobrien\chardef\questChar = `\?
172310490Scy\chardef\rquoteChar= `\'
173174294Sobrien\chardef\semiChar  = `\;
174310490Scy\chardef\slashChar = `\/
175174294Sobrien\chardef\underChar = `\_
176174294Sobrien
17738494Sobrien% Ignore a token.
17838494Sobrien%
17938494Sobrien\def\gobble#1{}
18038494Sobrien
181174294Sobrien% The following is used inside several \edef's.
182174294Sobrien\def\makecsname#1{\expandafter\noexpand\csname#1\endcsname}
18338494Sobrien
184174294Sobrien% Hyphenation fixes.
185174294Sobrien\hyphenation{
186174294Sobrien  Flor-i-da Ghost-script Ghost-view Mac-OS Post-Script
187174294Sobrien  ap-pen-dix bit-map bit-maps
188174294Sobrien  data-base data-bases eshell fall-ing half-way long-est man-u-script
189174294Sobrien  man-u-scripts mini-buf-fer mini-buf-fers over-view par-a-digm
190174294Sobrien  par-a-digms rath-er rec-tan-gu-lar ro-bot-ics se-vere-ly set-up spa-ces
191174294Sobrien  spell-ing spell-ings
192174294Sobrien  stand-alone strong-est time-stamp time-stamps which-ever white-space
193174294Sobrien  wide-spread wrap-around
194174294Sobrien}
195174294Sobrien
19638494Sobrien% Margin to add to right of even pages, to left of odd pages.
197174294Sobrien\newdimen\bindingoffset
198174294Sobrien\newdimen\normaloffset
19938494Sobrien\newdimen\pagewidth \newdimen\pageheight
20038494Sobrien
201174294Sobrien% For a final copy, take out the rectangles
202174294Sobrien% that mark overfull boxes (in case you have decided
203174294Sobrien% that the text looks ok even though it passes the margin).
204174294Sobrien%
205310490Scy\def\finalout{\overfullrule=0pt }
206174294Sobrien
20738494Sobrien% Sometimes it is convenient to have everything in the transcript file
20838494Sobrien% and nothing on the terminal.  We don't just call \tracingall here,
209174294Sobrien% since that produces some useless output on the terminal.  We also make
210174294Sobrien% some effort to order the tracing commands to reduce output in the log
211174294Sobrien% file; cf. trace.sty in LaTeX.
21238494Sobrien%
21338494Sobrien\def\gloggingall{\begingroup \globaldefs = 1 \loggingall \endgroup}%
214174294Sobrien\def\loggingall{%
215174294Sobrien  \tracingstats2
216174294Sobrien  \tracingpages1
217174294Sobrien  \tracinglostchars2  % 2 gives us more in etex
218174294Sobrien  \tracingparagraphs1
219174294Sobrien  \tracingoutput1
220174294Sobrien  \tracingmacros2
221174294Sobrien  \tracingrestores1
222174294Sobrien  \showboxbreadth\maxdimen \showboxdepth\maxdimen
223310490Scy  \ifx\eTeXversion\thisisundefined\else % etex gives us more logging
224174294Sobrien    \tracingscantokens1
225174294Sobrien    \tracingifs1
226174294Sobrien    \tracinggroups1
227174294Sobrien    \tracingnesting2
228174294Sobrien    \tracingassigns1
229174294Sobrien  \fi
230174294Sobrien  \tracingcommands3  % 3 gives us more in etex
231174294Sobrien  \errorcontextlines16
23238494Sobrien}%
23338494Sobrien
234310490Scy% @errormsg{MSG}.  Do the index-like expansions on MSG, but if things
235310490Scy% aren't perfect, it's not the end of the world, being an error message,
236310490Scy% after all.
237310490Scy% 
238310490Scy\def\errormsg{\begingroup \indexnofonts \doerrormsg}
239310490Scy\def\doerrormsg#1{\errmessage{#1}}
240310490Scy
24182794Sobrien% add check for \lastpenalty to plain's definitions.  If the last thing
24282794Sobrien% we did was a \nobreak, we don't want to insert more space.
243174294Sobrien%
24482794Sobrien\def\smallbreak{\ifnum\lastpenalty<10000\par\ifdim\lastskip<\smallskipamount
24582794Sobrien  \removelastskip\penalty-50\smallskip\fi\fi}
24682794Sobrien\def\medbreak{\ifnum\lastpenalty<10000\par\ifdim\lastskip<\medskipamount
24782794Sobrien  \removelastskip\penalty-100\medskip\fi\fi}
24882794Sobrien\def\bigbreak{\ifnum\lastpenalty<10000\par\ifdim\lastskip<\bigskipamount
24982794Sobrien  \removelastskip\penalty-200\bigskip\fi\fi}
25082794Sobrien
25138494Sobrien% Do @cropmarks to get crop marks.
25282794Sobrien%
25338494Sobrien\newif\ifcropmarks
25438494Sobrien\let\cropmarks = \cropmarkstrue
25538494Sobrien%
25638494Sobrien% Dimensions to add cropmarks at corners.
25738494Sobrien% Added by P. A. MacKay, 12 Nov. 1986
25838494Sobrien%
25942629Sobrien\newdimen\outerhsize \newdimen\outervsize % set by the paper size routines
26042629Sobrien\newdimen\cornerlong  \cornerlong=1pc
26142629Sobrien\newdimen\cornerthick \cornerthick=.3pt
26242629Sobrien\newdimen\topandbottommargin \topandbottommargin=.75in
26338494Sobrien
264310490Scy% Output a mark which sets \thischapter, \thissection and \thiscolor.
265310490Scy% We dump everything together because we only have one kind of mark.
266310490Scy% This works because we only use \botmark / \topmark, not \firstmark.
267310490Scy%
268310490Scy% A mark contains a subexpression of the \ifcase ... \fi construct.
269310490Scy% \get*marks macros below extract the needed part using \ifcase.
270310490Scy%
271310490Scy% Another complication is to let the user choose whether \thischapter
272310490Scy% (\thissection) refers to the chapter (section) in effect at the top
273310490Scy% of a page, or that at the bottom of a page.  The solution is
274310490Scy% described on page 260 of The TeXbook.  It involves outputting two
275310490Scy% marks for the sectioning macros, one before the section break, and
276310490Scy% one after.  I won't pretend I can describe this better than DEK...
277310490Scy\def\domark{%
278310490Scy  \toks0=\expandafter{\lastchapterdefs}%
279310490Scy  \toks2=\expandafter{\lastsectiondefs}%
280310490Scy  \toks4=\expandafter{\prevchapterdefs}%
281310490Scy  \toks6=\expandafter{\prevsectiondefs}%
282310490Scy  \toks8=\expandafter{\lastcolordefs}%
283310490Scy  \mark{%
284310490Scy                   \the\toks0 \the\toks2
285310490Scy      \noexpand\or \the\toks4 \the\toks6
286310490Scy    \noexpand\else \the\toks8
287310490Scy  }%
288310490Scy}
289310490Scy% \topmark doesn't work for the very first chapter (after the title
290310490Scy% page or the contents), so we use \firstmark there -- this gets us
291310490Scy% the mark with the chapter defs, unless the user sneaks in, e.g.,
292310490Scy% @setcolor (or @url, or @link, etc.) between @contents and the very
293310490Scy% first @chapter.
294310490Scy\def\gettopheadingmarks{%
295310490Scy  \ifcase0\topmark\fi
296310490Scy  \ifx\thischapter\empty \ifcase0\firstmark\fi \fi
297310490Scy}
298310490Scy\def\getbottomheadingmarks{\ifcase1\botmark\fi}
299310490Scy\def\getcolormarks{\ifcase2\topmark\fi}
300310490Scy
301310490Scy% Avoid "undefined control sequence" errors.
302310490Scy\def\lastchapterdefs{}
303310490Scy\def\lastsectiondefs{}
304310490Scy\def\prevchapterdefs{}
305310490Scy\def\prevsectiondefs{}
306310490Scy\def\lastcolordefs{}
307310490Scy
30838494Sobrien% Main output routine.
30938494Sobrien\chardef\PAGE = 255
31038494Sobrien\output = {\onepageout{\pagecontents\PAGE}}
31138494Sobrien
31238494Sobrien\newbox\headlinebox
31338494Sobrien\newbox\footlinebox
31438494Sobrien
31538494Sobrien% \onepageout takes a vbox as an argument.  Note that \pagecontents
31638494Sobrien% does insertions, but you have to call it yourself.
31738494Sobrien\def\onepageout#1{%
31838494Sobrien  \ifcropmarks \hoffset=0pt \else \hoffset=\normaloffset \fi
31938494Sobrien  %
32038494Sobrien  \ifodd\pageno  \advance\hoffset by \bindingoffset
32138494Sobrien  \else \advance\hoffset by -\bindingoffset\fi
32238494Sobrien  %
32338494Sobrien  % Do this outside of the \shipout so @code etc. will be expanded in
32438494Sobrien  % the headline as they should be, not taken literally (outputting ''code).
325310490Scy  \ifodd\pageno \getoddheadingmarks \else \getevenheadingmarks \fi
32638494Sobrien  \setbox\headlinebox = \vbox{\let\hsize=\pagewidth \makeheadline}%
327310490Scy  \ifodd\pageno \getoddfootingmarks \else \getevenfootingmarks \fi
32838494Sobrien  \setbox\footlinebox = \vbox{\let\hsize=\pagewidth \makefootline}%
32938494Sobrien  %
33038494Sobrien  {%
33138494Sobrien    % Have to do this stuff outside the \shipout because we want it to
33238494Sobrien    % take effect in \write's, yet the group defined by the \vbox ends
33338494Sobrien    % before the \shipout runs.
33438494Sobrien    %
33538494Sobrien    \indexdummies         % don't expand commands in the output.
33638494Sobrien    \normalturnoffactive  % \ in index entries must not stay \, e.g., if
337310490Scy               % the page break happens to be in the middle of an example.
338310490Scy               % We don't want .vr (or whatever) entries like this:
339310490Scy               % \entry{{\tt \indexbackslash }acronym}{32}{\code {\acronym}}
340310490Scy               % "\acronym" won't work when it's read back in;
341310490Scy               % it needs to be
342310490Scy               % {\code {{\tt \backslashcurfont }acronym}
34338494Sobrien    \shipout\vbox{%
34482794Sobrien      % Do this early so pdf references go to the beginning of the page.
345174294Sobrien      \ifpdfmakepagedest \pdfdest name{\the\pageno} xyz\fi
34682794Sobrien      %
34738494Sobrien      \ifcropmarks \vbox to \outervsize\bgroup
34838494Sobrien        \hsize = \outerhsize
34942629Sobrien        \vskip-\topandbottommargin
35042629Sobrien        \vtop to0pt{%
35142629Sobrien          \line{\ewtop\hfil\ewtop}%
35242629Sobrien          \nointerlineskip
35342629Sobrien          \line{%
35442629Sobrien            \vbox{\moveleft\cornerthick\nstop}%
35542629Sobrien            \hfill
35642629Sobrien            \vbox{\moveright\cornerthick\nstop}%
35742629Sobrien          }%
35842629Sobrien          \vss}%
35938494Sobrien        \vskip\topandbottommargin
36038494Sobrien        \line\bgroup
36138494Sobrien          \hfil % center the page within the outer (page) hsize.
36238494Sobrien          \ifodd\pageno\hskip\bindingoffset\fi
36338494Sobrien          \vbox\bgroup
36438494Sobrien      \fi
36538494Sobrien      %
36638494Sobrien      \unvbox\headlinebox
36738494Sobrien      \pagebody{#1}%
36838494Sobrien      \ifdim\ht\footlinebox > 0pt
36938494Sobrien        % Only leave this space if the footline is nonempty.
370310490Scy        % (We lessened \vsize for it in \oddfootingyyy.)
37138494Sobrien        % The \baselineskip=24pt in plain's \makefootline has no effect.
372310490Scy        \vskip 24pt
37338494Sobrien        \unvbox\footlinebox
37438494Sobrien      \fi
37538494Sobrien      %
37638494Sobrien      \ifcropmarks
37738494Sobrien          \egroup % end of \vbox\bgroup
37838494Sobrien        \hfil\egroup % end of (centering) \line\bgroup
37938494Sobrien        \vskip\topandbottommargin plus1fill minus1fill
38038494Sobrien        \boxmaxdepth = \cornerthick
38142629Sobrien        \vbox to0pt{\vss
38242629Sobrien          \line{%
38342629Sobrien            \vbox{\moveleft\cornerthick\nsbot}%
38442629Sobrien            \hfill
38542629Sobrien            \vbox{\moveright\cornerthick\nsbot}%
38642629Sobrien          }%
38742629Sobrien          \nointerlineskip
38842629Sobrien          \line{\ewbot\hfil\ewbot}%
38938494Sobrien        }%
39038494Sobrien      \egroup % \vbox from first cropmarks clause
39138494Sobrien      \fi
39238494Sobrien    }% end of \shipout\vbox
393310490Scy  }% end of group with \indexdummies
39438494Sobrien  \advancepageno
39538494Sobrien  \ifnum\outputpenalty>-20000 \else\dosupereject\fi
39638494Sobrien}
39738494Sobrien
39838494Sobrien\newinsert\margin \dimen\margin=\maxdimen
39938494Sobrien
40038494Sobrien\def\pagebody#1{\vbox to\pageheight{\boxmaxdepth=\maxdepth #1}}
40138494Sobrien{\catcode`\@ =11
40238494Sobrien\gdef\pagecontents#1{\ifvoid\topins\else\unvbox\topins\fi
40338494Sobrien% marginal hacks, juha@viisa.uucp (Juha Takala)
40438494Sobrien\ifvoid\margin\else % marginal info is present
40538494Sobrien  \rlap{\kern\hsize\vbox to\z@{\kern1pt\box\margin \vss}}\fi
406310490Scy\dimen@=\dp#1\relax \unvbox#1\relax
40738494Sobrien\ifvoid\footins\else\vskip\skip\footins\footnoterule \unvbox\footins\fi
40838494Sobrien\ifr@ggedbottom \kern-\dimen@ \vfil \fi}
40938494Sobrien}
41038494Sobrien
41138494Sobrien% Here are the rules for the cropmarks.  Note that they are
41238494Sobrien% offset so that the space between them is truly \outerhsize or \outervsize
41338494Sobrien% (P. A. MacKay, 12 November, 1986)
41438494Sobrien%
41538494Sobrien\def\ewtop{\vrule height\cornerthick depth0pt width\cornerlong}
41638494Sobrien\def\nstop{\vbox
41738494Sobrien  {\hrule height\cornerthick depth\cornerlong width\cornerthick}}
41838494Sobrien\def\ewbot{\vrule height0pt depth\cornerthick width\cornerlong}
41938494Sobrien\def\nsbot{\vbox
42038494Sobrien  {\hrule height\cornerlong depth\cornerthick width\cornerthick}}
42138494Sobrien
42238494Sobrien% Parse an argument, then pass it to #1.  The argument is the rest of
42338494Sobrien% the input line (except we remove a trailing comment).  #1 should be a
42438494Sobrien% macro which expects an ordinary undelimited TeX argument.
42538494Sobrien%
426174294Sobrien\def\parsearg{\parseargusing{}}
427174294Sobrien\def\parseargusing#1#2{%
428310490Scy  \def\argtorun{#2}%
42938494Sobrien  \begingroup
43038494Sobrien    \obeylines
431174294Sobrien    \spaceisspace
432174294Sobrien    #1%
433174294Sobrien    \parseargline\empty% Insert the \empty token, see \finishparsearg below.
43438494Sobrien}
43538494Sobrien
43638494Sobrien{\obeylines %
43738494Sobrien  \gdef\parseargline#1^^M{%
43838494Sobrien    \endgroup % End of the group started in \parsearg.
439174294Sobrien    \argremovecomment #1\comment\ArgTerm%
44038494Sobrien  }%
44138494Sobrien}
44238494Sobrien
443174294Sobrien% First remove any @comment, then any @c comment.
444174294Sobrien\def\argremovecomment#1\comment#2\ArgTerm{\argremovec #1\c\ArgTerm}
445174294Sobrien\def\argremovec#1\c#2\ArgTerm{\argcheckspaces#1\^^M\ArgTerm}
44638494Sobrien
447310490Scy% Each occurrence of `\^^M' or `<space>\^^M' is replaced by a single space.
448174294Sobrien%
449174294Sobrien% \argremovec might leave us with trailing space, e.g.,
45038494Sobrien%    @end itemize  @c foo
451174294Sobrien% This space token undergoes the same procedure and is eventually removed
452174294Sobrien% by \finishparsearg.
45338494Sobrien%
454174294Sobrien\def\argcheckspaces#1\^^M{\argcheckspacesX#1\^^M \^^M}
455174294Sobrien\def\argcheckspacesX#1 \^^M{\argcheckspacesY#1\^^M}
456174294Sobrien\def\argcheckspacesY#1\^^M#2\^^M#3\ArgTerm{%
457174294Sobrien  \def\temp{#3}%
458174294Sobrien  \ifx\temp\empty
459310490Scy    % Do not use \next, perhaps the caller of \parsearg uses it; reuse \temp:
460174294Sobrien    \let\temp\finishparsearg
461174294Sobrien  \else
462174294Sobrien    \let\temp\argcheckspaces
463174294Sobrien  \fi
464174294Sobrien  % Put the space token in:
465174294Sobrien  \temp#1 #3\ArgTerm
466174294Sobrien}
467174294Sobrien
468174294Sobrien% If a _delimited_ argument is enclosed in braces, they get stripped; so
469174294Sobrien% to get _exactly_ the rest of the line, we had to prevent such situation.
470174294Sobrien% We prepended an \empty token at the very beginning and we expand it now,
471310490Scy% just before passing the control to \argtorun.
472310490Scy% (Similarly, we have to think about #3 of \argcheckspacesY above: it is
473174294Sobrien% either the null string, or it ends with \^^M---thus there is no danger
474174294Sobrien% that a pair of braces would be stripped.
47538494Sobrien%
476174294Sobrien% But first, we have to remove the trailing space token.
477174294Sobrien%
478310490Scy\def\finishparsearg#1 \ArgTerm{\expandafter\argtorun\expandafter{#1}}
479174294Sobrien
480174294Sobrien% \parseargdef\foo{...}
481174294Sobrien%	is roughly equivalent to
482174294Sobrien% \def\foo{\parsearg\Xfoo}
483174294Sobrien% \def\Xfoo#1{...}
484174294Sobrien%
485174294Sobrien% Actually, I use \csname\string\foo\endcsname, ie. \\foo, as it is my
486174294Sobrien% favourite TeX trick.  --kasal, 16nov03
487174294Sobrien
488174294Sobrien\def\parseargdef#1{%
489174294Sobrien  \expandafter \doparseargdef \csname\string#1\endcsname #1%
49038494Sobrien}
491174294Sobrien\def\doparseargdef#1#2{%
492174294Sobrien  \def#2{\parsearg#1}%
493174294Sobrien  \def#1##1%
494174294Sobrien}
49538494Sobrien
496174294Sobrien% Several utility definitions with active space:
497174294Sobrien{
49838494Sobrien  \obeyspaces
499174294Sobrien  \gdef\obeyedspace{ }
50038494Sobrien
501174294Sobrien  % Make each space character in the input produce a normal interword
502174294Sobrien  % space in the output.  Don't allow a line break at this space, as this
503174294Sobrien  % is used only in environments like @example, where each line of input
504174294Sobrien  % should produce a line of output anyway.
505174294Sobrien  %
506174294Sobrien  \gdef\sepspaces{\obeyspaces\let =\tie}
50738494Sobrien
508174294Sobrien  % If an index command is used in an @example environment, any spaces
509174294Sobrien  % therein should become regular spaces in the raw index file, not the
510174294Sobrien  % expansion of \tie (\leavevmode \penalty \@M \ ).
511174294Sobrien  \gdef\unsepspaces{\let =\space}
512174294Sobrien}
513174294Sobrien
514174294Sobrien
51538494Sobrien\def\flushcr{\ifx\par\lisppar \def\next##1{}\else \let\next=\relax \fi \next}
51638494Sobrien
517174294Sobrien% Define the framework for environments in texinfo.tex.  It's used like this:
518174294Sobrien%
519174294Sobrien%   \envdef\foo{...}
520174294Sobrien%   \def\Efoo{...}
521174294Sobrien%
522174294Sobrien% It's the responsibility of \envdef to insert \begingroup before the
523174294Sobrien% actual body; @end closes the group after calling \Efoo.  \envdef also
524174294Sobrien% defines \thisenv, so the current environment is known; @end checks
525174294Sobrien% whether the environment name matches.  The \checkenv macro can also be
526174294Sobrien% used to check whether the current environment is the one expected.
527174294Sobrien%
528174294Sobrien% Non-false conditionals (@iftex, @ifset) don't fit into this, so they
529310490Scy% are not treated as environments; they don't open a group.  (The
530174294Sobrien% implementation of @end takes care not to call \endgroup in this
531174294Sobrien% special case.)
53238494Sobrien
53338494Sobrien
534310490Scy% At run-time, environments start with this:
535174294Sobrien\def\startenvironment#1{\begingroup\def\thisenv{#1}}
536174294Sobrien% initialize
537174294Sobrien\let\thisenv\empty
53838494Sobrien
539174294Sobrien% ... but they get defined via ``\envdef\foo{...}'':
540174294Sobrien\long\def\envdef#1#2{\def#1{\startenvironment#1#2}}
541174294Sobrien\def\envparseargdef#1#2{\parseargdef#1{\startenvironment#1#2}}
54238494Sobrien
543174294Sobrien% Check whether we're in the right environment:
544174294Sobrien\def\checkenv#1{%
545174294Sobrien  \def\temp{#1}%
546174294Sobrien  \ifx\thisenv\temp
54738494Sobrien  \else
548174294Sobrien    \badenverr
54938494Sobrien  \fi
55038494Sobrien}
55138494Sobrien
552310490Scy% Environment mismatch, #1 expected:
553174294Sobrien\def\badenverr{%
55438494Sobrien  \errhelp = \EMsimple
555174294Sobrien  \errmessage{This command can appear only \inenvironment\temp,
556174294Sobrien    not \inenvironment\thisenv}%
55738494Sobrien}
558174294Sobrien\def\inenvironment#1{%
559174294Sobrien  \ifx#1\empty
560310490Scy    outside of any environment%
561174294Sobrien  \else
562174294Sobrien    in environment \expandafter\string#1%
563174294Sobrien  \fi
564174294Sobrien}
56538494Sobrien
566174294Sobrien% @end foo executes the definition of \Efoo.
567174294Sobrien% But first, it executes a specialized version of \checkenv
56838494Sobrien%
569174294Sobrien\parseargdef\end{%
570174294Sobrien  \if 1\csname iscond.#1\endcsname
571174294Sobrien  \else
572310490Scy    % The general wording of \badenverr may not be ideal.
573174294Sobrien    \expandafter\checkenv\csname#1\endcsname
574174294Sobrien    \csname E#1\endcsname
575174294Sobrien    \endgroup
576174294Sobrien  \fi
57738494Sobrien}
57838494Sobrien
579174294Sobrien\newhelp\EMsimple{Press RETURN to continue.}
58038494Sobrien
58138494Sobrien
58242629Sobrien% Be sure we're in horizontal mode when doing a tie, since we make space
58342629Sobrien% equivalent to this in @example-like environments. Otherwise, a space
58442629Sobrien% at the beginning of a line will start with \penalty -- and
58542629Sobrien% since \penalty is valid in vertical mode, we'd end up putting the
58642629Sobrien% penalty on the vertical list instead of in the new paragraph.
58742629Sobrien{\catcode`@ = 11
58842629Sobrien % Avoid using \@M directly, because that causes trouble
58942629Sobrien % if the definition is written into an index file.
59042629Sobrien \global\let\tiepenalty = \@M
59142629Sobrien \gdef\tie{\leavevmode\penalty\tiepenalty\ }
59242629Sobrien}
59342629Sobrien
59438494Sobrien% @: forces normal size whitespace following.
59538494Sobrien\def\:{\spacefactor=1000 }
59638494Sobrien
59738494Sobrien% @* forces a line break.
598310490Scy\def\*{\unskip\hfil\break\hbox{}\ignorespaces}
59938494Sobrien
600174294Sobrien% @/ allows a line break.
601174294Sobrien\let\/=\allowbreak
602174294Sobrien
60338494Sobrien% @. is an end-of-sentence period.
604310490Scy\def\.{.\spacefactor=\endofsentencespacefactor\space}
60538494Sobrien
60638494Sobrien% @! is an end-of-sentence bang.
607310490Scy\def\!{!\spacefactor=\endofsentencespacefactor\space}
60838494Sobrien
60938494Sobrien% @? is an end-of-sentence query.
610310490Scy\def\?{?\spacefactor=\endofsentencespacefactor\space}
61138494Sobrien
612310490Scy% @frenchspacing on|off  says whether to put extra space after punctuation.
613310490Scy%
614310490Scy\def\onword{on}
615310490Scy\def\offword{off}
616310490Scy%
617310490Scy\parseargdef\frenchspacing{%
618310490Scy  \def\temp{#1}%
619310490Scy  \ifx\temp\onword \plainfrenchspacing
620310490Scy  \else\ifx\temp\offword \plainnonfrenchspacing
621310490Scy  \else
622310490Scy    \errhelp = \EMsimple
623310490Scy    \errmessage{Unknown @frenchspacing option `\temp', must be on|off}%
624310490Scy  \fi\fi
625310490Scy}
626310490Scy
62738494Sobrien% @w prevents a word break.  Without the \leavevmode, @w at the
62838494Sobrien% beginning of a paragraph, when TeX is still in vertical mode, would
62938494Sobrien% produce a whole line of output instead of starting the paragraph.
63038494Sobrien\def\w#1{\leavevmode\hbox{#1}}
63138494Sobrien
63238494Sobrien% @group ... @end group forces ... to be all on one page, by enclosing
63338494Sobrien% it in a TeX vbox.  We use \vtop instead of \vbox to construct the box
63438494Sobrien% to keep its height that of a normal line.  According to the rules for
63538494Sobrien% \topskip (p.114 of the TeXbook), the glue inserted is
63638494Sobrien% max (\topskip - \ht (first item), 0).  If that height is large,
63738494Sobrien% therefore, no glue is inserted, and the space between the headline and
63838494Sobrien% the text is small, which looks bad.
63938494Sobrien%
640174294Sobrien% Another complication is that the group might be very large.  This can
641174294Sobrien% cause the glue on the previous page to be unduly stretched, because it
642174294Sobrien% does not have much material.  In this case, it's better to add an
643174294Sobrien% explicit \vfill so that the extra space is at the bottom.  The
644174294Sobrien% threshold for doing this is if the group is more than \vfilllimit
645174294Sobrien% percent of a page (\vfilllimit can be changed inside of @tex).
646174294Sobrien%
647174294Sobrien\newbox\groupbox
648174294Sobrien\def\vfilllimit{0.7}
649174294Sobrien%
650174294Sobrien\envdef\group{%
651174294Sobrien  \ifnum\catcode`\^^M=\active \else
65238494Sobrien    \errhelp = \groupinvalidhelp
65338494Sobrien    \errmessage{@group invalid in context where filling is enabled}%
65438494Sobrien  \fi
655174294Sobrien  \startsavinginserts
65638494Sobrien  %
657174294Sobrien  \setbox\groupbox = \vtop\bgroup
65838494Sobrien    % Do @comment since we are called inside an environment such as
65938494Sobrien    % @example, where each end-of-line in the input causes an
66038494Sobrien    % end-of-line in the output.  We don't want the end-of-line after
66138494Sobrien    % the `@group' to put extra space in the output.  Since @group
66238494Sobrien    % should appear on a line by itself (according to the Texinfo
66338494Sobrien    % manual), we don't worry about eating any user text.
66438494Sobrien    \comment
66538494Sobrien}
66638494Sobrien%
667174294Sobrien% The \vtop produces a box with normal height and large depth; thus, TeX puts
668174294Sobrien% \baselineskip glue before it, and (when the next line of text is done)
669174294Sobrien% \lineskip glue after it.  Thus, space below is not quite equal to space
670174294Sobrien% above.  But it's pretty close.
671174294Sobrien\def\Egroup{%
672174294Sobrien    % To get correct interline space between the last line of the group
673174294Sobrien    % and the first line afterwards, we have to propagate \prevdepth.
674174294Sobrien    \endgraf % Not \par, as it may have been set to \lisppar.
675174294Sobrien    \global\dimen1 = \prevdepth
676174294Sobrien  \egroup           % End the \vtop.
677174294Sobrien  % \dimen0 is the vertical size of the group's box.
678174294Sobrien  \dimen0 = \ht\groupbox  \advance\dimen0 by \dp\groupbox
679174294Sobrien  % \dimen2 is how much space is left on the page (more or less).
680174294Sobrien  \dimen2 = \pageheight   \advance\dimen2 by -\pagetotal
681174294Sobrien  % if the group doesn't fit on the current page, and it's a big big
682174294Sobrien  % group, force a page break.
683174294Sobrien  \ifdim \dimen0 > \dimen2
684174294Sobrien    \ifdim \pagetotal < \vfilllimit\pageheight
685174294Sobrien      \page
686174294Sobrien    \fi
687174294Sobrien  \fi
688174294Sobrien  \box\groupbox
689174294Sobrien  \prevdepth = \dimen1
690174294Sobrien  \checkinserts
691174294Sobrien}
692174294Sobrien%
69338494Sobrien% TeX puts in an \escapechar (i.e., `@') at the beginning of the help
69438494Sobrien% message, so this ends up printing `@group can only ...'.
69538494Sobrien%
69638494Sobrien\newhelp\groupinvalidhelp{%
69738494Sobriengroup can only be used in environments such as @example,^^J%
69838494Sobrienwhere each line of input produces a line of output.}
69938494Sobrien
70038494Sobrien% @need space-in-mils
70138494Sobrien% forces a page break if there is not space-in-mils remaining.
70238494Sobrien
70338494Sobrien\newdimen\mil  \mil=0.001in
70438494Sobrien
705174294Sobrien\parseargdef\need{%
70682794Sobrien  % Ensure vertical mode, so we don't make a big box in the middle of a
70738494Sobrien  % paragraph.
70838494Sobrien  \par
70938494Sobrien  %
71082794Sobrien  % If the @need value is less than one line space, it's useless.
71182794Sobrien  \dimen0 = #1\mil
71282794Sobrien  \dimen2 = \ht\strutbox
71382794Sobrien  \advance\dimen2 by \dp\strutbox
71482794Sobrien  \ifdim\dimen0 > \dimen2
71582794Sobrien    %
71682794Sobrien    % Do a \strut just to make the height of this box be normal, so the
71782794Sobrien    % normal leading is inserted relative to the preceding line.
71882794Sobrien    % And a page break here is fine.
71982794Sobrien    \vtop to #1\mil{\strut\vfil}%
72082794Sobrien    %
72182794Sobrien    % TeX does not even consider page breaks if a penalty added to the
72282794Sobrien    % main vertical list is 10000 or more.  But in order to see if the
72382794Sobrien    % empty box we just added fits on the page, we must make it consider
72482794Sobrien    % page breaks.  On the other hand, we don't want to actually break the
72582794Sobrien    % page after the empty box.  So we use a penalty of 9999.
72682794Sobrien    %
72782794Sobrien    % There is an extremely small chance that TeX will actually break the
72882794Sobrien    % page at this \penalty, if there are no other feasible breakpoints in
72982794Sobrien    % sight.  (If the user is using lots of big @group commands, which
73082794Sobrien    % almost-but-not-quite fill up a page, TeX will have a hard time doing
73182794Sobrien    % good page breaking, for example.)  However, I could not construct an
73282794Sobrien    % example where a page broke at this \penalty; if it happens in a real
73382794Sobrien    % document, then we can reconsider our strategy.
73482794Sobrien    \penalty9999
73582794Sobrien    %
73682794Sobrien    % Back up by the size of the box, whether we did a page break or not.
73782794Sobrien    \kern -#1\mil
73882794Sobrien    %
73982794Sobrien    % Do not allow a page break right after this kern.
74082794Sobrien    \nobreak
74182794Sobrien  \fi
74238494Sobrien}
74338494Sobrien
744174294Sobrien% @br   forces paragraph break (and is undocumented).
74538494Sobrien
74638494Sobrien\let\br = \par
74738494Sobrien
748174294Sobrien% @page forces the start of a new page.
74942629Sobrien%
75038494Sobrien\def\page{\par\vfill\supereject}
75138494Sobrien
75238494Sobrien% @exdent text....
75338494Sobrien% outputs text on separate line in roman font, starting at standard page margin
75438494Sobrien
75538494Sobrien% This records the amount of indent in the innermost environment.
75638494Sobrien% That's how much \exdent should take out.
75738494Sobrien\newskip\exdentamount
75838494Sobrien
75938494Sobrien% This defn is used inside fill environments such as @defun.
760174294Sobrien\parseargdef\exdent{\hfil\break\hbox{\kern -\exdentamount{\rm#1}}\hfil\break}
76138494Sobrien
76238494Sobrien% This defn is used inside nofill environments such as @example.
763174294Sobrien\parseargdef\nofillexdent{{\advance \leftskip by -\exdentamount
764174294Sobrien  \leftline{\hskip\leftskip{\rm#1}}}}
76538494Sobrien
76682794Sobrien% @inmargin{WHICH}{TEXT} puts TEXT in the WHICH margin next to the current
76782794Sobrien% paragraph.  For more general purposes, use the \margin insertion
768310490Scy% class.  WHICH is `l' or `r'.  Not documented, written for gawk manual.
76982794Sobrien%
77038494Sobrien\newskip\inmarginspacing \inmarginspacing=1cm
77138494Sobrien\def\strutdepth{\dp\strutbox}
77282794Sobrien%
77382794Sobrien\def\doinmargin#1#2{\strut\vadjust{%
77482794Sobrien  \nobreak
77582794Sobrien  \kern-\strutdepth
77682794Sobrien  \vtop to \strutdepth{%
77782794Sobrien    \baselineskip=\strutdepth
77882794Sobrien    \vss
77982794Sobrien    % if you have multiple lines of stuff to put here, you'll need to
78082794Sobrien    % make the vbox yourself of the appropriate size.
78182794Sobrien    \ifx#1l%
78282794Sobrien      \llap{\ignorespaces #2\hskip\inmarginspacing}%
78382794Sobrien    \else
78482794Sobrien      \rlap{\hskip\hsize \hskip\inmarginspacing \ignorespaces #2}%
78582794Sobrien    \fi
78682794Sobrien    \null
78782794Sobrien  }%
78882794Sobrien}}
78982794Sobrien\def\inleftmargin{\doinmargin l}
79082794Sobrien\def\inrightmargin{\doinmargin r}
79182794Sobrien%
79282794Sobrien% @inmargin{TEXT [, RIGHT-TEXT]}
79382794Sobrien% (if RIGHT-TEXT is given, use TEXT for left page, RIGHT-TEXT for right;
79482794Sobrien% else use TEXT for both).
795174294Sobrien%
79682794Sobrien\def\inmargin#1{\parseinmargin #1,,\finish}
79782794Sobrien\def\parseinmargin#1,#2,#3\finish{% not perfect, but better than nothing.
798174294Sobrien  \setbox0 = \hbox{\ignorespaces #2}%
79982794Sobrien  \ifdim\wd0 > 0pt
80082794Sobrien    \def\lefttext{#1}%  have both texts
80182794Sobrien    \def\righttext{#2}%
80282794Sobrien  \else
80382794Sobrien    \def\lefttext{#1}%  have only one text
80482794Sobrien    \def\righttext{#1}%
80582794Sobrien  \fi
80682794Sobrien  %
80782794Sobrien  \ifodd\pageno
80882794Sobrien    \def\temp{\inrightmargin\righttext}% odd page -> outside is right margin
80982794Sobrien  \else
81082794Sobrien    \def\temp{\inleftmargin\lefttext}%
81182794Sobrien  \fi
81282794Sobrien  \temp
81382794Sobrien}
81438494Sobrien
815310490Scy% @| inserts a changebar to the left of the current line.  It should
816310490Scy% surround any changed text.  This approach does *not* work if the
817310490Scy% change spans more than two lines of output.  To handle that, we would
818310490Scy% have adopt a much more difficult approach (putting marks into the main
819310490Scy% vertical list for the beginning and end of each change).  This command
820310490Scy% is not documented, not supported, and doesn't work.
821174294Sobrien%
822310490Scy\def\|{%
823310490Scy  % \vadjust can only be used in horizontal mode.
824310490Scy  \leavevmode
825310490Scy  %
826310490Scy  % Append this vertical mode material after the current line in the output.
827310490Scy  \vadjust{%
828310490Scy    % We want to insert a rule with the height and depth of the current
829310490Scy    % leading; that is exactly what \strutbox is supposed to record.
830310490Scy    \vskip-\baselineskip
831310490Scy    %
832310490Scy    % \vadjust-items are inserted at the left edge of the type.  So
833310490Scy    % the \llap here moves out into the left-hand margin.
834310490Scy    \llap{%
835310490Scy      %
836310490Scy      % For a thicker or thinner bar, change the `1pt'.
837310490Scy      \vrule height\baselineskip width1pt
838310490Scy      %
839310490Scy      % This is the space between the bar and the text.
840310490Scy      \hskip 12pt
841310490Scy    }%
842310490Scy  }%
843310490Scy}
844310490Scy
845310490Scy% @include FILE -- \input text of FILE.
846310490Scy%
847174294Sobrien\def\include{\parseargusing\filenamecatcodes\includezzz}
848174294Sobrien\def\includezzz#1{%
849174294Sobrien  \pushthisfilestack
85038494Sobrien  \def\thisfile{#1}%
851174294Sobrien  {%
852310490Scy    \makevalueexpandable  % we want to expand any @value in FILE.
853310490Scy    \turnoffactive        % and allow special characters in the expansion
854310490Scy    \indexnofonts         % Allow `@@' and other weird things in file names.
855310490Scy    \wlog{texinfo.tex: doing @include of #1^^J}%
856310490Scy    \edef\temp{\noexpand\input #1 }%
857310490Scy    %
858310490Scy    % This trickery is to read FILE outside of a group, in case it makes
859310490Scy    % definitions, etc.
860174294Sobrien    \expandafter
861174294Sobrien  }\temp
862174294Sobrien  \popthisfilestack
863174294Sobrien}
864174294Sobrien\def\filenamecatcodes{%
865174294Sobrien  \catcode`\\=\other
866174294Sobrien  \catcode`~=\other
867174294Sobrien  \catcode`^=\other
868174294Sobrien  \catcode`_=\other
869174294Sobrien  \catcode`|=\other
870174294Sobrien  \catcode`<=\other
871174294Sobrien  \catcode`>=\other
872174294Sobrien  \catcode`+=\other
873174294Sobrien  \catcode`-=\other
874310490Scy  \catcode`\`=\other
875310490Scy  \catcode`\'=\other
876174294Sobrien}
87738494Sobrien
878174294Sobrien\def\pushthisfilestack{%
879174294Sobrien  \expandafter\pushthisfilestackX\popthisfilestack\StackTerm
880174294Sobrien}
881174294Sobrien\def\pushthisfilestackX{%
882174294Sobrien  \expandafter\pushthisfilestackY\thisfile\StackTerm
883174294Sobrien}
884174294Sobrien\def\pushthisfilestackY #1\StackTerm #2\StackTerm {%
885174294Sobrien  \gdef\popthisfilestack{\gdef\thisfile{#1}\gdef\popthisfilestack{#2}}%
886174294Sobrien}
887174294Sobrien
888174294Sobrien\def\popthisfilestack{\errthisfilestackempty}
889174294Sobrien\def\errthisfilestackempty{\errmessage{Internal error:
890174294Sobrien  the stack of filenames is empty.}}
891310490Scy%
89238494Sobrien\def\thisfile{}
89338494Sobrien
894174294Sobrien% @center line
895174294Sobrien% outputs that line, centered.
896174294Sobrien%
897174294Sobrien\parseargdef\center{%
898174294Sobrien  \ifhmode
899310490Scy    \let\centersub\centerH
900174294Sobrien  \else
901310490Scy    \let\centersub\centerV
902174294Sobrien  \fi
903310490Scy  \centersub{\hfil \ignorespaces#1\unskip \hfil}%
904310490Scy  \let\centersub\relax % don't let the definition persist, just in case
905174294Sobrien}
906310490Scy\def\centerH#1{{%
907310490Scy  \hfil\break
908310490Scy  \advance\hsize by -\leftskip
909310490Scy  \advance\hsize by -\rightskip
910310490Scy  \line{#1}%
911310490Scy  \break
912310490Scy}}
913310490Scy%
914310490Scy\newcount\centerpenalty
915310490Scy\def\centerV#1{%
916310490Scy  % The idea here is the same as in \startdefun, \cartouche, etc.: if
917310490Scy  % @center is the first thing after a section heading, we need to wipe
918310490Scy  % out the negative parskip inserted by \sectionheading, but still
919310490Scy  % prevent a page break here.
920310490Scy  \centerpenalty = \lastpenalty
921310490Scy  \ifnum\centerpenalty>10000 \vskip\parskip \fi
922310490Scy  \ifnum\centerpenalty>9999 \penalty\centerpenalty \fi
923310490Scy  \line{\kern\leftskip #1\kern\rightskip}%
924174294Sobrien}
92538494Sobrien
92638494Sobrien% @sp n   outputs n lines of vertical space
927310490Scy%
928174294Sobrien\parseargdef\sp{\vskip #1\baselineskip}
92938494Sobrien
93038494Sobrien% @comment ...line which is ignored...
93138494Sobrien% @c is the same as @comment
93238494Sobrien% @ignore ... @end ignore  is another way to write a comment
933310490Scy%
93442629Sobrien\def\comment{\begingroup \catcode`\^^M=\other%
93542629Sobrien\catcode`\@=\other \catcode`\{=\other \catcode`\}=\other%
93642629Sobrien\commentxxx}
93742629Sobrien{\catcode`\^^M=\other \gdef\commentxxx#1^^M{\endgroup}}
938310490Scy%
93938494Sobrien\let\c=\comment
94038494Sobrien
94182794Sobrien% @paragraphindent NCHARS
94282794Sobrien% We'll use ems for NCHARS, close enough.
943174294Sobrien% NCHARS can also be the word `asis' or `none'.
944174294Sobrien% We cannot feasibly implement @paragraphindent asis, though.
945174294Sobrien%
94682794Sobrien\def\asisword{asis} % no translation, these are keywords
94782794Sobrien\def\noneword{none}
94838494Sobrien%
949174294Sobrien\parseargdef\paragraphindent{%
95082794Sobrien  \def\temp{#1}%
95182794Sobrien  \ifx\temp\asisword
95238494Sobrien  \else
95382794Sobrien    \ifx\temp\noneword
95482794Sobrien      \defaultparindent = 0pt
95582794Sobrien    \else
95682794Sobrien      \defaultparindent = #1em
95782794Sobrien    \fi
95838494Sobrien  \fi
95982794Sobrien  \parindent = \defaultparindent
96038494Sobrien}
96138494Sobrien
96282794Sobrien% @exampleindent NCHARS
96382794Sobrien% We'll use ems for NCHARS like @paragraphindent.
96482794Sobrien% It seems @exampleindent asis isn't necessary, but
96582794Sobrien% I preserve it to make it similar to @paragraphindent.
966174294Sobrien\parseargdef\exampleindent{%
96782794Sobrien  \def\temp{#1}%
96882794Sobrien  \ifx\temp\asisword
96938494Sobrien  \else
97082794Sobrien    \ifx\temp\noneword
97182794Sobrien      \lispnarrowing = 0pt
97282794Sobrien    \else
97382794Sobrien      \lispnarrowing = #1em
97482794Sobrien    \fi
97538494Sobrien  \fi
97638494Sobrien}
97738494Sobrien
978174294Sobrien% @firstparagraphindent WORD
979174294Sobrien% If WORD is `none', then suppress indentation of the first paragraph
980174294Sobrien% after a section heading.  If WORD is `insert', then do indent at such
981174294Sobrien% paragraphs.
982174294Sobrien%
983174294Sobrien% The paragraph indentation is suppressed or not by calling
984174294Sobrien% \suppressfirstparagraphindent, which the sectioning commands do.
985174294Sobrien% We switch the definition of this back and forth according to WORD.
986174294Sobrien% By default, we suppress indentation.
987174294Sobrien%
988174294Sobrien\def\suppressfirstparagraphindent{\dosuppressfirstparagraphindent}
989174294Sobrien\def\insertword{insert}
990174294Sobrien%
991174294Sobrien\parseargdef\firstparagraphindent{%
992174294Sobrien  \def\temp{#1}%
993174294Sobrien  \ifx\temp\noneword
994174294Sobrien    \let\suppressfirstparagraphindent = \dosuppressfirstparagraphindent
995174294Sobrien  \else\ifx\temp\insertword
996174294Sobrien    \let\suppressfirstparagraphindent = \relax
997174294Sobrien  \else
998174294Sobrien    \errhelp = \EMsimple
999174294Sobrien    \errmessage{Unknown @firstparagraphindent option `\temp'}%
1000174294Sobrien  \fi\fi
1001174294Sobrien}
1002174294Sobrien
1003174294Sobrien% Here is how we actually suppress indentation.  Redefine \everypar to
1004174294Sobrien% \kern backwards by \parindent, and then reset itself to empty.
1005174294Sobrien%
1006174294Sobrien% We also make \indent itself not actually do anything until the next
1007174294Sobrien% paragraph.
1008174294Sobrien%
1009174294Sobrien\gdef\dosuppressfirstparagraphindent{%
1010174294Sobrien  \gdef\indent{%
1011174294Sobrien    \restorefirstparagraphindent
1012174294Sobrien    \indent
1013174294Sobrien  }%
1014174294Sobrien  \gdef\noindent{%
1015174294Sobrien    \restorefirstparagraphindent
1016174294Sobrien    \noindent
1017174294Sobrien  }%
1018174294Sobrien  \global\everypar = {%
1019174294Sobrien    \kern -\parindent
1020174294Sobrien    \restorefirstparagraphindent
1021174294Sobrien  }%
1022174294Sobrien}
1023174294Sobrien
1024174294Sobrien\gdef\restorefirstparagraphindent{%
1025174294Sobrien  \global \let \indent = \ptexindent
1026174294Sobrien  \global \let \noindent = \ptexnoindent
1027174294Sobrien  \global \everypar = {}%
1028174294Sobrien}
1029174294Sobrien
1030174294Sobrien
103138494Sobrien% @refill is a no-op.
103238494Sobrien\let\refill=\relax
103338494Sobrien
103442629Sobrien% If working on a large document in chapters, it is convenient to
103542629Sobrien% be able to disable indexing, cross-referencing, and contents, for test runs.
103642629Sobrien% This is done with @novalidate (before @setfilename).
103742629Sobrien%
103842629Sobrien\newif\iflinks \linkstrue % by default we want the aux files.
103942629Sobrien\let\novalidate = \linksfalse
104042629Sobrien
104138494Sobrien% @setfilename is done at the beginning of every texinfo file.
104238494Sobrien% So open here the files we need to have open while reading the input.
104338494Sobrien% This makes it possible to make a .fmt file for texinfo.
104438494Sobrien\def\setfilename{%
1045174294Sobrien   \fixbackslash  % Turn off hack to swallow `\input texinfo'.
104682794Sobrien   \iflinks
1047174294Sobrien     \tryauxfile
1048174294Sobrien     % Open the new aux file.  TeX will close it automatically at exit.
1049174294Sobrien     \immediate\openout\auxfile=\jobname.aux
105042629Sobrien   \fi % \openindices needs to do some work in any case.
105138494Sobrien   \openindices
1052174294Sobrien   \let\setfilename=\comment % Ignore extra @setfilename cmds.
105338494Sobrien   %
105438494Sobrien   % If texinfo.cnf is present on the system, read it.
105538494Sobrien   % Useful for site-wide @afourpaper, etc.
105638494Sobrien   \openin 1 texinfo.cnf
1057174294Sobrien   \ifeof 1 \else \input texinfo.cnf \fi
1058174294Sobrien   \closein 1
105938494Sobrien   %
106038494Sobrien   \comment % Ignore the actual filename.
106138494Sobrien}
106238494Sobrien
106342629Sobrien% Called from \setfilename.
106482794Sobrien%
106542629Sobrien\def\openindices{%
106642629Sobrien  \newindex{cp}%
106742629Sobrien  \newcodeindex{fn}%
106842629Sobrien  \newcodeindex{vr}%
106942629Sobrien  \newcodeindex{tp}%
107042629Sobrien  \newcodeindex{ky}%
107142629Sobrien  \newcodeindex{pg}%
107242629Sobrien}
107342629Sobrien
107438494Sobrien% @bye.
107538494Sobrien\outer\def\bye{\pagealignmacro\tracingstats=1\ptexend}
107638494Sobrien
107738494Sobrien
107882794Sobrien\message{pdf,}
107982794Sobrien% adobe `portable' document format
108082794Sobrien\newcount\tempnum
108182794Sobrien\newcount\lnkcount
108282794Sobrien\newtoks\filename
108382794Sobrien\newcount\filenamelength
108482794Sobrien\newcount\pgn
108582794Sobrien\newtoks\toksA
108682794Sobrien\newtoks\toksB
108782794Sobrien\newtoks\toksC
108882794Sobrien\newtoks\toksD
108982794Sobrien\newbox\boxA
109082794Sobrien\newcount\countA
109182794Sobrien\newif\ifpdf
109282794Sobrien\newif\ifpdfmakepagedest
109382794Sobrien
1094174294Sobrien% when pdftex is run in dvi mode, \pdfoutput is defined (so \pdfoutput=1
1095310490Scy% can be set).  So we test for \relax and 0 as well as being undefined.
1096310490Scy\ifx\pdfoutput\thisisundefined
109782794Sobrien\else
1098174294Sobrien  \ifx\pdfoutput\relax
1099174294Sobrien  \else
1100174294Sobrien    \ifcase\pdfoutput
1101174294Sobrien    \else
1102174294Sobrien      \pdftrue
1103174294Sobrien    \fi
1104174294Sobrien  \fi
1105174294Sobrien\fi
1106310490Scy
1107310490Scy% PDF uses PostScript string constants for the names of xref targets,
1108310490Scy% for display in the outlines, and in other places.  Thus, we have to
1109310490Scy% double any backslashes.  Otherwise, a name like "\node" will be
1110310490Scy% interpreted as a newline (\n), followed by o, d, e.  Not good.
1111310490Scy% 
1112310490Scy% See http://www.ntg.nl/pipermail/ntg-pdftex/2004-July/000654.html and
1113310490Scy% related messages.  The final outcome is that it is up to the TeX user
1114310490Scy% to double the backslashes and otherwise make the string valid, so
1115310490Scy% that's what we do.  pdftex 1.30.0 (ca.2005) introduced a primitive to
1116310490Scy% do this reliably, so we use it.
1117310490Scy
1118310490Scy% #1 is a control sequence in which to do the replacements,
1119310490Scy% which we \xdef.
1120310490Scy\def\txiescapepdf#1{%
1121310490Scy  \ifx\pdfescapestring\thisisundefined
1122310490Scy    % No primitive available; should we give a warning or log?
1123310490Scy    % Many times it won't matter.
1124310490Scy  \else
1125310490Scy    % The expandable \pdfescapestring primitive escapes parentheses,
1126310490Scy    % backslashes, and other special chars.
1127310490Scy    \xdef#1{\pdfescapestring{#1}}%
1128310490Scy  \fi
1129310490Scy}
1130310490Scy
1131310490Scy\newhelp\nopdfimagehelp{Texinfo supports .png, .jpg, .jpeg, and .pdf images
1132310490Scywith PDF output, and none of those formats could be found.  (.eps cannot
1133310490Scybe supported due to the design of the PDF format; use regular TeX (DVI
1134310490Scyoutput) for that.)}
1135310490Scy
1136174294Sobrien\ifpdf
1137310490Scy  %
1138310490Scy  % Color manipulation macros based on pdfcolor.tex,
1139310490Scy  % except using rgb instead of cmyk; the latter is said to render as a
1140310490Scy  % very dark gray on-screen and a very dark halftone in print, instead
1141310490Scy  % of actual black.
1142310490Scy  \def\rgbDarkRed{0.50 0.09 0.12}
1143310490Scy  \def\rgbBlack{0 0 0}
1144310490Scy  %
1145310490Scy  % k sets the color for filling (usual text, etc.);
1146310490Scy  % K sets the color for stroking (thin rules, e.g., normal _'s).
1147310490Scy  \def\pdfsetcolor#1{\pdfliteral{#1 rg  #1 RG}}
1148310490Scy  %
1149310490Scy  % Set color, and create a mark which defines \thiscolor accordingly,
1150310490Scy  % so that \makeheadline knows which color to restore.
1151310490Scy  \def\setcolor#1{%
1152310490Scy    \xdef\lastcolordefs{\gdef\noexpand\thiscolor{#1}}%
1153310490Scy    \domark
1154310490Scy    \pdfsetcolor{#1}%
1155310490Scy  }
1156310490Scy  %
1157310490Scy  \def\maincolor{\rgbBlack}
1158310490Scy  \pdfsetcolor{\maincolor}
1159310490Scy  \edef\thiscolor{\maincolor}
1160310490Scy  \def\lastcolordefs{}
1161310490Scy  %
1162310490Scy  \def\makefootline{%
1163310490Scy    \baselineskip24pt
1164310490Scy    \line{\pdfsetcolor{\maincolor}\the\footline}%
1165310490Scy  }
1166310490Scy  %
1167310490Scy  \def\makeheadline{%
1168310490Scy    \vbox to 0pt{%
1169310490Scy      \vskip-22.5pt
1170310490Scy      \line{%
1171310490Scy        \vbox to8.5pt{}%
1172310490Scy        % Extract \thiscolor definition from the marks.
1173310490Scy        \getcolormarks
1174310490Scy        % Typeset the headline with \maincolor, then restore the color.
1175310490Scy        \pdfsetcolor{\maincolor}\the\headline\pdfsetcolor{\thiscolor}%
1176310490Scy      }%
1177310490Scy      \vss
1178310490Scy    }%
1179310490Scy    \nointerlineskip
1180310490Scy  }
1181310490Scy  %
1182310490Scy  %
1183310490Scy  \pdfcatalog{/PageMode /UseOutlines}
1184310490Scy  %
1185310490Scy  % #1 is image name, #2 width (might be empty/whitespace), #3 height (ditto).
118682794Sobrien  \def\dopdfimage#1#2#3{%
1187310490Scy    \def\pdfimagewidth{#2}\setbox0 = \hbox{\ignorespaces #2}%
1188310490Scy    \def\pdfimageheight{#3}\setbox2 = \hbox{\ignorespaces #3}%
1189310490Scy    %
1190310490Scy    % pdftex (and the PDF format) support .pdf, .png, .jpg (among
1191310490Scy    % others).  Let's try in that order, PDF first since if
1192310490Scy    % someone has a scalable image, presumably better to use that than a
1193310490Scy    % bitmap.
1194310490Scy    \let\pdfimgext=\empty
1195310490Scy    \begingroup
1196310490Scy      \openin 1 #1.pdf \ifeof 1
1197310490Scy        \openin 1 #1.PDF \ifeof 1
1198310490Scy          \openin 1 #1.png \ifeof 1
1199310490Scy            \openin 1 #1.jpg \ifeof 1
1200310490Scy              \openin 1 #1.jpeg \ifeof 1
1201310490Scy                \openin 1 #1.JPG \ifeof 1
1202310490Scy                  \errhelp = \nopdfimagehelp
1203310490Scy                  \errmessage{Could not find image file #1 for pdf}%
1204310490Scy                \else \gdef\pdfimgext{JPG}%
1205310490Scy                \fi
1206310490Scy              \else \gdef\pdfimgext{jpeg}%
1207310490Scy              \fi
1208310490Scy            \else \gdef\pdfimgext{jpg}%
1209310490Scy            \fi
1210310490Scy          \else \gdef\pdfimgext{png}%
1211310490Scy          \fi
1212310490Scy        \else \gdef\pdfimgext{PDF}%
1213310490Scy        \fi
1214310490Scy      \else \gdef\pdfimgext{pdf}%
1215310490Scy      \fi
1216310490Scy      \closein 1
1217310490Scy    \endgroup
1218310490Scy    %
1219310490Scy    % without \immediate, ancient pdftex seg faults when the same image is
1220119679Smbr    % included twice.  (Version 3.14159-pre-1.0-unofficial-20010704.)
122182794Sobrien    \ifnum\pdftexversion < 14
1222119679Smbr      \immediate\pdfimage
122382794Sobrien    \else
1224119679Smbr      \immediate\pdfximage
122582794Sobrien    \fi
1226310490Scy      \ifdim \wd0 >0pt width \pdfimagewidth \fi
1227310490Scy      \ifdim \wd2 >0pt height \pdfimageheight \fi
122882794Sobrien      \ifnum\pdftexversion<13
1229310490Scy         #1.\pdfimgext
123082794Sobrien       \else
1231310490Scy         {#1.\pdfimgext}%
123282794Sobrien       \fi
123382794Sobrien    \ifnum\pdftexversion < 14 \else
123482794Sobrien      \pdfrefximage \pdflastximage
123582794Sobrien    \fi}
1236310490Scy  %
1237174294Sobrien  \def\pdfmkdest#1{{%
1238310490Scy    % We have to set dummies so commands such as @code, and characters
1239310490Scy    % such as \, aren't expanded when present in a section title.
1240310490Scy    \indexnofonts
1241310490Scy    \turnoffactive
1242310490Scy    \makevalueexpandable
1243310490Scy    \def\pdfdestname{#1}%
1244310490Scy    \txiescapepdf\pdfdestname
1245310490Scy    \safewhatsit{\pdfdest name{\pdfdestname} xyz}%
1246174294Sobrien  }}
1247310490Scy  %
1248310490Scy  % used to mark target names; must be expandable.
1249119679Smbr  \def\pdfmkpgn#1{#1}
1250310490Scy  %
1251310490Scy  % by default, use a color that is dark enough to print on paper as
1252310490Scy  % nearly black, but still distinguishable for online viewing.
1253310490Scy  \def\urlcolor{\rgbDarkRed}
1254310490Scy  \def\linkcolor{\rgbDarkRed}
1255310490Scy  \def\endlink{\setcolor{\maincolor}\pdfendlink}
1256310490Scy  %
125782794Sobrien  % Adding outlines to PDF; macros for calculating structure of outlines
125882794Sobrien  % come from Petr Olsak
125982794Sobrien  \def\expnumber#1{\expandafter\ifx\csname#1\endcsname\relax 0%
126082794Sobrien    \else \csname#1\endcsname \fi}
126182794Sobrien  \def\advancenumber#1{\tempnum=\expnumber{#1}\relax
1262174294Sobrien    \advance\tempnum by 1
126382794Sobrien    \expandafter\xdef\csname#1\endcsname{\the\tempnum}}
1264174294Sobrien  %
1265310490Scy  % #1 is the section text, which is what will be displayed in the
1266310490Scy  % outline by the pdf viewer.  #2 is the pdf expression for the number
1267310490Scy  % of subentries (or empty, for subsubsections).  #3 is the node text,
1268310490Scy  % which might be empty if this toc entry had no corresponding node.
1269310490Scy  % #4 is the page number
1270174294Sobrien  %
1271174294Sobrien  \def\dopdfoutline#1#2#3#4{%
1272174294Sobrien    % Generate a link to the node text if that exists; else, use the
1273174294Sobrien    % page number.  We could generate a destination for the section
1274174294Sobrien    % text in the case where a section has no node, but it doesn't
1275310490Scy    % seem worth the trouble, since most documents are normally structured.
1276310490Scy    \edef\pdfoutlinedest{#3}%
1277310490Scy    \ifx\pdfoutlinedest\empty
1278310490Scy      \def\pdfoutlinedest{#4}%
1279310490Scy    \else
1280310490Scy      \txiescapepdf\pdfoutlinedest
1281310490Scy    \fi
1282174294Sobrien    %
1283310490Scy    % Also escape PDF chars in the display string.
1284310490Scy    \edef\pdfoutlinetext{#1}%
1285310490Scy    \txiescapepdf\pdfoutlinetext
1286310490Scy    %
1287310490Scy    \pdfoutline goto name{\pdfmkpgn{\pdfoutlinedest}}#2{\pdfoutlinetext}%
1288174294Sobrien  }
1289174294Sobrien  %
1290174294Sobrien  \def\pdfmakeoutlines{%
1291174294Sobrien    \begingroup
1292174294Sobrien      % Read toc silently, to get counts of subentries for \pdfoutline.
1293310490Scy      \def\partentry##1##2##3##4{}% ignore parts in the outlines
1294174294Sobrien      \def\numchapentry##1##2##3##4{%
1295174294Sobrien	\def\thischapnum{##2}%
1296310490Scy	\def\thissecnum{0}%
1297310490Scy	\def\thissubsecnum{0}%
1298174294Sobrien      }%
1299174294Sobrien      \def\numsecentry##1##2##3##4{%
1300174294Sobrien	\advancenumber{chap\thischapnum}%
1301174294Sobrien	\def\thissecnum{##2}%
1302310490Scy	\def\thissubsecnum{0}%
1303174294Sobrien      }%
1304174294Sobrien      \def\numsubsecentry##1##2##3##4{%
1305174294Sobrien	\advancenumber{sec\thissecnum}%
1306174294Sobrien	\def\thissubsecnum{##2}%
1307174294Sobrien      }%
1308174294Sobrien      \def\numsubsubsecentry##1##2##3##4{%
1309174294Sobrien	\advancenumber{subsec\thissubsecnum}%
1310174294Sobrien      }%
1311310490Scy      \def\thischapnum{0}%
1312310490Scy      \def\thissecnum{0}%
1313310490Scy      \def\thissubsecnum{0}%
1314174294Sobrien      %
1315174294Sobrien      % use \def rather than \let here because we redefine \chapentry et
1316174294Sobrien      % al. a second time, below.
1317174294Sobrien      \def\appentry{\numchapentry}%
1318174294Sobrien      \def\appsecentry{\numsecentry}%
1319174294Sobrien      \def\appsubsecentry{\numsubsecentry}%
1320174294Sobrien      \def\appsubsubsecentry{\numsubsubsecentry}%
1321174294Sobrien      \def\unnchapentry{\numchapentry}%
1322174294Sobrien      \def\unnsecentry{\numsecentry}%
1323174294Sobrien      \def\unnsubsecentry{\numsubsecentry}%
1324174294Sobrien      \def\unnsubsubsecentry{\numsubsubsecentry}%
1325310490Scy      \readdatafile{toc}%
1326174294Sobrien      %
1327174294Sobrien      % Read toc second time, this time actually producing the outlines.
1328174294Sobrien      % The `-' means take the \expnumber as the absolute number of
1329174294Sobrien      % subentries, which we calculated on our first read of the .toc above.
1330174294Sobrien      %
1331174294Sobrien      % We use the node names as the destinations.
1332174294Sobrien      \def\numchapentry##1##2##3##4{%
1333174294Sobrien        \dopdfoutline{##1}{count-\expnumber{chap##2}}{##3}{##4}}%
1334174294Sobrien      \def\numsecentry##1##2##3##4{%
1335174294Sobrien        \dopdfoutline{##1}{count-\expnumber{sec##2}}{##3}{##4}}%
1336174294Sobrien      \def\numsubsecentry##1##2##3##4{%
1337174294Sobrien        \dopdfoutline{##1}{count-\expnumber{subsec##2}}{##3}{##4}}%
1338174294Sobrien      \def\numsubsubsecentry##1##2##3##4{% count is always zero
1339174294Sobrien        \dopdfoutline{##1}{}{##3}{##4}}%
1340174294Sobrien      %
1341174294Sobrien      % PDF outlines are displayed using system fonts, instead of
1342174294Sobrien      % document fonts.  Therefore we cannot use special characters,
1343174294Sobrien      % since the encoding is unknown.  For example, the eogonek from
1344174294Sobrien      % Latin 2 (0xea) gets translated to a | character.  Info from
1345174294Sobrien      % Staszek Wawrykiewicz, 19 Jan 2004 04:09:24 +0100.
1346174294Sobrien      %
1347310490Scy      % TODO this right, we have to translate 8-bit characters to
1348310490Scy      % their "best" equivalent, based on the @documentencoding.  Too
1349310490Scy      % much work for too little return.  Just use the ASCII equivalents
1350310490Scy      % we use for the index sort strings.
1351310490Scy      % 
1352174294Sobrien      \indexnofonts
1353310490Scy      \setupdatafile
1354310490Scy      % We can have normal brace characters in the PDF outlines, unlike
1355310490Scy      % Texinfo index files.  So set that up.
1356310490Scy      \def\{{\lbracecharliteral}%
1357310490Scy      \def\}{\rbracecharliteral}%
1358310490Scy      \catcode`\\=\active \otherbackslash
1359310490Scy      \input \tocreadfilename
1360174294Sobrien    \endgroup
1361174294Sobrien  }
1362310490Scy  {\catcode`[=1 \catcode`]=2
1363310490Scy   \catcode`{=\other \catcode`}=\other
1364310490Scy   \gdef\lbracecharliteral[{]%
1365310490Scy   \gdef\rbracecharliteral[}]%
1366310490Scy  ]
1367174294Sobrien  %
136882794Sobrien  \def\skipspaces#1{\def\PP{#1}\def\D{|}%
136982794Sobrien    \ifx\PP\D\let\nextsp\relax
137082794Sobrien    \else\let\nextsp\skipspaces
1371310490Scy      \addtokens{\filename}{\PP}%
1372310490Scy      \advance\filenamelength by 1
137382794Sobrien    \fi
137482794Sobrien    \nextsp}
1375310490Scy  \def\getfilename#1{%
1376310490Scy    \filenamelength=0
1377310490Scy    % If we don't expand the argument now, \skipspaces will get
1378310490Scy    % snagged on things like "@value{foo}".
1379310490Scy    \edef\temp{#1}%
1380310490Scy    \expandafter\skipspaces\temp|\relax
1381310490Scy  }
138282794Sobrien  \ifnum\pdftexversion < 14
138382794Sobrien    \let \startlink \pdfannotlink
138482794Sobrien  \else
138582794Sobrien    \let \startlink \pdfstartlink
138682794Sobrien  \fi
1387310490Scy  % make a live url in pdf output.
138882794Sobrien  \def\pdfurl#1{%
138982794Sobrien    \begingroup
1390310490Scy      % it seems we really need yet another set of dummies; have not
1391310490Scy      % tried to figure out what each command should do in the context
1392310490Scy      % of @url.  for now, just make @/ a no-op, that's the only one
1393310490Scy      % people have actually reported a problem with.
1394310490Scy      %
1395310490Scy      \normalturnoffactive
1396310490Scy      \def\@{@}%
1397310490Scy      \let\/=\empty
1398174294Sobrien      \makevalueexpandable
1399310490Scy      % do we want to go so far as to use \indexnofonts instead of just
1400310490Scy      % special-casing \var here?
1401310490Scy      \def\var##1{##1}%
1402310490Scy      %
1403310490Scy      \leavevmode\setcolor{\urlcolor}%
140482794Sobrien      \startlink attr{/Border [0 0 0]}%
140582794Sobrien        user{/Subtype /Link /A << /S /URI /URI (#1) >>}%
140682794Sobrien    \endgroup}
140782794Sobrien  \def\pdfgettoks#1.{\setbox\boxA=\hbox{\toksA={#1.}\toksB={}\maketoks}}
140882794Sobrien  \def\addtokens#1#2{\edef\addtoks{\noexpand#1={\the#1#2}}\addtoks}
140982794Sobrien  \def\adn#1{\addtokens{\toksC}{#1}\global\countA=1\let\next=\maketoks}
141082794Sobrien  \def\poptoks#1#2|ENDTOKS|{\let\first=#1\toksD={#1}\toksA={#2}}
141182794Sobrien  \def\maketoks{%
1412174294Sobrien    \expandafter\poptoks\the\toksA|ENDTOKS|\relax
141382794Sobrien    \ifx\first0\adn0
141482794Sobrien    \else\ifx\first1\adn1 \else\ifx\first2\adn2 \else\ifx\first3\adn3
141582794Sobrien    \else\ifx\first4\adn4 \else\ifx\first5\adn5 \else\ifx\first6\adn6
1416174294Sobrien    \else\ifx\first7\adn7 \else\ifx\first8\adn8 \else\ifx\first9\adn9
141782794Sobrien    \else
141882794Sobrien      \ifnum0=\countA\else\makelink\fi
141982794Sobrien      \ifx\first.\let\next=\done\else
142082794Sobrien        \let\next=\maketoks
142182794Sobrien        \addtokens{\toksB}{\the\toksD}
142282794Sobrien        \ifx\first,\addtokens{\toksB}{\space}\fi
142382794Sobrien      \fi
142482794Sobrien    \fi\fi\fi\fi\fi\fi\fi\fi\fi\fi
142582794Sobrien    \next}
142682794Sobrien  \def\makelink{\addtokens{\toksB}%
142782794Sobrien    {\noexpand\pdflink{\the\toksC}}\toksC={}\global\countA=0}
142882794Sobrien  \def\pdflink#1{%
142982794Sobrien    \startlink attr{/Border [0 0 0]} goto name{\pdfmkpgn{#1}}
1430310490Scy    \setcolor{\linkcolor}#1\endlink}
143182794Sobrien  \def\done{\edef\st{\global\noexpand\toksA={\the\toksB}}\st}
1432174294Sobrien\else
1433310490Scy  % non-pdf mode
1434174294Sobrien  \let\pdfmkdest = \gobble
1435174294Sobrien  \let\pdfurl = \gobble
1436174294Sobrien  \let\endlink = \relax
1437310490Scy  \let\setcolor = \gobble
1438310490Scy  \let\pdfsetcolor = \gobble
1439174294Sobrien  \let\pdfmakeoutlines = \relax
1440174294Sobrien\fi  % \ifx\pdfoutput
144182794Sobrien
144282794Sobrien
144338494Sobrien\message{fonts,}
144438494Sobrien
1445174294Sobrien% Change the current font style to #1, remembering it in \curfontstyle.
1446174294Sobrien% For now, we do not accumulate font styles: @b{@i{foo}} prints foo in
1447174294Sobrien% italics, not bold italics.
1448174294Sobrien%
1449174294Sobrien\def\setfontstyle#1{%
1450174294Sobrien  \def\curfontstyle{#1}% not as a control sequence, because we are \edef'd.
1451174294Sobrien  \csname ten#1\endcsname  % change the current font
1452174294Sobrien}
1453174294Sobrien
1454174294Sobrien% Select #1 fonts with the current style.
1455174294Sobrien%
1456174294Sobrien\def\selectfonts#1{\csname #1fonts\endcsname \csname\curfontstyle\endcsname}
1457174294Sobrien
1458174294Sobrien\def\rm{\fam=0 \setfontstyle{rm}}
1459174294Sobrien\def\it{\fam=\itfam \setfontstyle{it}}
1460174294Sobrien\def\sl{\fam=\slfam \setfontstyle{sl}}
1461310490Scy\def\bf{\fam=\bffam \setfontstyle{bf}}\def\bfstylename{bf}
1462174294Sobrien\def\tt{\fam=\ttfam \setfontstyle{tt}}
1463174294Sobrien
1464310490Scy% Unfortunately, we have to override this for titles and the like, since
1465310490Scy% in those cases "rm" is bold.  Sigh.
1466310490Scy\def\rmisbold{\rm\def\curfontstyle{bf}}
1467310490Scy
146842629Sobrien% Texinfo sort of supports the sans serif font style, which plain TeX does not.
1469174294Sobrien% So we set up a \sf.
147038494Sobrien\newfam\sffam
1471174294Sobrien\def\sf{\fam=\sffam \setfontstyle{sf}}
147238494Sobrien\let\li = \sf % Sometimes we call it \li, not \sf.
147338494Sobrien
1474174294Sobrien% We don't need math for this font style.
1475174294Sobrien\def\ttsl{\setfontstyle{ttsl}}
147638494Sobrien
147782794Sobrien
147882794Sobrien% Set the baselineskip to #1, and the lineskip and strut size
147982794Sobrien% correspondingly.  There is no deep meaning behind these magic numbers
148082794Sobrien% used as factors; they just match (closely enough) what Knuth defined.
148182794Sobrien%
148282794Sobrien\def\lineskipfactor{.08333}
148382794Sobrien\def\strutheightpercent{.70833}
148482794Sobrien\def\strutdepthpercent {.29167}
148582794Sobrien%
1486310490Scy% can get a sort of poor man's double spacing by redefining this.
1487310490Scy\def\baselinefactor{1}
1488310490Scy%
1489310490Scy\newdimen\textleading
149082794Sobrien\def\setleading#1{%
1491310490Scy  \dimen0 = #1\relax
1492310490Scy  \normalbaselineskip = \baselinefactor\dimen0
149382794Sobrien  \normallineskip = \lineskipfactor\normalbaselineskip
149482794Sobrien  \normalbaselines
149582794Sobrien  \setbox\strutbox =\hbox{%
149682794Sobrien    \vrule width0pt height\strutheightpercent\baselineskip
149782794Sobrien                    depth \strutdepthpercent \baselineskip
149882794Sobrien  }%
149982794Sobrien}
150082794Sobrien
1501310490Scy% PDF CMaps.  See also LaTeX's t1.cmap.
1502310490Scy%
1503310490Scy% do nothing with this by default.
1504310490Scy\expandafter\let\csname cmapOT1\endcsname\gobble
1505310490Scy\expandafter\let\csname cmapOT1IT\endcsname\gobble
1506310490Scy\expandafter\let\csname cmapOT1TT\endcsname\gobble
150738494Sobrien
1508310490Scy% if we are producing pdf, and we have \pdffontattr, then define cmaps.
1509310490Scy% (\pdffontattr was introduced many years ago, but people still run
1510310490Scy% older pdftex's; it's easy to conditionalize, so we do.)
1511310490Scy\ifpdf \ifx\pdffontattr\thisisundefined \else
1512310490Scy  \begingroup
1513310490Scy    \catcode`\^^M=\active \def^^M{^^J}% Output line endings as the ^^J char.
1514310490Scy    \catcode`\%=12 \immediate\pdfobj stream {%!PS-Adobe-3.0 Resource-CMap
1515310490Scy%%DocumentNeededResources: ProcSet (CIDInit)
1516310490Scy%%IncludeResource: ProcSet (CIDInit)
1517310490Scy%%BeginResource: CMap (TeX-OT1-0)
1518310490Scy%%Title: (TeX-OT1-0 TeX OT1 0)
1519310490Scy%%Version: 1.000
1520310490Scy%%EndComments
1521310490Scy/CIDInit /ProcSet findresource begin
1522310490Scy12 dict begin
1523310490Scybegincmap
1524310490Scy/CIDSystemInfo
1525310490Scy<< /Registry (TeX)
1526310490Scy/Ordering (OT1)
1527310490Scy/Supplement 0
1528310490Scy>> def
1529310490Scy/CMapName /TeX-OT1-0 def
1530310490Scy/CMapType 2 def
1531310490Scy1 begincodespacerange
1532310490Scy<00> <7F>
1533310490Scyendcodespacerange
1534310490Scy8 beginbfrange
1535310490Scy<00> <01> <0393>
1536310490Scy<09> <0A> <03A8>
1537310490Scy<23> <26> <0023>
1538310490Scy<28> <3B> <0028>
1539310490Scy<3F> <5B> <003F>
1540310490Scy<5D> <5E> <005D>
1541310490Scy<61> <7A> <0061>
1542310490Scy<7B> <7C> <2013>
1543310490Scyendbfrange
1544310490Scy40 beginbfchar
1545310490Scy<02> <0398>
1546310490Scy<03> <039B>
1547310490Scy<04> <039E>
1548310490Scy<05> <03A0>
1549310490Scy<06> <03A3>
1550310490Scy<07> <03D2>
1551310490Scy<08> <03A6>
1552310490Scy<0B> <00660066>
1553310490Scy<0C> <00660069>
1554310490Scy<0D> <0066006C>
1555310490Scy<0E> <006600660069>
1556310490Scy<0F> <00660066006C>
1557310490Scy<10> <0131>
1558310490Scy<11> <0237>
1559310490Scy<12> <0060>
1560310490Scy<13> <00B4>
1561310490Scy<14> <02C7>
1562310490Scy<15> <02D8>
1563310490Scy<16> <00AF>
1564310490Scy<17> <02DA>
1565310490Scy<18> <00B8>
1566310490Scy<19> <00DF>
1567310490Scy<1A> <00E6>
1568310490Scy<1B> <0153>
1569310490Scy<1C> <00F8>
1570310490Scy<1D> <00C6>
1571310490Scy<1E> <0152>
1572310490Scy<1F> <00D8>
1573310490Scy<21> <0021>
1574310490Scy<22> <201D>
1575310490Scy<27> <2019>
1576310490Scy<3C> <00A1>
1577310490Scy<3D> <003D>
1578310490Scy<3E> <00BF>
1579310490Scy<5C> <201C>
1580310490Scy<5F> <02D9>
1581310490Scy<60> <2018>
1582310490Scy<7D> <02DD>
1583310490Scy<7E> <007E>
1584310490Scy<7F> <00A8>
1585310490Scyendbfchar
1586310490Scyendcmap
1587310490ScyCMapName currentdict /CMap defineresource pop
1588310490Scyend
1589310490Scyend
1590310490Scy%%EndResource
1591310490Scy%%EOF
1592310490Scy    }\endgroup
1593310490Scy  \expandafter\edef\csname cmapOT1\endcsname#1{%
1594310490Scy    \pdffontattr#1{/ToUnicode \the\pdflastobj\space 0 R}%
1595310490Scy  }%
1596310490Scy%
1597310490Scy% \cmapOT1IT
1598310490Scy  \begingroup
1599310490Scy    \catcode`\^^M=\active \def^^M{^^J}% Output line endings as the ^^J char.
1600310490Scy    \catcode`\%=12 \immediate\pdfobj stream {%!PS-Adobe-3.0 Resource-CMap
1601310490Scy%%DocumentNeededResources: ProcSet (CIDInit)
1602310490Scy%%IncludeResource: ProcSet (CIDInit)
1603310490Scy%%BeginResource: CMap (TeX-OT1IT-0)
1604310490Scy%%Title: (TeX-OT1IT-0 TeX OT1IT 0)
1605310490Scy%%Version: 1.000
1606310490Scy%%EndComments
1607310490Scy/CIDInit /ProcSet findresource begin
1608310490Scy12 dict begin
1609310490Scybegincmap
1610310490Scy/CIDSystemInfo
1611310490Scy<< /Registry (TeX)
1612310490Scy/Ordering (OT1IT)
1613310490Scy/Supplement 0
1614310490Scy>> def
1615310490Scy/CMapName /TeX-OT1IT-0 def
1616310490Scy/CMapType 2 def
1617310490Scy1 begincodespacerange
1618310490Scy<00> <7F>
1619310490Scyendcodespacerange
1620310490Scy8 beginbfrange
1621310490Scy<00> <01> <0393>
1622310490Scy<09> <0A> <03A8>
1623310490Scy<25> <26> <0025>
1624310490Scy<28> <3B> <0028>
1625310490Scy<3F> <5B> <003F>
1626310490Scy<5D> <5E> <005D>
1627310490Scy<61> <7A> <0061>
1628310490Scy<7B> <7C> <2013>
1629310490Scyendbfrange
1630310490Scy42 beginbfchar
1631310490Scy<02> <0398>
1632310490Scy<03> <039B>
1633310490Scy<04> <039E>
1634310490Scy<05> <03A0>
1635310490Scy<06> <03A3>
1636310490Scy<07> <03D2>
1637310490Scy<08> <03A6>
1638310490Scy<0B> <00660066>
1639310490Scy<0C> <00660069>
1640310490Scy<0D> <0066006C>
1641310490Scy<0E> <006600660069>
1642310490Scy<0F> <00660066006C>
1643310490Scy<10> <0131>
1644310490Scy<11> <0237>
1645310490Scy<12> <0060>
1646310490Scy<13> <00B4>
1647310490Scy<14> <02C7>
1648310490Scy<15> <02D8>
1649310490Scy<16> <00AF>
1650310490Scy<17> <02DA>
1651310490Scy<18> <00B8>
1652310490Scy<19> <00DF>
1653310490Scy<1A> <00E6>
1654310490Scy<1B> <0153>
1655310490Scy<1C> <00F8>
1656310490Scy<1D> <00C6>
1657310490Scy<1E> <0152>
1658310490Scy<1F> <00D8>
1659310490Scy<21> <0021>
1660310490Scy<22> <201D>
1661310490Scy<23> <0023>
1662310490Scy<24> <00A3>
1663310490Scy<27> <2019>
1664310490Scy<3C> <00A1>
1665310490Scy<3D> <003D>
1666310490Scy<3E> <00BF>
1667310490Scy<5C> <201C>
1668310490Scy<5F> <02D9>
1669310490Scy<60> <2018>
1670310490Scy<7D> <02DD>
1671310490Scy<7E> <007E>
1672310490Scy<7F> <00A8>
1673310490Scyendbfchar
1674310490Scyendcmap
1675310490ScyCMapName currentdict /CMap defineresource pop
1676310490Scyend
1677310490Scyend
1678310490Scy%%EndResource
1679310490Scy%%EOF
1680310490Scy    }\endgroup
1681310490Scy  \expandafter\edef\csname cmapOT1IT\endcsname#1{%
1682310490Scy    \pdffontattr#1{/ToUnicode \the\pdflastobj\space 0 R}%
1683310490Scy  }%
1684310490Scy%
1685310490Scy% \cmapOT1TT
1686310490Scy  \begingroup
1687310490Scy    \catcode`\^^M=\active \def^^M{^^J}% Output line endings as the ^^J char.
1688310490Scy    \catcode`\%=12 \immediate\pdfobj stream {%!PS-Adobe-3.0 Resource-CMap
1689310490Scy%%DocumentNeededResources: ProcSet (CIDInit)
1690310490Scy%%IncludeResource: ProcSet (CIDInit)
1691310490Scy%%BeginResource: CMap (TeX-OT1TT-0)
1692310490Scy%%Title: (TeX-OT1TT-0 TeX OT1TT 0)
1693310490Scy%%Version: 1.000
1694310490Scy%%EndComments
1695310490Scy/CIDInit /ProcSet findresource begin
1696310490Scy12 dict begin
1697310490Scybegincmap
1698310490Scy/CIDSystemInfo
1699310490Scy<< /Registry (TeX)
1700310490Scy/Ordering (OT1TT)
1701310490Scy/Supplement 0
1702310490Scy>> def
1703310490Scy/CMapName /TeX-OT1TT-0 def
1704310490Scy/CMapType 2 def
1705310490Scy1 begincodespacerange
1706310490Scy<00> <7F>
1707310490Scyendcodespacerange
1708310490Scy5 beginbfrange
1709310490Scy<00> <01> <0393>
1710310490Scy<09> <0A> <03A8>
1711310490Scy<21> <26> <0021>
1712310490Scy<28> <5F> <0028>
1713310490Scy<61> <7E> <0061>
1714310490Scyendbfrange
1715310490Scy32 beginbfchar
1716310490Scy<02> <0398>
1717310490Scy<03> <039B>
1718310490Scy<04> <039E>
1719310490Scy<05> <03A0>
1720310490Scy<06> <03A3>
1721310490Scy<07> <03D2>
1722310490Scy<08> <03A6>
1723310490Scy<0B> <2191>
1724310490Scy<0C> <2193>
1725310490Scy<0D> <0027>
1726310490Scy<0E> <00A1>
1727310490Scy<0F> <00BF>
1728310490Scy<10> <0131>
1729310490Scy<11> <0237>
1730310490Scy<12> <0060>
1731310490Scy<13> <00B4>
1732310490Scy<14> <02C7>
1733310490Scy<15> <02D8>
1734310490Scy<16> <00AF>
1735310490Scy<17> <02DA>
1736310490Scy<18> <00B8>
1737310490Scy<19> <00DF>
1738310490Scy<1A> <00E6>
1739310490Scy<1B> <0153>
1740310490Scy<1C> <00F8>
1741310490Scy<1D> <00C6>
1742310490Scy<1E> <0152>
1743310490Scy<1F> <00D8>
1744310490Scy<20> <2423>
1745310490Scy<27> <2019>
1746310490Scy<60> <2018>
1747310490Scy<7F> <00A8>
1748310490Scyendbfchar
1749310490Scyendcmap
1750310490ScyCMapName currentdict /CMap defineresource pop
1751310490Scyend
1752310490Scyend
1753310490Scy%%EndResource
1754310490Scy%%EOF
1755310490Scy    }\endgroup
1756310490Scy  \expandafter\edef\csname cmapOT1TT\endcsname#1{%
1757310490Scy    \pdffontattr#1{/ToUnicode \the\pdflastobj\space 0 R}%
1758310490Scy  }%
1759310490Scy\fi\fi
1760310490Scy
1761310490Scy
1762310490Scy% Set the font macro #1 to the font named \fontprefix#2.
1763310490Scy% #3 is the font's design size, #4 is a scale factor, #5 is the CMap
1764310490Scy% encoding (only OT1, OT1IT and OT1TT are allowed, or empty to omit).
1765310490Scy% Example:
1766310490Scy% #1 = \textrm
1767310490Scy% #2 = \rmshape
1768310490Scy% #3 = 10
1769310490Scy% #4 = \mainmagstep
1770310490Scy% #5 = OT1
1771310490Scy%
1772310490Scy\def\setfont#1#2#3#4#5{%
1773310490Scy  \font#1=\fontprefix#2#3 scaled #4
1774310490Scy  \csname cmap#5\endcsname#1%
1775310490Scy}
1776310490Scy% This is what gets called when #5 of \setfont is empty.
1777310490Scy\let\cmap\gobble
1778310490Scy%
1779310490Scy% (end of cmaps)
1780310490Scy
178138494Sobrien% Use cm as the default font prefix.
178238494Sobrien% To specify the font prefix, you must define \fontprefix
178338494Sobrien% before you read in texinfo.tex.
1784310490Scy\ifx\fontprefix\thisisundefined
178538494Sobrien\def\fontprefix{cm}
178638494Sobrien\fi
178738494Sobrien% Support font families that don't use the same naming scheme as CM.
178838494Sobrien\def\rmshape{r}
1789310490Scy\def\rmbshape{bx}               % where the normal face is bold
179038494Sobrien\def\bfshape{b}
179138494Sobrien\def\bxshape{bx}
179238494Sobrien\def\ttshape{tt}
179338494Sobrien\def\ttbshape{tt}
179438494Sobrien\def\ttslshape{sltt}
179538494Sobrien\def\itshape{ti}
179638494Sobrien\def\itbshape{bxti}
179738494Sobrien\def\slshape{sl}
179838494Sobrien\def\slbshape{bxsl}
179938494Sobrien\def\sfshape{ss}
180038494Sobrien\def\sfbshape{ss}
180138494Sobrien\def\scshape{csc}
180238494Sobrien\def\scbshape{csc}
180338494Sobrien
1804310490Scy% Definitions for a main text size of 11pt.  (The default in Texinfo.)
1805310490Scy%
1806310490Scy\def\definetextfontsizexi{%
1807174294Sobrien% Text fonts (11.2pt, magstep1).
1808310490Scy\def\textnominalsize{11pt}
1809310490Scy\edef\mainmagstep{\magstephalf}
1810310490Scy\setfont\textrm\rmshape{10}{\mainmagstep}{OT1}
1811310490Scy\setfont\texttt\ttshape{10}{\mainmagstep}{OT1TT}
1812310490Scy\setfont\textbf\bfshape{10}{\mainmagstep}{OT1}
1813310490Scy\setfont\textit\itshape{10}{\mainmagstep}{OT1IT}
1814310490Scy\setfont\textsl\slshape{10}{\mainmagstep}{OT1}
1815310490Scy\setfont\textsf\sfshape{10}{\mainmagstep}{OT1}
1816310490Scy\setfont\textsc\scshape{10}{\mainmagstep}{OT1}
1817310490Scy\setfont\textttsl\ttslshape{10}{\mainmagstep}{OT1TT}
181838494Sobrien\font\texti=cmmi10 scaled \mainmagstep
181938494Sobrien\font\textsy=cmsy10 scaled \mainmagstep
1820310490Scy\def\textecsize{1095}
182138494Sobrien
1822174294Sobrien% A few fonts for @defun names and args.
1823310490Scy\setfont\defbf\bfshape{10}{\magstep1}{OT1}
1824310490Scy\setfont\deftt\ttshape{10}{\magstep1}{OT1TT}
1825310490Scy\setfont\defttsl\ttslshape{10}{\magstep1}{OT1TT}
1826174294Sobrien\def\df{\let\tentt=\deftt \let\tenbf = \defbf \let\tenttsl=\defttsl \bf}
182738494Sobrien
182882794Sobrien% Fonts for indices, footnotes, small examples (9pt).
1829310490Scy\def\smallnominalsize{9pt}
1830310490Scy\setfont\smallrm\rmshape{9}{1000}{OT1}
1831310490Scy\setfont\smalltt\ttshape{9}{1000}{OT1TT}
1832310490Scy\setfont\smallbf\bfshape{10}{900}{OT1}
1833310490Scy\setfont\smallit\itshape{9}{1000}{OT1IT}
1834310490Scy\setfont\smallsl\slshape{9}{1000}{OT1}
1835310490Scy\setfont\smallsf\sfshape{9}{1000}{OT1}
1836310490Scy\setfont\smallsc\scshape{10}{900}{OT1}
1837310490Scy\setfont\smallttsl\ttslshape{10}{900}{OT1TT}
183882794Sobrien\font\smalli=cmmi9
183982794Sobrien\font\smallsy=cmsy9
1840310490Scy\def\smallecsize{0900}
184138494Sobrien
184282794Sobrien% Fonts for small examples (8pt).
1843310490Scy\def\smallernominalsize{8pt}
1844310490Scy\setfont\smallerrm\rmshape{8}{1000}{OT1}
1845310490Scy\setfont\smallertt\ttshape{8}{1000}{OT1TT}
1846310490Scy\setfont\smallerbf\bfshape{10}{800}{OT1}
1847310490Scy\setfont\smallerit\itshape{8}{1000}{OT1IT}
1848310490Scy\setfont\smallersl\slshape{8}{1000}{OT1}
1849310490Scy\setfont\smallersf\sfshape{8}{1000}{OT1}
1850310490Scy\setfont\smallersc\scshape{10}{800}{OT1}
1851310490Scy\setfont\smallerttsl\ttslshape{10}{800}{OT1TT}
185282794Sobrien\font\smalleri=cmmi8
185382794Sobrien\font\smallersy=cmsy8
1854310490Scy\def\smallerecsize{0800}
185582794Sobrien
1856174294Sobrien% Fonts for title page (20.4pt):
1857310490Scy\def\titlenominalsize{20pt}
1858310490Scy\setfont\titlerm\rmbshape{12}{\magstep3}{OT1}
1859310490Scy\setfont\titleit\itbshape{10}{\magstep4}{OT1IT}
1860310490Scy\setfont\titlesl\slbshape{10}{\magstep4}{OT1}
1861310490Scy\setfont\titlett\ttbshape{12}{\magstep3}{OT1TT}
1862310490Scy\setfont\titlettsl\ttslshape{10}{\magstep4}{OT1TT}
1863310490Scy\setfont\titlesf\sfbshape{17}{\magstep1}{OT1}
186438494Sobrien\let\titlebf=\titlerm
1865310490Scy\setfont\titlesc\scbshape{10}{\magstep4}{OT1}
186638494Sobrien\font\titlei=cmmi12 scaled \magstep3
186738494Sobrien\font\titlesy=cmsy10 scaled \magstep4
1868310490Scy\def\titleecsize{2074}
186938494Sobrien
187038494Sobrien% Chapter (and unnumbered) fonts (17.28pt).
1871310490Scy\def\chapnominalsize{17pt}
1872310490Scy\setfont\chaprm\rmbshape{12}{\magstep2}{OT1}
1873310490Scy\setfont\chapit\itbshape{10}{\magstep3}{OT1IT}
1874310490Scy\setfont\chapsl\slbshape{10}{\magstep3}{OT1}
1875310490Scy\setfont\chaptt\ttbshape{12}{\magstep2}{OT1TT}
1876310490Scy\setfont\chapttsl\ttslshape{10}{\magstep3}{OT1TT}
1877310490Scy\setfont\chapsf\sfbshape{17}{1000}{OT1}
187838494Sobrien\let\chapbf=\chaprm
1879310490Scy\setfont\chapsc\scbshape{10}{\magstep3}{OT1}
188038494Sobrien\font\chapi=cmmi12 scaled \magstep2
188138494Sobrien\font\chapsy=cmsy10 scaled \magstep3
1882310490Scy\def\chapecsize{1728}
188338494Sobrien
188438494Sobrien% Section fonts (14.4pt).
1885310490Scy\def\secnominalsize{14pt}
1886310490Scy\setfont\secrm\rmbshape{12}{\magstep1}{OT1}
1887310490Scy\setfont\secit\itbshape{10}{\magstep2}{OT1IT}
1888310490Scy\setfont\secsl\slbshape{10}{\magstep2}{OT1}
1889310490Scy\setfont\sectt\ttbshape{12}{\magstep1}{OT1TT}
1890310490Scy\setfont\secttsl\ttslshape{10}{\magstep2}{OT1TT}
1891310490Scy\setfont\secsf\sfbshape{12}{\magstep1}{OT1}
189238494Sobrien\let\secbf\secrm
1893310490Scy\setfont\secsc\scbshape{10}{\magstep2}{OT1}
189438494Sobrien\font\seci=cmmi12 scaled \magstep1
189538494Sobrien\font\secsy=cmsy10 scaled \magstep2
1896310490Scy\def\sececsize{1440}
189738494Sobrien
189838494Sobrien% Subsection fonts (13.15pt).
1899310490Scy\def\ssecnominalsize{13pt}
1900310490Scy\setfont\ssecrm\rmbshape{12}{\magstephalf}{OT1}
1901310490Scy\setfont\ssecit\itbshape{10}{1315}{OT1IT}
1902310490Scy\setfont\ssecsl\slbshape{10}{1315}{OT1}
1903310490Scy\setfont\ssectt\ttbshape{12}{\magstephalf}{OT1TT}
1904310490Scy\setfont\ssecttsl\ttslshape{10}{1315}{OT1TT}
1905310490Scy\setfont\ssecsf\sfbshape{12}{\magstephalf}{OT1}
190638494Sobrien\let\ssecbf\ssecrm
1907310490Scy\setfont\ssecsc\scbshape{10}{1315}{OT1}
190838494Sobrien\font\sseci=cmmi12 scaled \magstephalf
190938494Sobrien\font\ssecsy=cmsy10 scaled 1315
1910310490Scy\def\ssececsize{1200}
191138494Sobrien
1912174294Sobrien% Reduced fonts for @acro in text (10pt).
1913310490Scy\def\reducednominalsize{10pt}
1914310490Scy\setfont\reducedrm\rmshape{10}{1000}{OT1}
1915310490Scy\setfont\reducedtt\ttshape{10}{1000}{OT1TT}
1916310490Scy\setfont\reducedbf\bfshape{10}{1000}{OT1}
1917310490Scy\setfont\reducedit\itshape{10}{1000}{OT1IT}
1918310490Scy\setfont\reducedsl\slshape{10}{1000}{OT1}
1919310490Scy\setfont\reducedsf\sfshape{10}{1000}{OT1}
1920310490Scy\setfont\reducedsc\scshape{10}{1000}{OT1}
1921310490Scy\setfont\reducedttsl\ttslshape{10}{1000}{OT1TT}
1922174294Sobrien\font\reducedi=cmmi10
1923174294Sobrien\font\reducedsy=cmsy10
1924310490Scy\def\reducedecsize{1000}
1925174294Sobrien
1926310490Scy\textleading = 13.2pt % line spacing for 11pt CM
1927310490Scy\textfonts            % reset the current fonts
1928310490Scy\rm
1929310490Scy} % end of 11pt text font size definitions, \definetextfontsizexi
1930310490Scy
1931310490Scy
1932310490Scy% Definitions to make the main text be 10pt Computer Modern, with
1933310490Scy% section, chapter, etc., sizes following suit.  This is for the GNU
1934310490Scy% Press printing of the Emacs 22 manual.  Maybe other manuals in the
1935310490Scy% future.  Used with @smallbook, which sets the leading to 12pt.
1936310490Scy%
1937310490Scy\def\definetextfontsizex{%
1938310490Scy% Text fonts (10pt).
1939310490Scy\def\textnominalsize{10pt}
1940310490Scy\edef\mainmagstep{1000}
1941310490Scy\setfont\textrm\rmshape{10}{\mainmagstep}{OT1}
1942310490Scy\setfont\texttt\ttshape{10}{\mainmagstep}{OT1TT}
1943310490Scy\setfont\textbf\bfshape{10}{\mainmagstep}{OT1}
1944310490Scy\setfont\textit\itshape{10}{\mainmagstep}{OT1IT}
1945310490Scy\setfont\textsl\slshape{10}{\mainmagstep}{OT1}
1946310490Scy\setfont\textsf\sfshape{10}{\mainmagstep}{OT1}
1947310490Scy\setfont\textsc\scshape{10}{\mainmagstep}{OT1}
1948310490Scy\setfont\textttsl\ttslshape{10}{\mainmagstep}{OT1TT}
1949310490Scy\font\texti=cmmi10 scaled \mainmagstep
1950310490Scy\font\textsy=cmsy10 scaled \mainmagstep
1951310490Scy\def\textecsize{1000}
1952310490Scy
1953310490Scy% A few fonts for @defun names and args.
1954310490Scy\setfont\defbf\bfshape{10}{\magstephalf}{OT1}
1955310490Scy\setfont\deftt\ttshape{10}{\magstephalf}{OT1TT}
1956310490Scy\setfont\defttsl\ttslshape{10}{\magstephalf}{OT1TT}
1957310490Scy\def\df{\let\tentt=\deftt \let\tenbf = \defbf \let\tenttsl=\defttsl \bf}
1958310490Scy
1959310490Scy% Fonts for indices, footnotes, small examples (9pt).
1960310490Scy\def\smallnominalsize{9pt}
1961310490Scy\setfont\smallrm\rmshape{9}{1000}{OT1}
1962310490Scy\setfont\smalltt\ttshape{9}{1000}{OT1TT}
1963310490Scy\setfont\smallbf\bfshape{10}{900}{OT1}
1964310490Scy\setfont\smallit\itshape{9}{1000}{OT1IT}
1965310490Scy\setfont\smallsl\slshape{9}{1000}{OT1}
1966310490Scy\setfont\smallsf\sfshape{9}{1000}{OT1}
1967310490Scy\setfont\smallsc\scshape{10}{900}{OT1}
1968310490Scy\setfont\smallttsl\ttslshape{10}{900}{OT1TT}
1969310490Scy\font\smalli=cmmi9
1970310490Scy\font\smallsy=cmsy9
1971310490Scy\def\smallecsize{0900}
1972310490Scy
1973310490Scy% Fonts for small examples (8pt).
1974310490Scy\def\smallernominalsize{8pt}
1975310490Scy\setfont\smallerrm\rmshape{8}{1000}{OT1}
1976310490Scy\setfont\smallertt\ttshape{8}{1000}{OT1TT}
1977310490Scy\setfont\smallerbf\bfshape{10}{800}{OT1}
1978310490Scy\setfont\smallerit\itshape{8}{1000}{OT1IT}
1979310490Scy\setfont\smallersl\slshape{8}{1000}{OT1}
1980310490Scy\setfont\smallersf\sfshape{8}{1000}{OT1}
1981310490Scy\setfont\smallersc\scshape{10}{800}{OT1}
1982310490Scy\setfont\smallerttsl\ttslshape{10}{800}{OT1TT}
1983310490Scy\font\smalleri=cmmi8
1984310490Scy\font\smallersy=cmsy8
1985310490Scy\def\smallerecsize{0800}
1986310490Scy
1987310490Scy% Fonts for title page (20.4pt):
1988310490Scy\def\titlenominalsize{20pt}
1989310490Scy\setfont\titlerm\rmbshape{12}{\magstep3}{OT1}
1990310490Scy\setfont\titleit\itbshape{10}{\magstep4}{OT1IT}
1991310490Scy\setfont\titlesl\slbshape{10}{\magstep4}{OT1}
1992310490Scy\setfont\titlett\ttbshape{12}{\magstep3}{OT1TT}
1993310490Scy\setfont\titlettsl\ttslshape{10}{\magstep4}{OT1TT}
1994310490Scy\setfont\titlesf\sfbshape{17}{\magstep1}{OT1}
1995310490Scy\let\titlebf=\titlerm
1996310490Scy\setfont\titlesc\scbshape{10}{\magstep4}{OT1}
1997310490Scy\font\titlei=cmmi12 scaled \magstep3
1998310490Scy\font\titlesy=cmsy10 scaled \magstep4
1999310490Scy\def\titleecsize{2074}
2000310490Scy
2001310490Scy% Chapter fonts (14.4pt).
2002310490Scy\def\chapnominalsize{14pt}
2003310490Scy\setfont\chaprm\rmbshape{12}{\magstep1}{OT1}
2004310490Scy\setfont\chapit\itbshape{10}{\magstep2}{OT1IT}
2005310490Scy\setfont\chapsl\slbshape{10}{\magstep2}{OT1}
2006310490Scy\setfont\chaptt\ttbshape{12}{\magstep1}{OT1TT}
2007310490Scy\setfont\chapttsl\ttslshape{10}{\magstep2}{OT1TT}
2008310490Scy\setfont\chapsf\sfbshape{12}{\magstep1}{OT1}
2009310490Scy\let\chapbf\chaprm
2010310490Scy\setfont\chapsc\scbshape{10}{\magstep2}{OT1}
2011310490Scy\font\chapi=cmmi12 scaled \magstep1
2012310490Scy\font\chapsy=cmsy10 scaled \magstep2
2013310490Scy\def\chapecsize{1440}
2014310490Scy
2015310490Scy% Section fonts (12pt).
2016310490Scy\def\secnominalsize{12pt}
2017310490Scy\setfont\secrm\rmbshape{12}{1000}{OT1}
2018310490Scy\setfont\secit\itbshape{10}{\magstep1}{OT1IT}
2019310490Scy\setfont\secsl\slbshape{10}{\magstep1}{OT1}
2020310490Scy\setfont\sectt\ttbshape{12}{1000}{OT1TT}
2021310490Scy\setfont\secttsl\ttslshape{10}{\magstep1}{OT1TT}
2022310490Scy\setfont\secsf\sfbshape{12}{1000}{OT1}
2023310490Scy\let\secbf\secrm
2024310490Scy\setfont\secsc\scbshape{10}{\magstep1}{OT1}
2025310490Scy\font\seci=cmmi12
2026310490Scy\font\secsy=cmsy10 scaled \magstep1
2027310490Scy\def\sececsize{1200}
2028310490Scy
2029310490Scy% Subsection fonts (10pt).
2030310490Scy\def\ssecnominalsize{10pt}
2031310490Scy\setfont\ssecrm\rmbshape{10}{1000}{OT1}
2032310490Scy\setfont\ssecit\itbshape{10}{1000}{OT1IT}
2033310490Scy\setfont\ssecsl\slbshape{10}{1000}{OT1}
2034310490Scy\setfont\ssectt\ttbshape{10}{1000}{OT1TT}
2035310490Scy\setfont\ssecttsl\ttslshape{10}{1000}{OT1TT}
2036310490Scy\setfont\ssecsf\sfbshape{10}{1000}{OT1}
2037310490Scy\let\ssecbf\ssecrm
2038310490Scy\setfont\ssecsc\scbshape{10}{1000}{OT1}
2039310490Scy\font\sseci=cmmi10
2040310490Scy\font\ssecsy=cmsy10
2041310490Scy\def\ssececsize{1000}
2042310490Scy
2043310490Scy% Reduced fonts for @acro in text (9pt).
2044310490Scy\def\reducednominalsize{9pt}
2045310490Scy\setfont\reducedrm\rmshape{9}{1000}{OT1}
2046310490Scy\setfont\reducedtt\ttshape{9}{1000}{OT1TT}
2047310490Scy\setfont\reducedbf\bfshape{10}{900}{OT1}
2048310490Scy\setfont\reducedit\itshape{9}{1000}{OT1IT}
2049310490Scy\setfont\reducedsl\slshape{9}{1000}{OT1}
2050310490Scy\setfont\reducedsf\sfshape{9}{1000}{OT1}
2051310490Scy\setfont\reducedsc\scshape{10}{900}{OT1}
2052310490Scy\setfont\reducedttsl\ttslshape{10}{900}{OT1TT}
2053310490Scy\font\reducedi=cmmi9
2054310490Scy\font\reducedsy=cmsy9
2055310490Scy\def\reducedecsize{0900}
2056310490Scy
2057310490Scy\divide\parskip by 2  % reduce space between paragraphs
2058310490Scy\textleading = 12pt   % line spacing for 10pt CM
2059310490Scy\textfonts            % reset the current fonts
2060310490Scy\rm
2061310490Scy} % end of 10pt text font size definitions, \definetextfontsizex
2062310490Scy
2063310490Scy
2064310490Scy% We provide the user-level command
2065310490Scy%   @fonttextsize 10
2066310490Scy% (or 11) to redefine the text font size.  pt is assumed.
2067310490Scy%
2068310490Scy\def\xiword{11}
2069310490Scy\def\xword{10}
2070310490Scy\def\xwordpt{10pt}
2071310490Scy%
2072310490Scy\parseargdef\fonttextsize{%
2073310490Scy  \def\textsizearg{#1}%
2074310490Scy  %\wlog{doing @fonttextsize \textsizearg}%
2075310490Scy  %
2076310490Scy  % Set \globaldefs so that documents can use this inside @tex, since
2077310490Scy  % makeinfo 4.8 does not support it, but we need it nonetheless.
2078310490Scy  %
2079310490Scy \begingroup \globaldefs=1
2080310490Scy  \ifx\textsizearg\xword \definetextfontsizex
2081310490Scy  \else \ifx\textsizearg\xiword \definetextfontsizexi
2082310490Scy  \else
2083310490Scy    \errhelp=\EMsimple
2084310490Scy    \errmessage{@fonttextsize only supports `10' or `11', not `\textsizearg'}
2085310490Scy  \fi\fi
2086310490Scy \endgroup
2087310490Scy}
2088310490Scy
2089310490Scy
209038494Sobrien% In order for the font changes to affect most math symbols and letters,
209138494Sobrien% we have to define the \textfont of the standard families.  Since
2092119679Smbr% texinfo doesn't allow for producing subscripts and superscripts except
2093119679Smbr% in the main text, we don't bother to reset \scriptfont and
2094119679Smbr% \scriptscriptfont (which would also require loading a lot more fonts).
209538494Sobrien%
209638494Sobrien\def\resetmathfonts{%
2097119679Smbr  \textfont0=\tenrm \textfont1=\teni \textfont2=\tensy
2098119679Smbr  \textfont\itfam=\tenit \textfont\slfam=\tensl \textfont\bffam=\tenbf
2099119679Smbr  \textfont\ttfam=\tentt \textfont\sffam=\tensf
210038494Sobrien}
210138494Sobrien
210238494Sobrien% The font-changing commands redefine the meanings of \tenSTYLE, instead
2103174294Sobrien% of just \STYLE.  We do this because \STYLE needs to also set the
2104174294Sobrien% current \fam for math mode.  Our \STYLE (e.g., \rm) commands hardwire
2105174294Sobrien% \tenSTYLE to set the current font.
2106174294Sobrien%
2107174294Sobrien% Each font-changing command also sets the names \lsize (one size lower)
2108174294Sobrien% and \lllsize (three sizes lower).  These relative commands are used in
2109174294Sobrien% the LaTeX logo and acronyms.
2110174294Sobrien%
2111174294Sobrien% This all needs generalizing, badly.
2112174294Sobrien%
211338494Sobrien\def\textfonts{%
211438494Sobrien  \let\tenrm=\textrm \let\tenit=\textit \let\tensl=\textsl
211538494Sobrien  \let\tenbf=\textbf \let\tentt=\texttt \let\smallcaps=\textsc
2116174294Sobrien  \let\tensf=\textsf \let\teni=\texti \let\tensy=\textsy
2117174294Sobrien  \let\tenttsl=\textttsl
2118310490Scy  \def\curfontsize{text}%
2119174294Sobrien  \def\lsize{reduced}\def\lllsize{smaller}%
212082794Sobrien  \resetmathfonts \setleading{\textleading}}
212138494Sobrien\def\titlefonts{%
212238494Sobrien  \let\tenrm=\titlerm \let\tenit=\titleit \let\tensl=\titlesl
212338494Sobrien  \let\tenbf=\titlebf \let\tentt=\titlett \let\smallcaps=\titlesc
212438494Sobrien  \let\tensf=\titlesf \let\teni=\titlei \let\tensy=\titlesy
212538494Sobrien  \let\tenttsl=\titlettsl
2126310490Scy  \def\curfontsize{title}%
2127174294Sobrien  \def\lsize{chap}\def\lllsize{subsec}%
2128310490Scy  \resetmathfonts \setleading{27pt}}
2129310490Scy\def\titlefont#1{{\titlefonts\rmisbold #1}}
213038494Sobrien\def\chapfonts{%
213138494Sobrien  \let\tenrm=\chaprm \let\tenit=\chapit \let\tensl=\chapsl
213238494Sobrien  \let\tenbf=\chapbf \let\tentt=\chaptt \let\smallcaps=\chapsc
2133310490Scy  \let\tensf=\chapsf \let\teni=\chapi \let\tensy=\chapsy
2134310490Scy  \let\tenttsl=\chapttsl
2135310490Scy  \def\curfontsize{chap}%
2136174294Sobrien  \def\lsize{sec}\def\lllsize{text}%
213738494Sobrien  \resetmathfonts \setleading{19pt}}
213838494Sobrien\def\secfonts{%
213938494Sobrien  \let\tenrm=\secrm \let\tenit=\secit \let\tensl=\secsl
214038494Sobrien  \let\tenbf=\secbf \let\tentt=\sectt \let\smallcaps=\secsc
2141174294Sobrien  \let\tensf=\secsf \let\teni=\seci \let\tensy=\secsy
2142174294Sobrien  \let\tenttsl=\secttsl
2143310490Scy  \def\curfontsize{sec}%
2144174294Sobrien  \def\lsize{subsec}\def\lllsize{reduced}%
214538494Sobrien  \resetmathfonts \setleading{16pt}}
214638494Sobrien\def\subsecfonts{%
214738494Sobrien  \let\tenrm=\ssecrm \let\tenit=\ssecit \let\tensl=\ssecsl
214838494Sobrien  \let\tenbf=\ssecbf \let\tentt=\ssectt \let\smallcaps=\ssecsc
2149174294Sobrien  \let\tensf=\ssecsf \let\teni=\sseci \let\tensy=\ssecsy
2150174294Sobrien  \let\tenttsl=\ssecttsl
2151310490Scy  \def\curfontsize{ssec}%
2152174294Sobrien  \def\lsize{text}\def\lllsize{small}%
215338494Sobrien  \resetmathfonts \setleading{15pt}}
2154174294Sobrien\let\subsubsecfonts = \subsecfonts
2155174294Sobrien\def\reducedfonts{%
2156174294Sobrien  \let\tenrm=\reducedrm \let\tenit=\reducedit \let\tensl=\reducedsl
2157174294Sobrien  \let\tenbf=\reducedbf \let\tentt=\reducedtt \let\reducedcaps=\reducedsc
2158174294Sobrien  \let\tensf=\reducedsf \let\teni=\reducedi \let\tensy=\reducedsy
2159174294Sobrien  \let\tenttsl=\reducedttsl
2160310490Scy  \def\curfontsize{reduced}%
2161174294Sobrien  \def\lsize{small}\def\lllsize{smaller}%
2162174294Sobrien  \resetmathfonts \setleading{10.5pt}}
216382794Sobrien\def\smallfonts{%
216482794Sobrien  \let\tenrm=\smallrm \let\tenit=\smallit \let\tensl=\smallsl
216582794Sobrien  \let\tenbf=\smallbf \let\tentt=\smalltt \let\smallcaps=\smallsc
216682794Sobrien  \let\tensf=\smallsf \let\teni=\smalli \let\tensy=\smallsy
216782794Sobrien  \let\tenttsl=\smallttsl
2168310490Scy  \def\curfontsize{small}%
2169174294Sobrien  \def\lsize{smaller}\def\lllsize{smaller}%
217082794Sobrien  \resetmathfonts \setleading{10.5pt}}
217182794Sobrien\def\smallerfonts{%
217282794Sobrien  \let\tenrm=\smallerrm \let\tenit=\smallerit \let\tensl=\smallersl
217382794Sobrien  \let\tenbf=\smallerbf \let\tentt=\smallertt \let\smallcaps=\smallersc
217482794Sobrien  \let\tensf=\smallersf \let\teni=\smalleri \let\tensy=\smallersy
217582794Sobrien  \let\tenttsl=\smallerttsl
2176310490Scy  \def\curfontsize{smaller}%
2177174294Sobrien  \def\lsize{smaller}\def\lllsize{smaller}%
217882794Sobrien  \resetmathfonts \setleading{9.5pt}}
217938494Sobrien
2180310490Scy% Fonts for short table of contents.
2181310490Scy\setfont\shortcontrm\rmshape{12}{1000}{OT1}
2182310490Scy\setfont\shortcontbf\bfshape{10}{\magstep1}{OT1}  % no cmb12
2183310490Scy\setfont\shortcontsl\slshape{12}{1000}{OT1}
2184310490Scy\setfont\shortconttt\ttshape{12}{1000}{OT1TT}
2185310490Scy
2186310490Scy% Define these just so they can be easily changed for other fonts.
2187310490Scy\def\angleleft{$\langle$}
2188310490Scy\def\angleright{$\rangle$}
2189310490Scy
2190174294Sobrien% Set the fonts to use with the @small... environments.
2191174294Sobrien\let\smallexamplefonts = \smallfonts
2192174294Sobrien
2193174294Sobrien% About \smallexamplefonts.  If we use \smallfonts (9pt), @smallexample
2194174294Sobrien% can fit this many characters:
2195174294Sobrien%   8.5x11=86   smallbook=72  a4=90  a5=69
2196174294Sobrien% If we use \scriptfonts (8pt), then we can fit this many characters:
2197174294Sobrien%   8.5x11=90+  smallbook=80  a4=90+  a5=77
2198174294Sobrien% For me, subjectively, the few extra characters that fit aren't worth
2199174294Sobrien% the additional smallness of 8pt.  So I'm making the default 9pt.
2200174294Sobrien%
2201174294Sobrien% By the way, for comparison, here's what fits with @example (10pt):
2202174294Sobrien%   8.5x11=71  smallbook=60  a4=75  a5=58
2203174294Sobrien% --karl, 24jan03.
2204174294Sobrien
220538494Sobrien% Set up the default fonts, so we can use them for creating boxes.
220638494Sobrien%
2207310490Scy\definetextfontsizexi
220838494Sobrien
220942629Sobrien
2210310490Scy\message{markup,}
2211310490Scy
2212310490Scy% Check if we are currently using a typewriter font.  Since all the
2213310490Scy% Computer Modern typewriter fonts have zero interword stretch (and
2214310490Scy% shrink), and it is reasonable to expect all typewriter fonts to have
2215310490Scy% this property, we can check that font parameter.
2216310490Scy%
2217310490Scy\def\ifmonospace{\ifdim\fontdimen3\font=0pt }
2218310490Scy
2219310490Scy% Markup style infrastructure.  \defmarkupstylesetup\INITMACRO will
2220310490Scy% define and register \INITMACRO to be called on markup style changes.
2221310490Scy% \INITMACRO can check \currentmarkupstyle for the innermost
2222310490Scy% style and the set of \ifmarkupSTYLE switches for all styles
2223310490Scy% currently in effect.
2224310490Scy\newif\ifmarkupvar
2225310490Scy\newif\ifmarkupsamp
2226310490Scy\newif\ifmarkupkey
2227310490Scy%\newif\ifmarkupfile % @file == @samp.
2228310490Scy%\newif\ifmarkupoption % @option == @samp.
2229310490Scy\newif\ifmarkupcode
2230310490Scy\newif\ifmarkupkbd
2231310490Scy%\newif\ifmarkupenv % @env == @code.
2232310490Scy%\newif\ifmarkupcommand % @command == @code.
2233310490Scy\newif\ifmarkuptex % @tex (and part of @math, for now).
2234310490Scy\newif\ifmarkupexample
2235310490Scy\newif\ifmarkupverb
2236310490Scy\newif\ifmarkupverbatim
2237310490Scy
2238310490Scy\let\currentmarkupstyle\empty
2239310490Scy
2240310490Scy\def\setupmarkupstyle#1{%
2241310490Scy  \csname markup#1true\endcsname
2242310490Scy  \def\currentmarkupstyle{#1}%
2243310490Scy  \markupstylesetup
2244310490Scy}
2245310490Scy
2246310490Scy\let\markupstylesetup\empty
2247310490Scy
2248310490Scy\def\defmarkupstylesetup#1{%
2249310490Scy  \expandafter\def\expandafter\markupstylesetup
2250310490Scy    \expandafter{\markupstylesetup #1}%
2251310490Scy  \def#1%
2252310490Scy}
2253310490Scy
2254310490Scy% Markup style setup for left and right quotes.
2255310490Scy\defmarkupstylesetup\markupsetuplq{%
2256310490Scy  \expandafter\let\expandafter \temp
2257310490Scy    \csname markupsetuplq\currentmarkupstyle\endcsname
2258310490Scy  \ifx\temp\relax \markupsetuplqdefault \else \temp \fi
2259310490Scy}
2260310490Scy
2261310490Scy\defmarkupstylesetup\markupsetuprq{%
2262310490Scy  \expandafter\let\expandafter \temp
2263310490Scy    \csname markupsetuprq\currentmarkupstyle\endcsname
2264310490Scy  \ifx\temp\relax \markupsetuprqdefault \else \temp \fi
2265310490Scy}
2266310490Scy
2267310490Scy{
2268310490Scy\catcode`\'=\active
2269310490Scy\catcode`\`=\active
2270310490Scy
2271310490Scy\gdef\markupsetuplqdefault{\let`\lq}
2272310490Scy\gdef\markupsetuprqdefault{\let'\rq}
2273310490Scy
2274310490Scy\gdef\markupsetcodequoteleft{\let`\codequoteleft}
2275310490Scy\gdef\markupsetcodequoteright{\let'\codequoteright}
2276310490Scy}
2277310490Scy
2278310490Scy\let\markupsetuplqcode \markupsetcodequoteleft
2279310490Scy\let\markupsetuprqcode \markupsetcodequoteright
2280310490Scy%
2281310490Scy\let\markupsetuplqexample \markupsetcodequoteleft
2282310490Scy\let\markupsetuprqexample \markupsetcodequoteright
2283310490Scy%
2284310490Scy\let\markupsetuplqkbd     \markupsetcodequoteleft
2285310490Scy\let\markupsetuprqkbd     \markupsetcodequoteright
2286310490Scy%
2287310490Scy\let\markupsetuplqsamp \markupsetcodequoteleft
2288310490Scy\let\markupsetuprqsamp \markupsetcodequoteright
2289310490Scy%
2290310490Scy\let\markupsetuplqverb \markupsetcodequoteleft
2291310490Scy\let\markupsetuprqverb \markupsetcodequoteright
2292310490Scy%
2293310490Scy\let\markupsetuplqverbatim \markupsetcodequoteleft
2294310490Scy\let\markupsetuprqverbatim \markupsetcodequoteright
2295310490Scy
2296310490Scy% Allow an option to not use regular directed right quote/apostrophe
2297310490Scy% (char 0x27), but instead the undirected quote from cmtt (char 0x0d).
2298310490Scy% The undirected quote is ugly, so don't make it the default, but it
2299310490Scy% works for pasting with more pdf viewers (at least evince), the
2300310490Scy% lilypond developers report.  xpdf does work with the regular 0x27.
2301310490Scy%
2302310490Scy\def\codequoteright{%
2303310490Scy  \expandafter\ifx\csname SETtxicodequoteundirected\endcsname\relax
2304310490Scy    \expandafter\ifx\csname SETcodequoteundirected\endcsname\relax
2305310490Scy      '%
2306310490Scy    \else \char'15 \fi
2307310490Scy  \else \char'15 \fi
2308310490Scy}
2309310490Scy%
2310310490Scy% and a similar option for the left quote char vs. a grave accent.
2311310490Scy% Modern fonts display ASCII 0x60 as a grave accent, so some people like
2312310490Scy% the code environments to do likewise.
2313310490Scy%
2314310490Scy\def\codequoteleft{%
2315310490Scy  \expandafter\ifx\csname SETtxicodequotebacktick\endcsname\relax
2316310490Scy    \expandafter\ifx\csname SETcodequotebacktick\endcsname\relax
2317310490Scy      % [Knuth] pp. 380,381,391
2318310490Scy      % \relax disables Spanish ligatures ?` and !` of \tt font.
2319310490Scy      \relax`%
2320310490Scy    \else \char'22 \fi
2321310490Scy  \else \char'22 \fi
2322310490Scy}
2323310490Scy
2324310490Scy% Commands to set the quote options.
2325310490Scy% 
2326310490Scy\parseargdef\codequoteundirected{%
2327310490Scy  \def\temp{#1}%
2328310490Scy  \ifx\temp\onword
2329310490Scy    \expandafter\let\csname SETtxicodequoteundirected\endcsname
2330310490Scy      = t%
2331310490Scy  \else\ifx\temp\offword
2332310490Scy    \expandafter\let\csname SETtxicodequoteundirected\endcsname
2333310490Scy      = \relax
2334310490Scy  \else
2335310490Scy    \errhelp = \EMsimple
2336310490Scy    \errmessage{Unknown @codequoteundirected value `\temp', must be on|off}%
2337310490Scy  \fi\fi
2338310490Scy}
2339310490Scy%
2340310490Scy\parseargdef\codequotebacktick{%
2341310490Scy  \def\temp{#1}%
2342310490Scy  \ifx\temp\onword
2343310490Scy    \expandafter\let\csname SETtxicodequotebacktick\endcsname
2344310490Scy      = t%
2345310490Scy  \else\ifx\temp\offword
2346310490Scy    \expandafter\let\csname SETtxicodequotebacktick\endcsname
2347310490Scy      = \relax
2348310490Scy  \else
2349310490Scy    \errhelp = \EMsimple
2350310490Scy    \errmessage{Unknown @codequotebacktick value `\temp', must be on|off}%
2351310490Scy  \fi\fi
2352310490Scy}
2353310490Scy
2354310490Scy% [Knuth] pp. 380,381,391, disable Spanish ligatures ?` and !` of \tt font.
2355310490Scy\def\noligaturesquoteleft{\relax\lq}
2356310490Scy
235738494Sobrien% Count depth in font-changes, for error checks
235838494Sobrien\newcount\fontdepth \fontdepth=0
235938494Sobrien
2360310490Scy% Font commands.
236138494Sobrien
2362310490Scy% #1 is the font command (\sl or \it), #2 is the text to slant.
2363310490Scy% If we are in a monospaced environment, however, 1) always use \ttsl,
2364310490Scy% and 2) do not add an italic correction.
2365310490Scy\def\dosmartslant#1#2{%
2366310490Scy  \ifusingtt 
2367310490Scy    {{\ttsl #2}\let\next=\relax}%
2368310490Scy    {\def\next{{#1#2}\futurelet\next\smartitaliccorrection}}%
2369310490Scy  \next
2370310490Scy}
2371310490Scy\def\smartslanted{\dosmartslant\sl}
2372310490Scy\def\smartitalic{\dosmartslant\it}
237338494Sobrien
2374310490Scy% Output an italic correction unless \next (presumed to be the following
2375310490Scy% character) is such as not to need one.
2376310490Scy\def\smartitaliccorrection{%
2377310490Scy  \ifx\next,%
2378310490Scy  \else\ifx\next-%
2379310490Scy  \else\ifx\next.%
2380310490Scy  \else\ptexslash
2381310490Scy  \fi\fi\fi
2382310490Scy  \aftersmartic
2383310490Scy}
238438494Sobrien
2385310490Scy% Unconditional use \ttsl, and no ic.  @var is set to this for defuns.
2386310490Scy\def\ttslanted#1{{\ttsl #1}}
2387174294Sobrien
2388310490Scy% @cite is like \smartslanted except unconditionally use \sl.  We never want
2389174294Sobrien% ttsl for book titles, do we?
2390310490Scy\def\cite#1{{\sl #1}\futurelet\next\smartitaliccorrection}
2391174294Sobrien
2392310490Scy\def\aftersmartic{}
2393310490Scy\def\var#1{%
2394310490Scy  \let\saveaftersmartic = \aftersmartic
2395310490Scy  \def\aftersmartic{\null\let\aftersmartic=\saveaftersmartic}%
2396310490Scy  \smartslanted{#1}%
2397310490Scy}
2398310490Scy
239938494Sobrien\let\i=\smartitalic
2400174294Sobrien\let\slanted=\smartslanted
240142629Sobrien\let\dfn=\smartslanted
240238494Sobrien\let\emph=\smartitalic
240338494Sobrien
2404310490Scy% Explicit font changes: @r, @sc, undocumented @ii.
2405310490Scy\def\r#1{{\rm #1}}              % roman font
2406310490Scy\def\sc#1{{\smallcaps#1}}       % smallcaps font
2407310490Scy\def\ii#1{{\it #1}}             % italic font
2408310490Scy
2409310490Scy% @b, explicit bold.  Also @strong.
241038494Sobrien\def\b#1{{\bf #1}}
241138494Sobrien\let\strong=\b
241238494Sobrien
2413310490Scy% @sansserif, explicit sans.
2414310490Scy\def\sansserif#1{{\sf #1}}
2415310490Scy
241638494Sobrien% We can't just use \exhyphenpenalty, because that only has effect at
241738494Sobrien% the end of a paragraph.  Restore normal hyphenation at the end of the
241838494Sobrien% group within which \nohyphenation is presumably called.
241938494Sobrien%
242038494Sobrien\def\nohyphenation{\hyphenchar\font = -1  \aftergroup\restorehyphenation}
242138494Sobrien\def\restorehyphenation{\hyphenchar\font = `- }
242238494Sobrien
2423174294Sobrien% Set sfcode to normal for the chars that usually have another value.
2424174294Sobrien% Can't use plain's \frenchspacing because it uses the `\x notation, and
2425174294Sobrien% sometimes \x has an active definition that messes things up.
2426174294Sobrien%
2427174294Sobrien\catcode`@=11
2428310490Scy  \def\plainfrenchspacing{%
2429174294Sobrien    \sfcode\dotChar  =\@m \sfcode\questChar=\@m \sfcode\exclamChar=\@m
2430174294Sobrien    \sfcode\colonChar=\@m \sfcode\semiChar =\@m \sfcode\commaChar =\@m
2431310490Scy    \def\endofsentencespacefactor{1000}% for @. and friends
2432174294Sobrien  }
2433310490Scy  \def\plainnonfrenchspacing{%
2434310490Scy    \sfcode`\.3000\sfcode`\?3000\sfcode`\!3000
2435310490Scy    \sfcode`\:2000\sfcode`\;1500\sfcode`\,1250
2436310490Scy    \def\endofsentencespacefactor{3000}% for @. and friends
2437310490Scy  }
2438174294Sobrien\catcode`@=\other
2439310490Scy\def\endofsentencespacefactor{3000}% default
2440174294Sobrien
2441310490Scy% @t, explicit typewriter.
244238494Sobrien\def\t#1{%
2443310490Scy  {\tt \rawbackslash \plainfrenchspacing #1}%
244438494Sobrien  \null
244538494Sobrien}
244638494Sobrien
2447310490Scy% @samp.
2448310490Scy\def\samp#1{{\setupmarkupstyle{samp}\lq\tclose{#1}\rq\null}}
244938494Sobrien
2450310490Scy% @indicateurl is \samp, that is, with quotes.
2451310490Scy\let\indicateurl=\samp
2452310490Scy
2453310490Scy% @code (and similar) prints in typewriter, but with spaces the same
2454310490Scy% size as normal in the surrounding text, without hyphenation, etc.
2455310490Scy% This is a subroutine for that.
245638494Sobrien\def\tclose#1{%
245738494Sobrien  {%
245838494Sobrien    % Change normal interword space to be same as for the current font.
245938494Sobrien    \spaceskip = \fontdimen2\font
246038494Sobrien    %
246138494Sobrien    % Switch to typewriter.
246238494Sobrien    \tt
246338494Sobrien    %
246438494Sobrien    % But `\ ' produces the large typewriter interword space.
246538494Sobrien    \def\ {{\spaceskip = 0pt{} }}%
246638494Sobrien    %
246738494Sobrien    % Turn off hyphenation.
246838494Sobrien    \nohyphenation
246938494Sobrien    %
247038494Sobrien    \rawbackslash
2471310490Scy    \plainfrenchspacing
247238494Sobrien    #1%
247338494Sobrien  }%
2474310490Scy  \null % reset spacefactor to 1000
247538494Sobrien}
247638494Sobrien
2477174294Sobrien% We *must* turn on hyphenation at `-' and `_' in @code.
247838494Sobrien% Otherwise, it is too hard to avoid overfull hboxes
247938494Sobrien% in the Emacs manual, the Library manual, etc.
2480310490Scy%
248138494Sobrien% Unfortunately, TeX uses one parameter (\hyphenchar) to control
248238494Sobrien% both hyphenation at - and hyphenation within words.
248338494Sobrien% We must therefore turn them both off (\tclose does that)
248438494Sobrien% and arrange explicitly to hyphenate at a dash.
248538494Sobrien%  -- rms.
248638494Sobrien{
2487310490Scy  \catcode`\-=\active \catcode`\_=\active
2488310490Scy  \catcode`\'=\active \catcode`\`=\active
2489310490Scy  \global\let'=\rq \global\let`=\lq  % default definitions
249042629Sobrien  %
249142629Sobrien  \global\def\code{\begingroup
2492310490Scy    \setupmarkupstyle{code}%
2493310490Scy    % The following should really be moved into \setupmarkupstyle handlers.
2494310490Scy    \catcode\dashChar=\active  \catcode\underChar=\active
2495310490Scy    \ifallowcodebreaks
2496310490Scy     \let-\codedash
2497310490Scy     \let_\codeunder
2498310490Scy    \else
2499310490Scy     \let-\normaldash
2500310490Scy     \let_\realunder
2501310490Scy    \fi
250242629Sobrien    \codex
250342629Sobrien  }
250438494Sobrien}
250538494Sobrien
2506310490Scy\def\codex #1{\tclose{#1}\endgroup}
2507310490Scy
2508310490Scy\def\normaldash{-}
250938494Sobrien\def\codedash{-\discretionary{}{}{}}
2510119679Smbr\def\codeunder{%
2511119679Smbr  % this is all so @math{@code{var_name}+1} can work.  In math mode, _
2512119679Smbr  % is "active" (mathcode"8000) and \normalunderscore (or \char95, etc.)
2513119679Smbr  % will therefore expand the active definition of _, which is us
2514119679Smbr  % (inside @code that is), therefore an endless loop.
2515119679Smbr  \ifusingtt{\ifmmode
2516119679Smbr               \mathchar"075F % class 0=ordinary, family 7=ttfam, pos 0x5F=_.
2517119679Smbr             \else\normalunderscore \fi
2518119679Smbr             \discretionary{}{}{}}%
2519119679Smbr            {\_}%
2520119679Smbr}
252138494Sobrien
2522310490Scy% An additional complication: the above will allow breaks after, e.g.,
2523310490Scy% each of the four underscores in __typeof__.  This is bad.
2524310490Scy% @allowcodebreaks provides a document-level way to turn breaking at -
2525310490Scy% and _ on and off.
2526310490Scy%
2527310490Scy\newif\ifallowcodebreaks  \allowcodebreakstrue
252838494Sobrien
2529310490Scy\def\keywordtrue{true}
2530310490Scy\def\keywordfalse{false}
2531310490Scy
2532310490Scy\parseargdef\allowcodebreaks{%
2533310490Scy  \def\txiarg{#1}%
2534310490Scy  \ifx\txiarg\keywordtrue
2535310490Scy    \allowcodebreakstrue
2536310490Scy  \else\ifx\txiarg\keywordfalse
2537310490Scy    \allowcodebreaksfalse
2538174294Sobrien  \else
2539174294Sobrien    \errhelp = \EMsimple
2540310490Scy    \errmessage{Unknown @allowcodebreaks option `\txiarg', must be true|false}%
2541310490Scy  \fi\fi
254238494Sobrien}
254338494Sobrien
2544310490Scy% For @command, @env, @file, @option quotes seem unnecessary,
2545310490Scy% so use \code rather than \samp.
2546310490Scy\let\command=\code
254742629Sobrien\let\env=\code
2548310490Scy\let\file=\code
2549310490Scy\let\option=\code
255038494Sobrien
255182794Sobrien% @uref (abbreviation for `urlref') takes an optional (comma-separated)
255282794Sobrien% second argument specifying the text to display and an optional third
255382794Sobrien% arg as text to display instead of (rather than in addition to) the url
2554310490Scy% itself.  First (mandatory) arg is the url.
2555310490Scy% (This \urefnobreak definition isn't used now, leaving it for a while
2556310490Scy% for comparison.)
2557310490Scy\def\urefnobreak#1{\dourefnobreak #1,,,\finish}
2558310490Scy\def\dourefnobreak#1,#2,#3,#4\finish{\begingroup
255982794Sobrien  \unsepspaces
256082794Sobrien  \pdfurl{#1}%
256182794Sobrien  \setbox0 = \hbox{\ignorespaces #3}%
256238494Sobrien  \ifdim\wd0 > 0pt
256382794Sobrien    \unhbox0 % third arg given, show only that
256438494Sobrien  \else
256582794Sobrien    \setbox0 = \hbox{\ignorespaces #2}%
256682794Sobrien    \ifdim\wd0 > 0pt
256782794Sobrien      \ifpdf
256882794Sobrien        \unhbox0             % PDF: 2nd arg given, show only it
256982794Sobrien      \else
257082794Sobrien        \unhbox0\ (\code{#1})% DVI: 2nd arg given, show both it and url
257182794Sobrien      \fi
257282794Sobrien    \else
257382794Sobrien      \code{#1}% only url given, so show it
257482794Sobrien    \fi
257538494Sobrien  \fi
257682794Sobrien  \endlink
257782794Sobrien\endgroup}
257838494Sobrien
2579310490Scy% This \urefbreak definition is the active one.
2580310490Scy\def\urefbreak{\begingroup \urefcatcodes \dourefbreak}
2581310490Scy\let\uref=\urefbreak
2582310490Scy\def\dourefbreak#1{\urefbreakfinish #1,,,\finish}
2583310490Scy\def\urefbreakfinish#1,#2,#3,#4\finish{% doesn't work in @example
2584310490Scy  \unsepspaces
2585310490Scy  \pdfurl{#1}%
2586310490Scy  \setbox0 = \hbox{\ignorespaces #3}%
2587310490Scy  \ifdim\wd0 > 0pt
2588310490Scy    \unhbox0 % third arg given, show only that
2589310490Scy  \else
2590310490Scy    \setbox0 = \hbox{\ignorespaces #2}%
2591310490Scy    \ifdim\wd0 > 0pt
2592310490Scy      \ifpdf
2593310490Scy        \unhbox0             % PDF: 2nd arg given, show only it
2594310490Scy      \else
2595310490Scy        \unhbox0\ (\urefcode{#1})% DVI: 2nd arg given, show both it and url
2596310490Scy      \fi
2597310490Scy    \else
2598310490Scy      \urefcode{#1}% only url given, so show it
2599310490Scy    \fi
2600310490Scy  \fi
2601310490Scy  \endlink
2602310490Scy\endgroup}
2603310490Scy
2604310490Scy% Allow line breaks around only a few characters (only).
2605310490Scy\def\urefcatcodes{%
2606310490Scy  \catcode\ampChar=\active   \catcode\dotChar=\active
2607310490Scy  \catcode\hashChar=\active  \catcode\questChar=\active
2608310490Scy  \catcode\slashChar=\active
2609310490Scy}
2610310490Scy{
2611310490Scy  \urefcatcodes
2612310490Scy  %
2613310490Scy  \global\def\urefcode{\begingroup
2614310490Scy    \setupmarkupstyle{code}%
2615310490Scy    \urefcatcodes
2616310490Scy    \let&\urefcodeamp
2617310490Scy    \let.\urefcodedot
2618310490Scy    \let#\urefcodehash
2619310490Scy    \let?\urefcodequest
2620310490Scy    \let/\urefcodeslash
2621310490Scy    \codex
2622310490Scy  }
2623310490Scy  %
2624310490Scy  % By default, they are just regular characters.
2625310490Scy  \global\def&{\normalamp}
2626310490Scy  \global\def.{\normaldot}
2627310490Scy  \global\def#{\normalhash}
2628310490Scy  \global\def?{\normalquest}
2629310490Scy  \global\def/{\normalslash}
2630310490Scy}
2631310490Scy
2632310490Scy% we put a little stretch before and after the breakable chars, to help
2633310490Scy% line breaking of long url's.  The unequal skips make look better in
2634310490Scy% cmtt at least, especially for dots.
2635310490Scy\def\urefprestretch{\urefprebreak \hskip0pt plus.13em }
2636310490Scy\def\urefpoststretch{\urefpostbreak \hskip0pt plus.1em }
2637310490Scy%
2638310490Scy\def\urefcodeamp{\urefprestretch \&\urefpoststretch}
2639310490Scy\def\urefcodedot{\urefprestretch .\urefpoststretch}
2640310490Scy\def\urefcodehash{\urefprestretch \#\urefpoststretch}
2641310490Scy\def\urefcodequest{\urefprestretch ?\urefpoststretch}
2642310490Scy\def\urefcodeslash{\futurelet\next\urefcodeslashfinish}
2643310490Scy{
2644310490Scy  \catcode`\/=\active
2645310490Scy  \global\def\urefcodeslashfinish{%
2646310490Scy    \urefprestretch \slashChar
2647310490Scy    % Allow line break only after the final / in a sequence of
2648310490Scy    % slashes, to avoid line break between the slashes in http://.
2649310490Scy    \ifx\next/\else \urefpoststretch \fi
2650310490Scy  }
2651310490Scy}
2652310490Scy
2653310490Scy% One more complication: by default we'll break after the special
2654310490Scy% characters, but some people like to break before the special chars, so
2655310490Scy% allow that.  Also allow no breaking at all, for manual control.
2656310490Scy% 
2657310490Scy\parseargdef\urefbreakstyle{%
2658310490Scy  \def\txiarg{#1}%
2659310490Scy  \ifx\txiarg\wordnone
2660310490Scy    \def\urefprebreak{\nobreak}\def\urefpostbreak{\nobreak}
2661310490Scy  \else\ifx\txiarg\wordbefore
2662310490Scy    \def\urefprebreak{\allowbreak}\def\urefpostbreak{\nobreak}
2663310490Scy  \else\ifx\txiarg\wordafter
2664310490Scy    \def\urefprebreak{\nobreak}\def\urefpostbreak{\allowbreak}
2665310490Scy  \else
2666310490Scy    \errhelp = \EMsimple
2667310490Scy    \errmessage{Unknown @urefbreakstyle setting `\txiarg'}%
2668310490Scy  \fi\fi\fi
2669310490Scy}
2670310490Scy\def\wordafter{after}
2671310490Scy\def\wordbefore{before}
2672310490Scy\def\wordnone{none}
2673310490Scy
2674310490Scy\urefbreakstyle after
2675310490Scy
2676174294Sobrien% @url synonym for @uref, since that's how everyone uses it.
2677174294Sobrien%
2678174294Sobrien\let\url=\uref
2679174294Sobrien
268082794Sobrien% rms does not like angle brackets --karl, 17may97.
268182794Sobrien% So now @email is just like @uref, unless we are pdf.
2682174294Sobrien%
268342629Sobrien%\def\email#1{\angleleft{\tt #1}\angleright}
268482794Sobrien\ifpdf
268582794Sobrien  \def\email#1{\doemail#1,,\finish}
268682794Sobrien  \def\doemail#1,#2,#3\finish{\begingroup
268782794Sobrien    \unsepspaces
268882794Sobrien    \pdfurl{mailto:#1}%
268982794Sobrien    \setbox0 = \hbox{\ignorespaces #2}%
269082794Sobrien    \ifdim\wd0>0pt\unhbox0\else\code{#1}\fi
269182794Sobrien    \endlink
269282794Sobrien  \endgroup}
269382794Sobrien\else
269482794Sobrien  \let\email=\uref
269582794Sobrien\fi
269638494Sobrien
2697310490Scy% @kbdinputstyle -- arg is `distinct' (@kbd uses slanted tty font always),
2698310490Scy%   `example' (@kbd uses ttsl only inside of @example and friends),
2699310490Scy%   or `code' (@kbd uses normal tty font always).
2700310490Scy\parseargdef\kbdinputstyle{%
2701310490Scy  \def\txiarg{#1}%
2702310490Scy  \ifx\txiarg\worddistinct
2703310490Scy    \gdef\kbdexamplefont{\ttsl}\gdef\kbdfont{\ttsl}%
2704310490Scy  \else\ifx\txiarg\wordexample
2705310490Scy    \gdef\kbdexamplefont{\ttsl}\gdef\kbdfont{\tt}%
2706310490Scy  \else\ifx\txiarg\wordcode
2707310490Scy    \gdef\kbdexamplefont{\tt}\gdef\kbdfont{\tt}%
2708310490Scy  \else
2709310490Scy    \errhelp = \EMsimple
2710310490Scy    \errmessage{Unknown @kbdinputstyle setting `\txiarg'}%
2711310490Scy  \fi\fi\fi
2712310490Scy}
2713310490Scy\def\worddistinct{distinct}
2714310490Scy\def\wordexample{example}
2715310490Scy\def\wordcode{code}
2716310490Scy
2717310490Scy% Default is `distinct'.
2718310490Scy\kbdinputstyle distinct
2719310490Scy
2720310490Scy% @kbd is like @code, except that if the argument is just one @key command,
2721310490Scy% then @kbd has no effect.
2722310490Scy\def\kbd#1{{\def\look{#1}\expandafter\kbdsub\look??\par}}
2723310490Scy
2724310490Scy\def\xkey{\key}
2725310490Scy\def\kbdsub#1#2#3\par{%
2726310490Scy  \def\one{#1}\def\three{#3}\def\threex{??}%
2727310490Scy  \ifx\one\xkey\ifx\threex\three \key{#2}%
2728310490Scy  \else{\tclose{\kbdfont\setupmarkupstyle{kbd}\look}}\fi
2729310490Scy  \else{\tclose{\kbdfont\setupmarkupstyle{kbd}\look}}\fi
2730310490Scy}
2731310490Scy
2732310490Scy% definition of @key that produces a lozenge.  Doesn't adjust to text size.
2733310490Scy%\setfont\keyrm\rmshape{8}{1000}{OT1}
2734310490Scy%\font\keysy=cmsy9
2735310490Scy%\def\key#1{{\keyrm\textfont2=\keysy \leavevmode\hbox{%
2736310490Scy%  \raise0.4pt\hbox{\angleleft}\kern-.08em\vtop{%
2737310490Scy%    \vbox{\hrule\kern-0.4pt
2738310490Scy%     \hbox{\raise0.4pt\hbox{\vphantom{\angleleft}}#1}}%
2739310490Scy%    \kern-0.4pt\hrule}%
2740310490Scy%  \kern-.06em\raise0.4pt\hbox{\angleright}}}}
2741310490Scy
2742310490Scy% definition of @key with no lozenge.  If the current font is already
2743310490Scy% monospace, don't change it; that way, we respect @kbdinputstyle.  But
2744310490Scy% if it isn't monospace, then use \tt.
274538494Sobrien%
2746310490Scy\def\key#1{{\setupmarkupstyle{key}%
2747310490Scy  \nohyphenation
2748310490Scy  \ifmonospace\else\tt\fi
2749310490Scy  #1}\null}
275038494Sobrien
2751310490Scy% @clicksequence{File @click{} Open ...}
2752310490Scy\def\clicksequence#1{\begingroup #1\endgroup}
2753310490Scy
2754310490Scy% @clickstyle @arrow   (by default)
2755310490Scy\parseargdef\clickstyle{\def\click{#1}}
2756310490Scy\def\click{\arrow}
2757310490Scy
275838494Sobrien% Typeset a dimension, e.g., `in' or `pt'.  The only reason for the
275942629Sobrien% argument is to make the input look right: @dmn{pt} instead of @dmn{}pt.
276038494Sobrien%
276138494Sobrien\def\dmn#1{\thinspace #1}
276238494Sobrien
276338494Sobrien% @l was never documented to mean ``switch to the Lisp font'',
276438494Sobrien% and it is not used as such in any manual I can find.  We need it for
276538494Sobrien% Polish suppressed-l.  --karl, 22sep96.
276638494Sobrien%\def\l#1{{\li #1}\null}
276738494Sobrien
2768174294Sobrien% @acronym for "FBI", "NATO", and the like.
2769174294Sobrien% We print this one point size smaller, since it's intended for
2770174294Sobrien% all-uppercase.
2771310490Scy%
2772174294Sobrien\def\acronym#1{\doacronym #1,,\finish}
2773174294Sobrien\def\doacronym#1,#2,#3\finish{%
2774174294Sobrien  {\selectfonts\lsize #1}%
2775174294Sobrien  \def\temp{#2}%
2776174294Sobrien  \ifx\temp\empty \else
2777174294Sobrien    \space ({\unsepspaces \ignorespaces \temp \unskip})%
2778174294Sobrien  \fi
2779310490Scy  \null % reset \spacefactor=1000
2780174294Sobrien}
278142629Sobrien
2782174294Sobrien% @abbr for "Comput. J." and the like.
2783174294Sobrien% No font change, but don't do end-of-sentence spacing.
2784310490Scy%
2785174294Sobrien\def\abbr#1{\doabbr #1,,\finish}
2786174294Sobrien\def\doabbr#1,#2,#3\finish{%
2787310490Scy  {\plainfrenchspacing #1}%
2788174294Sobrien  \def\temp{#2}%
2789174294Sobrien  \ifx\temp\empty \else
2790174294Sobrien    \space ({\unsepspaces \ignorespaces \temp \unskip})%
2791174294Sobrien  \fi
2792310490Scy  \null % reset \spacefactor=1000
2793174294Sobrien}
2794174294Sobrien
2795310490Scy% @asis just yields its argument.  Used with @table, for example.
2796310490Scy%
2797310490Scy\def\asis#1{#1}
2798310490Scy
2799310490Scy% @math outputs its argument in math mode.
2800310490Scy%
2801310490Scy% One complication: _ usually means subscripts, but it could also mean
2802310490Scy% an actual _ character, as in @math{@var{some_variable} + 1}.  So make
2803310490Scy% _ active, and distinguish by seeing if the current family is \slfam,
2804310490Scy% which is what @var uses.
2805310490Scy{
2806310490Scy  \catcode`\_ = \active
2807310490Scy  \gdef\mathunderscore{%
2808310490Scy    \catcode`\_=\active
2809310490Scy    \def_{\ifnum\fam=\slfam \_\else\sb\fi}%
2810310490Scy  }
2811310490Scy}
2812310490Scy% Another complication: we want \\ (and @\) to output a math (or tt) \.
2813310490Scy% FYI, plain.tex uses \\ as a temporary control sequence (for no
2814310490Scy% particular reason), but this is not advertised and we don't care.
2815310490Scy%
2816310490Scy% The \mathchar is class=0=ordinary, family=7=ttfam, position=5C=\.
2817310490Scy\def\mathbackslash{\ifnum\fam=\ttfam \mathchar"075C \else\backslash \fi}
2818310490Scy%
2819310490Scy\def\math{%
2820310490Scy  \tex
2821310490Scy  \mathunderscore
2822310490Scy  \let\\ = \mathbackslash
2823310490Scy  \mathactive
2824310490Scy  % make the texinfo accent commands work in math mode
2825310490Scy  \let\"=\ddot
2826310490Scy  \let\'=\acute
2827310490Scy  \let\==\bar
2828310490Scy  \let\^=\hat
2829310490Scy  \let\`=\grave
2830310490Scy  \let\u=\breve
2831310490Scy  \let\v=\check
2832310490Scy  \let\~=\tilde
2833310490Scy  \let\dotaccent=\dot
2834310490Scy  $\finishmath
2835310490Scy}
2836310490Scy\def\finishmath#1{#1$\endgroup}  % Close the group opened by \tex.
2837310490Scy
2838310490Scy% Some active characters (such as <) are spaced differently in math.
2839310490Scy% We have to reset their definitions in case the @math was an argument
2840310490Scy% to a command which sets the catcodes (such as @item or @section).
2841310490Scy%
2842310490Scy{
2843310490Scy  \catcode`^ = \active
2844310490Scy  \catcode`< = \active
2845310490Scy  \catcode`> = \active
2846310490Scy  \catcode`+ = \active
2847310490Scy  \catcode`' = \active
2848310490Scy  \gdef\mathactive{%
2849310490Scy    \let^ = \ptexhat
2850310490Scy    \let< = \ptexless
2851310490Scy    \let> = \ptexgtr
2852310490Scy    \let+ = \ptexplus
2853310490Scy    \let' = \ptexquoteright
2854310490Scy  }
2855310490Scy}
2856310490Scy
2857310490Scy% ctrl is no longer a Texinfo command, but leave this definition for fun.
2858310490Scy\def\ctrl #1{{\tt \rawbackslash \hat}#1}
2859310490Scy
2860310490Scy% @inlinefmt{FMTNAME,PROCESSED-TEXT} and @inlineraw{FMTNAME,RAW-TEXT}.
2861310490Scy% Ignore unless FMTNAME == tex; then it is like @iftex and @tex,
2862310490Scy% except specified as a normal braced arg, so no newlines to worry about.
2863310490Scy% 
2864310490Scy\def\outfmtnametex{tex}
2865310490Scy%
2866310490Scy\long\def\inlinefmt#1{\doinlinefmt #1,\finish}
2867310490Scy\long\def\doinlinefmt#1,#2,\finish{%
2868310490Scy  \def\inlinefmtname{#1}%
2869310490Scy  \ifx\inlinefmtname\outfmtnametex \ignorespaces #2\fi
2870310490Scy}
2871310490Scy% For raw, must switch into @tex before parsing the argument, to avoid
2872310490Scy% setting catcodes prematurely.  Doing it this way means that, for
2873310490Scy% example, @inlineraw{html, foo{bar} gets a parse error instead of being
2874310490Scy% ignored.  But this isn't important because if people want a literal
2875310490Scy% *right* brace they would have to use a command anyway, so they may as
2876310490Scy% well use a command to get a left brace too.  We could re-use the
2877310490Scy% delimiter character idea from \verb, but it seems like overkill.
2878310490Scy% 
2879310490Scy\long\def\inlineraw{\tex \doinlineraw}
2880310490Scy\long\def\doinlineraw#1{\doinlinerawtwo #1,\finish}
2881310490Scy\def\doinlinerawtwo#1,#2,\finish{%
2882310490Scy  \def\inlinerawname{#1}%
2883310490Scy  \ifx\inlinerawname\outfmtnametex \ignorespaces #2\fi
2884310490Scy  \endgroup % close group opened by \tex.
2885310490Scy}
2886310490Scy
2887310490Scy
2888310490Scy\message{glyphs,}
2889310490Scy% and logos.
2890310490Scy
2891310490Scy% @@ prints an @, as does @atchar{}.
2892310490Scy\def\@{\char64 }
2893310490Scy\let\atchar=\@
2894310490Scy
2895310490Scy% @{ @} @lbracechar{} @rbracechar{} all generate brace characters.
2896310490Scy% Unless we're in typewriter, use \ecfont because the CM text fonts do
2897310490Scy% not have braces, and we don't want to switch into math.
2898310490Scy\def\mylbrace{{\ifmonospace\else\ecfont\fi \char123}}
2899310490Scy\def\myrbrace{{\ifmonospace\else\ecfont\fi \char125}}
2900310490Scy\let\{=\mylbrace \let\lbracechar=\{
2901310490Scy\let\}=\myrbrace \let\rbracechar=\}
2902310490Scy\begingroup
2903310490Scy  % Definitions to produce \{ and \} commands for indices,
2904310490Scy  % and @{ and @} for the aux/toc files.
2905310490Scy  \catcode`\{ = \other \catcode`\} = \other
2906310490Scy  \catcode`\[ = 1 \catcode`\] = 2
2907310490Scy  \catcode`\! = 0 \catcode`\\ = \other
2908310490Scy  !gdef!lbracecmd[\{]%
2909310490Scy  !gdef!rbracecmd[\}]%
2910310490Scy  !gdef!lbraceatcmd[@{]%
2911310490Scy  !gdef!rbraceatcmd[@}]%
2912310490Scy!endgroup
2913310490Scy
2914310490Scy% @comma{} to avoid , parsing problems.
2915310490Scy\let\comma = ,
2916310490Scy
2917310490Scy% Accents: @, @dotaccent @ringaccent @ubaraccent @udotaccent
2918310490Scy% Others are defined by plain TeX: @` @' @" @^ @~ @= @u @v @H.
2919310490Scy\let\, = \ptexc
2920310490Scy\let\dotaccent = \ptexdot
2921310490Scy\def\ringaccent#1{{\accent23 #1}}
2922310490Scy\let\tieaccent = \ptext
2923310490Scy\let\ubaraccent = \ptexb
2924310490Scy\let\udotaccent = \d
2925310490Scy
2926310490Scy% Other special characters: @questiondown @exclamdown @ordf @ordm
2927310490Scy% Plain TeX defines: @AA @AE @O @OE @L (plus lowercase versions) @ss.
2928310490Scy\def\questiondown{?`}
2929310490Scy\def\exclamdown{!`}
2930310490Scy\def\ordf{\leavevmode\raise1ex\hbox{\selectfonts\lllsize \underbar{a}}}
2931310490Scy\def\ordm{\leavevmode\raise1ex\hbox{\selectfonts\lllsize \underbar{o}}}
2932310490Scy
2933310490Scy% Dotless i and dotless j, used for accents.
2934310490Scy\def\imacro{i}
2935310490Scy\def\jmacro{j}
2936310490Scy\def\dotless#1{%
2937310490Scy  \def\temp{#1}%
2938310490Scy  \ifx\temp\imacro \ifmmode\imath \else\ptexi \fi
2939310490Scy  \else\ifx\temp\jmacro \ifmmode\jmath \else\j \fi
2940310490Scy  \else \errmessage{@dotless can be used only with i or j}%
2941310490Scy  \fi\fi
2942310490Scy}
2943310490Scy
2944310490Scy% The \TeX{} logo, as in plain, but resetting the spacing so that a
2945310490Scy% period following counts as ending a sentence.  (Idea found in latex.)
2946310490Scy%
2947310490Scy\edef\TeX{\TeX \spacefactor=1000 }
2948310490Scy
2949310490Scy% @LaTeX{} logo.  Not quite the same results as the definition in
2950310490Scy% latex.ltx, since we use a different font for the raised A; it's most
2951310490Scy% convenient for us to use an explicitly smaller font, rather than using
2952310490Scy% the \scriptstyle font (since we don't reset \scriptstyle and
2953310490Scy% \scriptscriptstyle).
2954310490Scy%
2955310490Scy\def\LaTeX{%
2956310490Scy  L\kern-.36em
2957310490Scy  {\setbox0=\hbox{T}%
2958310490Scy   \vbox to \ht0{\hbox{%
2959310490Scy     \ifx\textnominalsize\xwordpt
2960310490Scy       % for 10pt running text, \lllsize (8pt) is too small for the A in LaTeX.
2961310490Scy       % Revert to plain's \scriptsize, which is 7pt.
2962310490Scy       \count255=\the\fam $\fam\count255 \scriptstyle A$%
2963310490Scy     \else
2964310490Scy       % For 11pt, we can use our lllsize.
2965310490Scy       \selectfonts\lllsize A%
2966310490Scy     \fi
2967310490Scy     }%
2968310490Scy     \vss
2969310490Scy  }}%
2970310490Scy  \kern-.15em
2971310490Scy  \TeX
2972310490Scy}
2973310490Scy
2974310490Scy% Some math mode symbols.
2975310490Scy\def\bullet{$\ptexbullet$}
2976310490Scy\def\geq{\ifmmode \ge\else $\ge$\fi}
2977310490Scy\def\leq{\ifmmode \le\else $\le$\fi}
2978310490Scy\def\minus{\ifmmode -\else $-$\fi}
2979310490Scy
2980310490Scy% @dots{} outputs an ellipsis using the current font.
2981310490Scy% We do .5em per period so that it has the same spacing in the cm
2982310490Scy% typewriter fonts as three actual period characters; on the other hand,
2983310490Scy% in other typewriter fonts three periods are wider than 1.5em.  So do
2984310490Scy% whichever is larger.
2985310490Scy%
2986310490Scy\def\dots{%
2987310490Scy  \leavevmode
2988310490Scy  \setbox0=\hbox{...}% get width of three periods
2989310490Scy  \ifdim\wd0 > 1.5em
2990310490Scy    \dimen0 = \wd0
2991310490Scy  \else
2992310490Scy    \dimen0 = 1.5em
2993310490Scy  \fi
2994310490Scy  \hbox to \dimen0{%
2995310490Scy    \hskip 0pt plus.25fil
2996310490Scy    .\hskip 0pt plus1fil
2997310490Scy    .\hskip 0pt plus1fil
2998310490Scy    .\hskip 0pt plus.5fil
2999310490Scy  }%
3000310490Scy}
3001310490Scy
3002310490Scy% @enddots{} is an end-of-sentence ellipsis.
3003310490Scy%
3004310490Scy\def\enddots{%
3005310490Scy  \dots
3006310490Scy  \spacefactor=\endofsentencespacefactor
3007310490Scy}
3008310490Scy
3009310490Scy% @point{}, @result{}, @expansion{}, @print{}, @equiv{}.
3010310490Scy%
3011310490Scy% Since these characters are used in examples, they should be an even number of
3012310490Scy% \tt widths. Each \tt character is 1en, so two makes it 1em.
3013310490Scy%
3014310490Scy\def\point{$\star$}
3015310490Scy\def\arrow{\leavevmode\raise.05ex\hbox to 1em{\hfil$\rightarrow$\hfil}}
3016310490Scy\def\result{\leavevmode\raise.05ex\hbox to 1em{\hfil$\Rightarrow$\hfil}}
3017310490Scy\def\expansion{\leavevmode\hbox to 1em{\hfil$\mapsto$\hfil}}
3018310490Scy\def\print{\leavevmode\lower.1ex\hbox to 1em{\hfil$\dashv$\hfil}}
3019310490Scy\def\equiv{\leavevmode\hbox to 1em{\hfil$\ptexequiv$\hfil}}
3020310490Scy
3021310490Scy% The @error{} command.
3022310490Scy% Adapted from the TeXbook's \boxit.
3023310490Scy%
3024310490Scy\newbox\errorbox
3025310490Scy%
3026310490Scy{\tentt \global\dimen0 = 3em}% Width of the box.
3027310490Scy\dimen2 = .55pt % Thickness of rules
3028310490Scy% The text. (`r' is open on the right, `e' somewhat less so on the left.)
3029310490Scy\setbox0 = \hbox{\kern-.75pt \reducedsf \putworderror\kern-1.5pt}
3030310490Scy%
3031310490Scy\setbox\errorbox=\hbox to \dimen0{\hfil
3032310490Scy   \hsize = \dimen0 \advance\hsize by -5.8pt % Space to left+right.
3033310490Scy   \advance\hsize by -2\dimen2 % Rules.
3034310490Scy   \vbox{%
3035310490Scy      \hrule height\dimen2
3036310490Scy      \hbox{\vrule width\dimen2 \kern3pt          % Space to left of text.
3037310490Scy         \vtop{\kern2.4pt \box0 \kern2.4pt}% Space above/below.
3038310490Scy         \kern3pt\vrule width\dimen2}% Space to right.
3039310490Scy      \hrule height\dimen2}
3040310490Scy    \hfil}
3041310490Scy%
3042310490Scy\def\error{\leavevmode\lower.7ex\copy\errorbox}
3043310490Scy
3044174294Sobrien% @pounds{} is a sterling sign, which Knuth put in the CM italic font.
3045174294Sobrien%
304638494Sobrien\def\pounds{{\it\$}}
304738494Sobrien
3048310490Scy% @euro{} comes from a separate font, depending on the current style.
3049310490Scy% We use the free feym* fonts from the eurosym package by Henrik
3050310490Scy% Theiling, which support regular, slanted, bold and bold slanted (and
3051310490Scy% "outlined" (blackboard board, sort of) versions, which we don't need).
3052310490Scy% It is available from http://www.ctan.org/tex-archive/fonts/eurosym.
3053310490Scy%
3054310490Scy% Although only regular is the truly official Euro symbol, we ignore
3055310490Scy% that.  The Euro is designed to be slightly taller than the regular
3056310490Scy% font height.
3057310490Scy%
3058310490Scy% feymr - regular
3059310490Scy% feymo - slanted
3060310490Scy% feybr - bold
3061310490Scy% feybo - bold slanted
3062310490Scy%
3063310490Scy% There is no good (free) typewriter version, to my knowledge.
3064310490Scy% A feymr10 euro is ~7.3pt wide, while a normal cmtt10 char is ~5.25pt wide.
3065310490Scy% Hmm.
3066310490Scy%
3067310490Scy% Also doesn't work in math.  Do we need to do math with euro symbols?
3068310490Scy% Hope not.
3069310490Scy%
3070310490Scy%
3071310490Scy\def\euro{{\eurofont e}}
3072310490Scy\def\eurofont{%
3073310490Scy  % We set the font at each command, rather than predefining it in
3074310490Scy  % \textfonts and the other font-switching commands, so that
3075310490Scy  % installations which never need the symbol don't have to have the
3076310490Scy  % font installed.
3077310490Scy  %
3078310490Scy  % There is only one designed size (nominal 10pt), so we always scale
3079310490Scy  % that to the current nominal size.
3080310490Scy  %
3081310490Scy  % By the way, simply using "at 1em" works for cmr10 and the like, but
3082310490Scy  % does not work for cmbx10 and other extended/shrunken fonts.
3083310490Scy  %
3084310490Scy  \def\eurosize{\csname\curfontsize nominalsize\endcsname}%
3085310490Scy  %
3086310490Scy  \ifx\curfontstyle\bfstylename
3087310490Scy    % bold:
3088310490Scy    \font\thiseurofont = \ifusingit{feybo10}{feybr10} at \eurosize
3089310490Scy  \else
3090310490Scy    % regular:
3091310490Scy    \font\thiseurofont = \ifusingit{feymo10}{feymr10} at \eurosize
3092310490Scy  \fi
3093310490Scy  \thiseurofont
3094310490Scy}
3095310490Scy
3096310490Scy% Glyphs from the EC fonts.  We don't use \let for the aliases, because
3097310490Scy% sometimes we redefine the original macro, and the alias should reflect
3098310490Scy% the redefinition.
3099310490Scy%
3100310490Scy% Use LaTeX names for the Icelandic letters.
3101310490Scy\def\DH{{\ecfont \char"D0}} % Eth
3102310490Scy\def\dh{{\ecfont \char"F0}} % eth
3103310490Scy\def\TH{{\ecfont \char"DE}} % Thorn
3104310490Scy\def\th{{\ecfont \char"FE}} % thorn
3105310490Scy%
3106310490Scy\def\guillemetleft{{\ecfont \char"13}}
3107310490Scy\def\guillemotleft{\guillemetleft}
3108310490Scy\def\guillemetright{{\ecfont \char"14}}
3109310490Scy\def\guillemotright{\guillemetright}
3110310490Scy\def\guilsinglleft{{\ecfont \char"0E}}
3111310490Scy\def\guilsinglright{{\ecfont \char"0F}}
3112310490Scy\def\quotedblbase{{\ecfont \char"12}}
3113310490Scy\def\quotesinglbase{{\ecfont \char"0D}}
3114310490Scy%
3115310490Scy% This positioning is not perfect (see the ogonek LaTeX package), but
3116310490Scy% we have the precomposed glyphs for the most common cases.  We put the
3117310490Scy% tests to use those glyphs in the single \ogonek macro so we have fewer
3118310490Scy% dummy definitions to worry about for index entries, etc.
3119310490Scy%
3120310490Scy% ogonek is also used with other letters in Lithuanian (IOU), but using
3121310490Scy% the precomposed glyphs for those is not so easy since they aren't in
3122310490Scy% the same EC font.
3123310490Scy\def\ogonek#1{{%
3124310490Scy  \def\temp{#1}%
3125310490Scy  \ifx\temp\macrocharA\Aogonek
3126310490Scy  \else\ifx\temp\macrochara\aogonek
3127310490Scy  \else\ifx\temp\macrocharE\Eogonek
3128310490Scy  \else\ifx\temp\macrochare\eogonek
3129310490Scy  \else
3130310490Scy    \ecfont \setbox0=\hbox{#1}%
3131310490Scy    \ifdim\ht0=1ex\accent"0C #1%
3132310490Scy    \else\ooalign{\unhbox0\crcr\hidewidth\char"0C \hidewidth}%
3133310490Scy    \fi
3134310490Scy  \fi\fi\fi\fi
3135310490Scy  }%
3136310490Scy}
3137310490Scy\def\Aogonek{{\ecfont \char"81}}\def\macrocharA{A}
3138310490Scy\def\aogonek{{\ecfont \char"A1}}\def\macrochara{a}
3139310490Scy\def\Eogonek{{\ecfont \char"86}}\def\macrocharE{E}
3140310490Scy\def\eogonek{{\ecfont \char"A6}}\def\macrochare{e}
3141310490Scy%
3142310490Scy% Use the ec* fonts (cm-super in outline format) for non-CM glyphs.
3143310490Scy\def\ecfont{%
3144310490Scy  % We can't distinguish serif/sans and italic/slanted, but this
3145310490Scy  % is used for crude hacks anyway (like adding French and German
3146310490Scy  % quotes to documents typeset with CM, where we lose kerning), so
3147310490Scy  % hopefully nobody will notice/care.
3148310490Scy  \edef\ecsize{\csname\curfontsize ecsize\endcsname}%
3149310490Scy  \edef\nominalsize{\csname\curfontsize nominalsize\endcsname}%
3150310490Scy  \ifmonospace
3151310490Scy    % typewriter:
3152310490Scy    \font\thisecfont = ectt\ecsize \space at \nominalsize
3153310490Scy  \else
3154310490Scy    \ifx\curfontstyle\bfstylename
3155310490Scy      % bold:
3156310490Scy      \font\thisecfont = ecb\ifusingit{i}{x}\ecsize \space at \nominalsize
3157310490Scy    \else
3158310490Scy      % regular:
3159310490Scy      \font\thisecfont = ec\ifusingit{ti}{rm}\ecsize \space at \nominalsize
3160310490Scy    \fi
3161310490Scy  \fi
3162310490Scy  \thisecfont
3163310490Scy}
3164310490Scy
3165174294Sobrien% @registeredsymbol - R in a circle.  The font for the R should really
3166174294Sobrien% be smaller yet, but lllsize is the best we can do for now.
3167174294Sobrien% Adapted from the plain.tex definition of \copyright.
3168174294Sobrien%
3169174294Sobrien\def\registeredsymbol{%
3170174294Sobrien  $^{{\ooalign{\hfil\raise.07ex\hbox{\selectfonts\lllsize R}%
3171174294Sobrien               \hfil\crcr\Orb}}%
3172174294Sobrien    }$%
3173174294Sobrien}
317438494Sobrien
3175310490Scy% @textdegree - the normal degrees sign.
3176310490Scy%
3177310490Scy\def\textdegree{$^\circ$}
3178310490Scy
3179174294Sobrien% Laurent Siebenmann reports \Orb undefined with:
3180174294Sobrien%  Textures 1.7.7 (preloaded format=plain 93.10.14)  (68K)  16 APR 2004 02:38
3181174294Sobrien% so we'll define it if necessary.
3182310490Scy%
3183310490Scy\ifx\Orb\thisisundefined
3184174294Sobrien\def\Orb{\mathhexbox20D}
3185174294Sobrien\fi
3186174294Sobrien
3187310490Scy% Quotes.
3188310490Scy\chardef\quotedblleft="5C
3189310490Scy\chardef\quotedblright=`\"
3190310490Scy\chardef\quoteleft=`\`
3191310490Scy\chardef\quoteright=`\'
3192174294Sobrien
3193310490Scy
319438494Sobrien\message{page headings,}
319538494Sobrien
319638494Sobrien\newskip\titlepagetopglue \titlepagetopglue = 1.5in
319738494Sobrien\newskip\titlepagebottomglue \titlepagebottomglue = 2pc
319838494Sobrien
319938494Sobrien% First the title page.  Must do @settitle before @titlepage.
320038494Sobrien\newif\ifseenauthor
320138494Sobrien\newif\iffinishedtitlepage
320238494Sobrien
320342629Sobrien% Do an implicit @contents or @shortcontents after @end titlepage if the
320482794Sobrien% user says @setcontentsaftertitlepage or @setshortcontentsaftertitlepage.
320582794Sobrien%
320642629Sobrien\newif\ifsetcontentsaftertitlepage
320742629Sobrien \let\setcontentsaftertitlepage = \setcontentsaftertitlepagetrue
320842629Sobrien\newif\ifsetshortcontentsaftertitlepage
320942629Sobrien \let\setshortcontentsaftertitlepage = \setshortcontentsaftertitlepagetrue
321042629Sobrien
3211310490Scy\parseargdef\shorttitlepage{%
3212310490Scy  \begingroup \hbox{}\vskip 1.5in \chaprm \centerline{#1}%
3213310490Scy  \endgroup\page\hbox{}\page}
321438494Sobrien
3215174294Sobrien\envdef\titlepage{%
3216174294Sobrien  % Open one extra group, as we want to close it in the middle of \Etitlepage.
3217174294Sobrien  \begingroup
3218174294Sobrien    \parindent=0pt \textfonts
3219174294Sobrien    % Leave some space at the very top of the page.
3220174294Sobrien    \vglue\titlepagetopglue
3221174294Sobrien    % No rule at page bottom unless we print one at the top with @title.
3222174294Sobrien    \finishedtitlepagetrue
3223174294Sobrien    %
3224174294Sobrien    % Most title ``pages'' are actually two pages long, with space
3225174294Sobrien    % at the top of the second.  We don't want the ragged left on the second.
3226174294Sobrien    \let\oldpage = \page
3227174294Sobrien    \def\page{%
322838494Sobrien      \iffinishedtitlepage\else
3229174294Sobrien	 \finishtitlepage
323038494Sobrien      \fi
323138494Sobrien      \let\page = \oldpage
3232174294Sobrien      \page
3233174294Sobrien      \null
3234174294Sobrien    }%
323538494Sobrien}
323638494Sobrien
323738494Sobrien\def\Etitlepage{%
3238174294Sobrien    \iffinishedtitlepage\else
3239174294Sobrien	\finishtitlepage
3240174294Sobrien    \fi
3241174294Sobrien    % It is important to do the page break before ending the group,
3242174294Sobrien    % because the headline and footline are only empty inside the group.
3243174294Sobrien    % If we use the new definition of \page, we always get a blank page
3244174294Sobrien    % after the title page, which we certainly don't want.
3245174294Sobrien    \oldpage
3246174294Sobrien  \endgroup
3247174294Sobrien  %
3248174294Sobrien  % Need this before the \...aftertitlepage checks so that if they are
3249174294Sobrien  % in effect the toc pages will come out with page numbers.
3250174294Sobrien  \HEADINGSon
3251174294Sobrien  %
3252174294Sobrien  % If they want short, they certainly want long too.
3253174294Sobrien  \ifsetshortcontentsaftertitlepage
3254174294Sobrien    \shortcontents
3255174294Sobrien    \contents
3256174294Sobrien    \global\let\shortcontents = \relax
3257174294Sobrien    \global\let\contents = \relax
3258174294Sobrien  \fi
3259174294Sobrien  %
3260174294Sobrien  \ifsetcontentsaftertitlepage
3261174294Sobrien    \contents
3262174294Sobrien    \global\let\contents = \relax
3263174294Sobrien    \global\let\shortcontents = \relax
3264174294Sobrien  \fi
326538494Sobrien}
326638494Sobrien
326738494Sobrien\def\finishtitlepage{%
3268174294Sobrien  \vskip4pt \hrule height 2pt width \hsize
3269174294Sobrien  \vskip\titlepagebottomglue
3270174294Sobrien  \finishedtitlepagetrue
327138494Sobrien}
327238494Sobrien
3273310490Scy% Settings used for typesetting titles: no hyphenation, no indentation,
3274310490Scy% don't worry much about spacing, ragged right.  This should be used
3275310490Scy% inside a \vbox, and fonts need to be set appropriately first.  Because
3276310490Scy% it is always used for titles, nothing else, we call \rmisbold.  \par
3277310490Scy% should be specified before the end of the \vbox, since a vbox is a group.
3278310490Scy% 
3279310490Scy\def\raggedtitlesettings{%
3280310490Scy  \rmisbold
3281310490Scy  \hyphenpenalty=10000
3282310490Scy  \parindent=0pt
3283310490Scy  \tolerance=5000
3284310490Scy  \ptexraggedright
3285310490Scy}
3286174294Sobrien
3287310490Scy% Macros to be used within @titlepage:
3288310490Scy
3289174294Sobrien\let\subtitlerm=\tenrm
3290174294Sobrien\def\subtitlefont{\subtitlerm \normalbaselineskip = 13pt \normalbaselines}
3291174294Sobrien
3292174294Sobrien\parseargdef\title{%
3293174294Sobrien  \checkenv\titlepage
3294310490Scy  \vbox{\titlefonts \raggedtitlesettings #1\par}%
3295174294Sobrien  % print a rule at the page bottom also.
3296174294Sobrien  \finishedtitlepagefalse
3297174294Sobrien  \vskip4pt \hrule height 4pt width \hsize \vskip4pt
3298174294Sobrien}
3299174294Sobrien
3300174294Sobrien\parseargdef\subtitle{%
3301174294Sobrien  \checkenv\titlepage
3302174294Sobrien  {\subtitlefont \rightline{#1}}%
3303174294Sobrien}
3304174294Sobrien
3305174294Sobrien% @author should come last, but may come many times.
3306174294Sobrien% It can also be used inside @quotation.
3307174294Sobrien%
3308174294Sobrien\parseargdef\author{%
3309174294Sobrien  \def\temp{\quotation}%
3310174294Sobrien  \ifx\thisenv\temp
3311174294Sobrien    \def\quotationauthor{#1}% printed in \Equotation.
3312174294Sobrien  \else
3313174294Sobrien    \checkenv\titlepage
3314174294Sobrien    \ifseenauthor\else \vskip 0pt plus 1filll \seenauthortrue \fi
3315310490Scy    {\secfonts\rmisbold \leftline{#1}}%
3316174294Sobrien  \fi
3317174294Sobrien}
3318174294Sobrien
3319174294Sobrien
3320310490Scy% Set up page headings and footings.
332138494Sobrien
332238494Sobrien\let\thispage=\folio
332338494Sobrien
332442629Sobrien\newtoks\evenheadline    % headline on even pages
332542629Sobrien\newtoks\oddheadline     % headline on odd pages
332642629Sobrien\newtoks\evenfootline    % footline on even pages
332742629Sobrien\newtoks\oddfootline     % footline on odd pages
332838494Sobrien
3329174294Sobrien% Now make TeX use those variables
333038494Sobrien\headline={{\textfonts\rm \ifodd\pageno \the\oddheadline
333138494Sobrien                            \else \the\evenheadline \fi}}
333238494Sobrien\footline={{\textfonts\rm \ifodd\pageno \the\oddfootline
333338494Sobrien                            \else \the\evenfootline \fi}\HEADINGShook}
333438494Sobrien\let\HEADINGShook=\relax
333538494Sobrien
333638494Sobrien% Commands to set those variables.
333738494Sobrien% For example, this is what  @headings on  does
333838494Sobrien% @evenheading @thistitle|@thispage|@thischapter
333938494Sobrien% @oddheading @thischapter|@thispage|@thistitle
334038494Sobrien% @evenfooting @thisfile||
334138494Sobrien% @oddfooting ||@thisfile
334238494Sobrien
3343174294Sobrien
334438494Sobrien\def\evenheading{\parsearg\evenheadingxxx}
3345174294Sobrien\def\evenheadingxxx #1{\evenheadingyyy #1\|\|\|\|\finish}
3346174294Sobrien\def\evenheadingyyy #1\|#2\|#3\|#4\finish{%
334738494Sobrien\global\evenheadline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
334838494Sobrien
3349174294Sobrien\def\oddheading{\parsearg\oddheadingxxx}
3350174294Sobrien\def\oddheadingxxx #1{\oddheadingyyy #1\|\|\|\|\finish}
3351174294Sobrien\def\oddheadingyyy #1\|#2\|#3\|#4\finish{%
335238494Sobrien\global\oddheadline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
335338494Sobrien
3354174294Sobrien\parseargdef\everyheading{\oddheadingxxx{#1}\evenheadingxxx{#1}}%
335538494Sobrien
3356174294Sobrien\def\evenfooting{\parsearg\evenfootingxxx}
3357174294Sobrien\def\evenfootingxxx #1{\evenfootingyyy #1\|\|\|\|\finish}
3358174294Sobrien\def\evenfootingyyy #1\|#2\|#3\|#4\finish{%
335938494Sobrien\global\evenfootline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
336038494Sobrien
3361174294Sobrien\def\oddfooting{\parsearg\oddfootingxxx}
3362174294Sobrien\def\oddfootingxxx #1{\oddfootingyyy #1\|\|\|\|\finish}
3363174294Sobrien\def\oddfootingyyy #1\|#2\|#3\|#4\finish{%
336438494Sobrien  \global\oddfootline = {\rlap{\centerline{#2}}\line{#1\hfil#3}}%
336538494Sobrien  %
336638494Sobrien  % Leave some space for the footline.  Hopefully ok to assume
336738494Sobrien  % @evenfooting will not be used by itself.
3368310490Scy  \global\advance\pageheight by -12pt
3369310490Scy  \global\advance\vsize by -12pt
337038494Sobrien}
337138494Sobrien
3372174294Sobrien\parseargdef\everyfooting{\oddfootingxxx{#1}\evenfootingxxx{#1}}
337338494Sobrien
3374310490Scy% @evenheadingmarks top     \thischapter <- chapter at the top of a page
3375310490Scy% @evenheadingmarks bottom  \thischapter <- chapter at the bottom of a page
3376310490Scy%
3377310490Scy% The same set of arguments for:
3378310490Scy%
3379310490Scy% @oddheadingmarks
3380310490Scy% @evenfootingmarks
3381310490Scy% @oddfootingmarks
3382310490Scy% @everyheadingmarks
3383310490Scy% @everyfootingmarks
3384174294Sobrien
3385310490Scy\def\evenheadingmarks{\headingmarks{even}{heading}}
3386310490Scy\def\oddheadingmarks{\headingmarks{odd}{heading}}
3387310490Scy\def\evenfootingmarks{\headingmarks{even}{footing}}
3388310490Scy\def\oddfootingmarks{\headingmarks{odd}{footing}}
3389310490Scy\def\everyheadingmarks#1 {\headingmarks{even}{heading}{#1}
3390310490Scy                          \headingmarks{odd}{heading}{#1} }
3391310490Scy\def\everyfootingmarks#1 {\headingmarks{even}{footing}{#1}
3392310490Scy                          \headingmarks{odd}{footing}{#1} }
3393310490Scy% #1 = even/odd, #2 = heading/footing, #3 = top/bottom.
3394310490Scy\def\headingmarks#1#2#3 {%
3395310490Scy  \expandafter\let\expandafter\temp \csname get#3headingmarks\endcsname
3396310490Scy  \global\expandafter\let\csname get#1#2marks\endcsname \temp
3397310490Scy}
3398310490Scy
3399310490Scy\everyheadingmarks bottom
3400310490Scy\everyfootingmarks bottom
3401310490Scy
340238494Sobrien% @headings double      turns headings on for double-sided printing.
340338494Sobrien% @headings single      turns headings on for single-sided printing.
340438494Sobrien% @headings off         turns them off.
340538494Sobrien% @headings on          same as @headings double, retained for compatibility.
340638494Sobrien% @headings after       turns on double-sided headings after this page.
340738494Sobrien% @headings doubleafter turns on double-sided headings after this page.
340838494Sobrien% @headings singleafter turns on single-sided headings after this page.
340938494Sobrien% By default, they are off at the start of a document,
341038494Sobrien% and turned `on' after @end titlepage.
341138494Sobrien
341238494Sobrien\def\headings #1 {\csname HEADINGS#1\endcsname}
341338494Sobrien
3414310490Scy\def\headingsoff{% non-global headings elimination
3415310490Scy  \evenheadline={\hfil}\evenfootline={\hfil}%
3416310490Scy   \oddheadline={\hfil}\oddfootline={\hfil}%
3417310490Scy}
3418310490Scy
3419310490Scy\def\HEADINGSoff{{\globaldefs=1 \headingsoff}} % global setting
3420310490Scy\HEADINGSoff  % it's the default
3421310490Scy
342238494Sobrien% When we turn headings on, set the page number to 1.
342338494Sobrien% For double-sided printing, put current file name in lower left corner,
342438494Sobrien% chapter name on inside top of right hand pages, document
342538494Sobrien% title on inside top of left hand pages, and page numbers on outside top
342638494Sobrien% edge of all pages.
3427174294Sobrien\def\HEADINGSdouble{%
342838494Sobrien\global\pageno=1
342938494Sobrien\global\evenfootline={\hfil}
343038494Sobrien\global\oddfootline={\hfil}
343138494Sobrien\global\evenheadline={\line{\folio\hfil\thistitle}}
343238494Sobrien\global\oddheadline={\line{\thischapter\hfil\folio}}
343338494Sobrien\global\let\contentsalignmacro = \chapoddpage
343438494Sobrien}
343538494Sobrien\let\contentsalignmacro = \chappager
343638494Sobrien
343738494Sobrien% For single-sided printing, chapter title goes across top left of page,
343838494Sobrien% page number on top right.
3439174294Sobrien\def\HEADINGSsingle{%
344038494Sobrien\global\pageno=1
344138494Sobrien\global\evenfootline={\hfil}
344238494Sobrien\global\oddfootline={\hfil}
344338494Sobrien\global\evenheadline={\line{\thischapter\hfil\folio}}
344438494Sobrien\global\oddheadline={\line{\thischapter\hfil\folio}}
344538494Sobrien\global\let\contentsalignmacro = \chappager
344638494Sobrien}
344738494Sobrien\def\HEADINGSon{\HEADINGSdouble}
344838494Sobrien
344938494Sobrien\def\HEADINGSafter{\let\HEADINGShook=\HEADINGSdoublex}
345038494Sobrien\let\HEADINGSdoubleafter=\HEADINGSafter
345138494Sobrien\def\HEADINGSdoublex{%
345238494Sobrien\global\evenfootline={\hfil}
345338494Sobrien\global\oddfootline={\hfil}
345438494Sobrien\global\evenheadline={\line{\folio\hfil\thistitle}}
345538494Sobrien\global\oddheadline={\line{\thischapter\hfil\folio}}
345638494Sobrien\global\let\contentsalignmacro = \chapoddpage
345738494Sobrien}
345838494Sobrien
345938494Sobrien\def\HEADINGSsingleafter{\let\HEADINGShook=\HEADINGSsinglex}
346038494Sobrien\def\HEADINGSsinglex{%
346138494Sobrien\global\evenfootline={\hfil}
346238494Sobrien\global\oddfootline={\hfil}
346338494Sobrien\global\evenheadline={\line{\thischapter\hfil\folio}}
346438494Sobrien\global\oddheadline={\line{\thischapter\hfil\folio}}
346538494Sobrien\global\let\contentsalignmacro = \chappager
346638494Sobrien}
346738494Sobrien
346838494Sobrien% Subroutines used in generating headings
346982794Sobrien% This produces Day Month Year style of output.
347082794Sobrien% Only define if not already defined, in case a txi-??.tex file has set
347182794Sobrien% up a different format (e.g., txi-cs.tex does this).
3472310490Scy\ifx\today\thisisundefined
347382794Sobrien\def\today{%
347482794Sobrien  \number\day\space
347582794Sobrien  \ifcase\month
347682794Sobrien  \or\putwordMJan\or\putwordMFeb\or\putwordMMar\or\putwordMApr
347782794Sobrien  \or\putwordMMay\or\putwordMJun\or\putwordMJul\or\putwordMAug
347882794Sobrien  \or\putwordMSep\or\putwordMOct\or\putwordMNov\or\putwordMDec
347982794Sobrien  \fi
348082794Sobrien  \space\number\year}
348182794Sobrien\fi
348238494Sobrien
348382794Sobrien% @settitle line...  specifies the title of the document, for headings.
348482794Sobrien% It generates no output of its own.
348582794Sobrien\def\thistitle{\putwordNoTitle}
3486174294Sobrien\def\settitle{\parsearg{\gdef\thistitle}}
348738494Sobrien
348838494Sobrien
348938494Sobrien\message{tables,}
3490174294Sobrien% Tables -- @table, @ftable, @vtable, @item(x).
349138494Sobrien
349238494Sobrien% default indentation of table text
349338494Sobrien\newdimen\tableindent \tableindent=.8in
349438494Sobrien% default indentation of @itemize and @enumerate text
349538494Sobrien\newdimen\itemindent  \itemindent=.3in
349638494Sobrien% margin between end of table item and start of table text.
349738494Sobrien\newdimen\itemmargin  \itemmargin=.1in
349838494Sobrien
349938494Sobrien% used internally for \itemindent minus \itemmargin
350038494Sobrien\newdimen\itemmax
350138494Sobrien
3502174294Sobrien% Note @table, @ftable, and @vtable define @item, @itemx, etc., with
350338494Sobrien% these defs.
350438494Sobrien% They also define \itemindex
350538494Sobrien% to index the item name in whatever manner is desired (perhaps none).
350638494Sobrien
350738494Sobrien\newif\ifitemxneedsnegativevskip
350838494Sobrien
350938494Sobrien\def\itemxpar{\par\ifitemxneedsnegativevskip\nobreak\vskip-\parskip\nobreak\fi}
351038494Sobrien
351138494Sobrien\def\internalBitem{\smallbreak \parsearg\itemzzz}
351238494Sobrien\def\internalBitemx{\itemxpar \parsearg\itemzzz}
351338494Sobrien
351438494Sobrien\def\itemzzz #1{\begingroup %
351538494Sobrien  \advance\hsize by -\rightskip
351638494Sobrien  \advance\hsize by -\tableindent
3517174294Sobrien  \setbox0=\hbox{\itemindicate{#1}}%
351838494Sobrien  \itemindex{#1}%
351938494Sobrien  \nobreak % This prevents a break before @itemx.
352038494Sobrien  %
352138494Sobrien  % If the item text does not fit in the space we have, put it on a line
352238494Sobrien  % by itself, and do not allow a page break either before or after that
352338494Sobrien  % line.  We do not start a paragraph here because then if the next
352438494Sobrien  % command is, e.g., @kindex, the whatsit would get put into the
352538494Sobrien  % horizontal list on a line by itself, resulting in extra blank space.
352638494Sobrien  \ifdim \wd0>\itemmax
352738494Sobrien    %
352838494Sobrien    % Make this a paragraph so we get the \parskip glue and wrapping,
352938494Sobrien    % but leave it ragged-right.
353038494Sobrien    \begingroup
353138494Sobrien      \advance\leftskip by-\tableindent
353238494Sobrien      \advance\hsize by\tableindent
3533310490Scy      \advance\rightskip by0pt plus1fil\relax
353438494Sobrien      \leavevmode\unhbox0\par
353538494Sobrien    \endgroup
353638494Sobrien    %
353738494Sobrien    % We're going to be starting a paragraph, but we don't want the
353838494Sobrien    % \parskip glue -- logically it's part of the @item we just started.
353938494Sobrien    \nobreak \vskip-\parskip
354038494Sobrien    %
3541174294Sobrien    % Stop a page break at the \parskip glue coming up.  However, if
3542174294Sobrien    % what follows is an environment such as @example, there will be no
3543174294Sobrien    % \parskip glue; then the negative vskip we just inserted would
3544174294Sobrien    % cause the example and the item to crash together.  So we use this
3545174294Sobrien    % bizarre value of 10001 as a signal to \aboveenvbreak to insert
3546174294Sobrien    % \parskip glue after all.  Section titles are handled this way also.
3547310490Scy    %
3548174294Sobrien    \penalty 10001
354938494Sobrien    \endgroup
355038494Sobrien    \itemxneedsnegativevskipfalse
355138494Sobrien  \else
355238494Sobrien    % The item text fits into the space.  Start a paragraph, so that the
355382794Sobrien    % following text (if any) will end up on the same line.
355438494Sobrien    \noindent
355542629Sobrien    % Do this with kerns and \unhbox so that if there is a footnote in
355642629Sobrien    % the item text, it can migrate to the main vertical list and
355742629Sobrien    % eventually be printed.
355842629Sobrien    \nobreak\kern-\tableindent
355942629Sobrien    \dimen0 = \itemmax  \advance\dimen0 by \itemmargin \advance\dimen0 by -\wd0
356042629Sobrien    \unhbox0
356142629Sobrien    \nobreak\kern\dimen0
356242629Sobrien    \endgroup
356342629Sobrien    \itemxneedsnegativevskiptrue
356438494Sobrien  \fi
356538494Sobrien}
356638494Sobrien
3567174294Sobrien\def\item{\errmessage{@item while not in a list environment}}
3568174294Sobrien\def\itemx{\errmessage{@itemx while not in a list environment}}
356938494Sobrien
357042629Sobrien% @table, @ftable, @vtable.
3571174294Sobrien\envdef\table{%
3572174294Sobrien  \let\itemindex\gobble
3573310490Scy  \tablecheck{table}%
357438494Sobrien}
3575174294Sobrien\envdef\ftable{%
3576174294Sobrien  \def\itemindex ##1{\doind {fn}{\code{##1}}}%
3577310490Scy  \tablecheck{ftable}%
3578174294Sobrien}
3579174294Sobrien\envdef\vtable{%
3580174294Sobrien  \def\itemindex ##1{\doind {vr}{\code{##1}}}%
3581310490Scy  \tablecheck{vtable}%
3582174294Sobrien}
3583310490Scy\def\tablecheck#1{%
3584310490Scy  \ifnum \the\catcode`\^^M=\active
3585310490Scy    \endgroup
3586310490Scy    \errmessage{This command won't work in this context; perhaps the problem is
3587310490Scy      that we are \inenvironment\thisenv}%
3588310490Scy    \def\next{\doignore{#1}}%
3589310490Scy  \else
3590310490Scy    \let\next\tablex
3591310490Scy  \fi
3592310490Scy  \next
3593310490Scy}
3594174294Sobrien\def\tablex#1{%
3595174294Sobrien  \def\itemindicate{#1}%
3596174294Sobrien  \parsearg\tabley
3597174294Sobrien}
3598174294Sobrien\def\tabley#1{%
3599174294Sobrien  {%
3600174294Sobrien    \makevalueexpandable
3601174294Sobrien    \edef\temp{\noexpand\tablez #1\space\space\space}%
3602174294Sobrien    \expandafter
3603174294Sobrien  }\temp \endtablez
3604174294Sobrien}
3605174294Sobrien\def\tablez #1 #2 #3 #4\endtablez{%
3606174294Sobrien  \aboveenvbreak
3607174294Sobrien  \ifnum 0#1>0 \advance \leftskip by #1\mil \fi
3608174294Sobrien  \ifnum 0#2>0 \tableindent=#2\mil \fi
3609174294Sobrien  \ifnum 0#3>0 \advance \rightskip by #3\mil \fi
3610174294Sobrien  \itemmax=\tableindent
3611174294Sobrien  \advance \itemmax by -\itemmargin
3612174294Sobrien  \advance \leftskip by \tableindent
3613174294Sobrien  \exdentamount=\tableindent
3614174294Sobrien  \parindent = 0pt
3615174294Sobrien  \parskip = \smallskipamount
3616174294Sobrien  \ifdim \parskip=0pt \parskip=2pt \fi
3617174294Sobrien  \let\item = \internalBitem
3618174294Sobrien  \let\itemx = \internalBitemx
3619174294Sobrien}
3620174294Sobrien\def\Etable{\endgraf\afterenvbreak}
3621174294Sobrien\let\Eftable\Etable
3622174294Sobrien\let\Evtable\Etable
3623174294Sobrien\let\Eitemize\Etable
3624174294Sobrien\let\Eenumerate\Etable
362538494Sobrien
362638494Sobrien% This is the counter used by @enumerate, which is really @itemize
362738494Sobrien
362838494Sobrien\newcount \itemno
362938494Sobrien
3630174294Sobrien\envdef\itemize{\parsearg\doitemize}
363138494Sobrien
3632174294Sobrien\def\doitemize#1{%
3633174294Sobrien  \aboveenvbreak
3634174294Sobrien  \itemmax=\itemindent
3635174294Sobrien  \advance\itemmax by -\itemmargin
3636174294Sobrien  \advance\leftskip by \itemindent
3637174294Sobrien  \exdentamount=\itemindent
3638174294Sobrien  \parindent=0pt
3639174294Sobrien  \parskip=\smallskipamount
3640174294Sobrien  \ifdim\parskip=0pt \parskip=2pt \fi
3641310490Scy  %
3642310490Scy  % Try typesetting the item mark that if the document erroneously says
3643310490Scy  % something like @itemize @samp (intending @table), there's an error
3644310490Scy  % right away at the @itemize.  It's not the best error message in the
3645310490Scy  % world, but it's better than leaving it to the @item.  This means if
3646310490Scy  % the user wants an empty mark, they have to say @w{} not just @w.
3647174294Sobrien  \def\itemcontents{#1}%
3648310490Scy  \setbox0 = \hbox{\itemcontents}%
3649310490Scy  %
3650174294Sobrien  % @itemize with no arg is equivalent to @itemize @bullet.
3651174294Sobrien  \ifx\itemcontents\empty\def\itemcontents{\bullet}\fi
3652310490Scy  %
3653174294Sobrien  \let\item=\itemizeitem
365438494Sobrien}
365538494Sobrien
3656174294Sobrien% Definition of @item while inside @itemize and @enumerate.
3657174294Sobrien%
3658174294Sobrien\def\itemizeitem{%
3659174294Sobrien  \advance\itemno by 1  % for enumerations
3660174294Sobrien  {\let\par=\endgraf \smallbreak}% reasonable place to break
3661174294Sobrien  {%
3662174294Sobrien   % If the document has an @itemize directly after a section title, a
3663174294Sobrien   % \nobreak will be last on the list, and \sectionheading will have
3664174294Sobrien   % done a \vskip-\parskip.  In that case, we don't want to zero
3665174294Sobrien   % parskip, or the item text will crash with the heading.  On the
3666174294Sobrien   % other hand, when there is normal text preceding the item (as there
3667174294Sobrien   % usually is), we do want to zero parskip, or there would be too much
3668174294Sobrien   % space.  In that case, we won't have a \nobreak before.  At least
3669174294Sobrien   % that's the theory.
3670174294Sobrien   \ifnum\lastpenalty<10000 \parskip=0in \fi
3671174294Sobrien   \noindent
3672174294Sobrien   \hbox to 0pt{\hss \itemcontents \kern\itemmargin}%
3673310490Scy   %
3674174294Sobrien   \vadjust{\penalty 1200}}% not good to break after first line of item.
3675174294Sobrien  \flushcr
3676174294Sobrien}
367738494Sobrien
367838494Sobrien% \splitoff TOKENS\endmark defines \first to be the first token in
367938494Sobrien% TOKENS, and \rest to be the remainder.
368038494Sobrien%
368138494Sobrien\def\splitoff#1#2\endmark{\def\first{#1}\def\rest{#2}}%
368238494Sobrien
368338494Sobrien% Allow an optional argument of an uppercase letter, lowercase letter,
368438494Sobrien% or number, to specify the first label in the enumerated list.  No
368538494Sobrien% argument is the same as `1'.
368638494Sobrien%
3687174294Sobrien\envparseargdef\enumerate{\enumeratey #1  \endenumeratey}
368838494Sobrien\def\enumeratey #1 #2\endenumeratey{%
368938494Sobrien  % If we were given no argument, pretend we were given `1'.
369038494Sobrien  \def\thearg{#1}%
369138494Sobrien  \ifx\thearg\empty \def\thearg{1}\fi
369238494Sobrien  %
369338494Sobrien  % Detect if the argument is a single token.  If so, it might be a
369438494Sobrien  % letter.  Otherwise, the only valid thing it can be is a number.
369538494Sobrien  % (We will always have one token, because of the test we just made.
369638494Sobrien  % This is a good thing, since \splitoff doesn't work given nothing at
369738494Sobrien  % all -- the first parameter is undelimited.)
369838494Sobrien  \expandafter\splitoff\thearg\endmark
369938494Sobrien  \ifx\rest\empty
370038494Sobrien    % Only one token in the argument.  It could still be anything.
370138494Sobrien    % A ``lowercase letter'' is one whose \lccode is nonzero.
370238494Sobrien    % An ``uppercase letter'' is one whose \lccode is both nonzero, and
370338494Sobrien    %   not equal to itself.
370438494Sobrien    % Otherwise, we assume it's a number.
370538494Sobrien    %
370638494Sobrien    % We need the \relax at the end of the \ifnum lines to stop TeX from
370738494Sobrien    % continuing to look for a <number>.
370838494Sobrien    %
370938494Sobrien    \ifnum\lccode\expandafter`\thearg=0\relax
371038494Sobrien      \numericenumerate % a number (we hope)
371138494Sobrien    \else
371238494Sobrien      % It's a letter.
371338494Sobrien      \ifnum\lccode\expandafter`\thearg=\expandafter`\thearg\relax
371438494Sobrien        \lowercaseenumerate % lowercase letter
371538494Sobrien      \else
371638494Sobrien        \uppercaseenumerate % uppercase letter
371738494Sobrien      \fi
371838494Sobrien    \fi
371938494Sobrien  \else
372038494Sobrien    % Multiple tokens in the argument.  We hope it's a number.
372138494Sobrien    \numericenumerate
372238494Sobrien  \fi
372338494Sobrien}
372438494Sobrien
372538494Sobrien% An @enumerate whose labels are integers.  The starting integer is
372638494Sobrien% given in \thearg.
372738494Sobrien%
372838494Sobrien\def\numericenumerate{%
372938494Sobrien  \itemno = \thearg
373038494Sobrien  \startenumeration{\the\itemno}%
373138494Sobrien}
373238494Sobrien
373338494Sobrien% The starting (lowercase) letter is in \thearg.
373438494Sobrien\def\lowercaseenumerate{%
373538494Sobrien  \itemno = \expandafter`\thearg
373638494Sobrien  \startenumeration{%
373738494Sobrien    % Be sure we're not beyond the end of the alphabet.
373838494Sobrien    \ifnum\itemno=0
373938494Sobrien      \errmessage{No more lowercase letters in @enumerate; get a bigger
374038494Sobrien                  alphabet}%
374138494Sobrien    \fi
374238494Sobrien    \char\lccode\itemno
374338494Sobrien  }%
374438494Sobrien}
374538494Sobrien
374638494Sobrien% The starting (uppercase) letter is in \thearg.
374738494Sobrien\def\uppercaseenumerate{%
374838494Sobrien  \itemno = \expandafter`\thearg
374938494Sobrien  \startenumeration{%
375038494Sobrien    % Be sure we're not beyond the end of the alphabet.
375138494Sobrien    \ifnum\itemno=0
375238494Sobrien      \errmessage{No more uppercase letters in @enumerate; get a bigger
375338494Sobrien                  alphabet}
375438494Sobrien    \fi
375538494Sobrien    \char\uccode\itemno
375638494Sobrien  }%
375738494Sobrien}
375838494Sobrien
3759174294Sobrien% Call \doitemize, adding a period to the first argument and supplying the
376038494Sobrien% common last two arguments.  Also subtract one from the initial value in
376138494Sobrien% \itemno, since @item increments \itemno.
376238494Sobrien%
376338494Sobrien\def\startenumeration#1{%
376438494Sobrien  \advance\itemno by -1
3765174294Sobrien  \doitemize{#1.}\flushcr
376638494Sobrien}
376738494Sobrien
376838494Sobrien% @alphaenumerate and @capsenumerate are abbreviations for giving an arg
376938494Sobrien% to @enumerate.
377038494Sobrien%
377138494Sobrien\def\alphaenumerate{\enumerate{a}}
377238494Sobrien\def\capsenumerate{\enumerate{A}}
377338494Sobrien\def\Ealphaenumerate{\Eenumerate}
377438494Sobrien\def\Ecapsenumerate{\Eenumerate}
377538494Sobrien
377638494Sobrien
377738494Sobrien% @multitable macros
377838494Sobrien% Amy Hendrickson, 8/18/94, 3/6/96
377938494Sobrien%
378038494Sobrien% @multitable ... @end multitable will make as many columns as desired.
378138494Sobrien% Contents of each column will wrap at width given in preamble.  Width
378238494Sobrien% can be specified either with sample text given in a template line,
378338494Sobrien% or in percent of \hsize, the current width of text on page.
378438494Sobrien
378538494Sobrien% Table can continue over pages but will only break between lines.
378638494Sobrien
378738494Sobrien% To make preamble:
378838494Sobrien%
378938494Sobrien% Either define widths of columns in terms of percent of \hsize:
379038494Sobrien%   @multitable @columnfractions .25 .3 .45
379138494Sobrien%   @item ...
379238494Sobrien%
379338494Sobrien%   Numbers following @columnfractions are the percent of the total
379438494Sobrien%   current hsize to be used for each column. You may use as many
379538494Sobrien%   columns as desired.
379638494Sobrien
379738494Sobrien
379838494Sobrien% Or use a template:
379938494Sobrien%   @multitable {Column 1 template} {Column 2 template} {Column 3 template}
380038494Sobrien%   @item ...
380138494Sobrien%   using the widest term desired in each column.
380238494Sobrien
380338494Sobrien% Each new table line starts with @item, each subsequent new column
380438494Sobrien% starts with @tab. Empty columns may be produced by supplying @tab's
380538494Sobrien% with nothing between them for as many times as empty columns are needed,
380638494Sobrien% ie, @tab@tab@tab will produce two empty columns.
380738494Sobrien
3808174294Sobrien% @item, @tab do not need to be on their own lines, but it will not hurt
3809174294Sobrien% if they are.
381038494Sobrien
381138494Sobrien% Sample multitable:
381238494Sobrien
381338494Sobrien%   @multitable {Column 1 template} {Column 2 template} {Column 3 template}
381438494Sobrien%   @item first col stuff @tab second col stuff @tab third col
381538494Sobrien%   @item
381638494Sobrien%   first col stuff
381738494Sobrien%   @tab
381838494Sobrien%   second col stuff
381938494Sobrien%   @tab
382038494Sobrien%   third col
382138494Sobrien%   @item first col stuff @tab second col stuff
382238494Sobrien%   @tab Many paragraphs of text may be used in any column.
382338494Sobrien%
382438494Sobrien%         They will wrap at the width determined by the template.
382538494Sobrien%   @item@tab@tab This will be in third column.
382638494Sobrien%   @end multitable
382738494Sobrien
382838494Sobrien% Default dimensions may be reset by user.
382938494Sobrien% @multitableparskip is vertical space between paragraphs in table.
383038494Sobrien% @multitableparindent is paragraph indent in table.
383138494Sobrien% @multitablecolmargin is horizontal space to be left between columns.
383238494Sobrien% @multitablelinespace is space to leave between table items, baseline
383338494Sobrien%                                                            to baseline.
383438494Sobrien%   0pt means it depends on current normal line spacing.
383542629Sobrien%
383638494Sobrien\newskip\multitableparskip
383738494Sobrien\newskip\multitableparindent
383838494Sobrien\newdimen\multitablecolspace
383938494Sobrien\newskip\multitablelinespace
384038494Sobrien\multitableparskip=0pt
384138494Sobrien\multitableparindent=6pt
384238494Sobrien\multitablecolspace=12pt
384338494Sobrien\multitablelinespace=0pt
384438494Sobrien
384538494Sobrien% Macros used to set up halign preamble:
384682794Sobrien%
384738494Sobrien\let\endsetuptable\relax
384838494Sobrien\def\xendsetuptable{\endsetuptable}
384938494Sobrien\let\columnfractions\relax
385038494Sobrien\def\xcolumnfractions{\columnfractions}
385138494Sobrien\newif\ifsetpercent
385238494Sobrien
3853174294Sobrien% #1 is the @columnfraction, usually a decimal number like .5, but might
3854174294Sobrien% be just 1.  We just use it, whatever it is.
3855174294Sobrien%
3856174294Sobrien\def\pickupwholefraction#1 {%
385782794Sobrien  \global\advance\colcount by 1
3858174294Sobrien  \expandafter\xdef\csname col\the\colcount\endcsname{#1\hsize}%
385982794Sobrien  \setuptable
386082794Sobrien}
386138494Sobrien
386238494Sobrien\newcount\colcount
386382794Sobrien\def\setuptable#1{%
386482794Sobrien  \def\firstarg{#1}%
386582794Sobrien  \ifx\firstarg\xendsetuptable
386682794Sobrien    \let\go = \relax
386738494Sobrien  \else
386882794Sobrien    \ifx\firstarg\xcolumnfractions
386982794Sobrien      \global\setpercenttrue
387038494Sobrien    \else
387182794Sobrien      \ifsetpercent
387282794Sobrien         \let\go\pickupwholefraction
387382794Sobrien      \else
387482794Sobrien         \global\advance\colcount by 1
3875174294Sobrien         \setbox0=\hbox{#1\unskip\space}% Add a normal word space as a
3876174294Sobrien                   % separator; typically that is always in the input, anyway.
387782794Sobrien         \expandafter\xdef\csname col\the\colcount\endcsname{\the\wd0}%
387882794Sobrien      \fi
387982794Sobrien    \fi
388082794Sobrien    \ifx\go\pickupwholefraction
388182794Sobrien      % Put the argument back for the \pickupwholefraction call, so
388282794Sobrien      % we'll always have a period there to be parsed.
388382794Sobrien      \def\go{\pickupwholefraction#1}%
388482794Sobrien    \else
388582794Sobrien      \let\go = \setuptable
388638494Sobrien    \fi%
388782794Sobrien  \fi
388882794Sobrien  \go
388982794Sobrien}
389038494Sobrien
3891174294Sobrien% multitable-only commands.
3892174294Sobrien%
3893174294Sobrien% @headitem starts a heading row, which we typeset in bold.
3894174294Sobrien% Assignments have to be global since we are inside the implicit group
3895310490Scy% of an alignment entry.  \everycr resets \everytab so we don't have to
3896310490Scy% undo it ourselves.
3897310490Scy\def\headitemfont{\b}% for people to use in the template row; not changeable
3898310490Scy\def\headitem{%
3899310490Scy  \checkenv\multitable
3900310490Scy  \crcr
3901310490Scy  \global\everytab={\bf}% can't use \headitemfont since the parsing differs
3902310490Scy  \the\everytab % for the first item
3903310490Scy}%
3904174294Sobrien%
3905174294Sobrien% A \tab used to include \hskip1sp.  But then the space in a template
3906174294Sobrien% line is not enough.  That is bad.  So let's go back to just `&' until
3907310490Scy% we again encounter the problem the 1sp was intended to solve.
3908174294Sobrien%					--karl, nathan@acm.org, 20apr99.
3909174294Sobrien\def\tab{\checkenv\multitable &\the\everytab}%
391038494Sobrien
391138494Sobrien% @multitable ... @end multitable definitions:
391282794Sobrien%
3913174294Sobrien\newtoks\everytab  % insert after every tab.
3914174294Sobrien%
3915174294Sobrien\envdef\multitable{%
391642629Sobrien  \vskip\parskip
3917174294Sobrien  \startsavinginserts
3918174294Sobrien  %
3919174294Sobrien  % @item within a multitable starts a normal row.
3920174294Sobrien  % We use \def instead of \let so that if one of the multitable entries
3921174294Sobrien  % contains an @itemize, we don't choke on the \item (seen as \crcr aka
3922174294Sobrien  % \endtemplate) expanding \doitemize.
3923174294Sobrien  \def\item{\crcr}%
3924174294Sobrien  %
392542629Sobrien  \tolerance=9500
392642629Sobrien  \hbadness=9500
392742629Sobrien  \setmultitablespacing
392842629Sobrien  \parskip=\multitableparskip
392942629Sobrien  \parindent=\multitableparindent
393042629Sobrien  \overfullrule=0pt
393142629Sobrien  \global\colcount=0
393242629Sobrien  %
3933174294Sobrien  \everycr = {%
3934174294Sobrien    \noalign{%
3935174294Sobrien      \global\everytab={}%
3936174294Sobrien      \global\colcount=0 % Reset the column counter.
3937174294Sobrien      % Check for saved footnotes, etc.
3938174294Sobrien      \checkinserts
3939174294Sobrien      % Keeps underfull box messages off when table breaks over pages.
3940174294Sobrien      %\filbreak
3941174294Sobrien	% Maybe so, but it also creates really weird page breaks when the
3942174294Sobrien	% table breaks over pages. Wouldn't \vfil be better?  Wait until the
3943174294Sobrien	% problem manifests itself, so it can be fixed for real --karl.
3944174294Sobrien    }%
3945174294Sobrien  }%
3946174294Sobrien  %
3947174294Sobrien  \parsearg\domultitable
3948174294Sobrien}
3949174294Sobrien\def\domultitable#1{%
395042629Sobrien  % To parse everything between @multitable and @item:
395142629Sobrien  \setuptable#1 \endsetuptable
395242629Sobrien  %
395342629Sobrien  % This preamble sets up a generic column definition, which will
395442629Sobrien  % be used as many times as user calls for columns.
395542629Sobrien  % \vtop will set a single line and will also let text wrap and
395642629Sobrien  % continue for many paragraphs if desired.
3957174294Sobrien  \halign\bgroup &%
3958174294Sobrien    \global\advance\colcount by 1
3959174294Sobrien    \multistrut
3960174294Sobrien    \vtop{%
3961174294Sobrien      % Use the current \colcount to find the correct column width:
3962174294Sobrien      \hsize=\expandafter\csname col\the\colcount\endcsname
3963174294Sobrien      %
3964174294Sobrien      % In order to keep entries from bumping into each other
3965174294Sobrien      % we will add a \leftskip of \multitablecolspace to all columns after
3966174294Sobrien      % the first one.
3967174294Sobrien      %
3968174294Sobrien      % If a template has been used, we will add \multitablecolspace
3969174294Sobrien      % to the width of each template entry.
3970174294Sobrien      %
3971174294Sobrien      % If the user has set preamble in terms of percent of \hsize we will
3972174294Sobrien      % use that dimension as the width of the column, and the \leftskip
3973174294Sobrien      % will keep entries from bumping into each other.  Table will start at
3974174294Sobrien      % left margin and final column will justify at right margin.
3975174294Sobrien      %
3976174294Sobrien      % Make sure we don't inherit \rightskip from the outer environment.
3977174294Sobrien      \rightskip=0pt
3978174294Sobrien      \ifnum\colcount=1
3979174294Sobrien	% The first column will be indented with the surrounding text.
3980174294Sobrien	\advance\hsize by\leftskip
3981174294Sobrien      \else
3982174294Sobrien	\ifsetpercent \else
3983174294Sobrien	  % If user has not set preamble in terms of percent of \hsize
3984174294Sobrien	  % we will advance \hsize by \multitablecolspace.
3985174294Sobrien	  \advance\hsize by \multitablecolspace
3986174294Sobrien	\fi
3987174294Sobrien       % In either case we will make \leftskip=\multitablecolspace:
3988174294Sobrien      \leftskip=\multitablecolspace
3989174294Sobrien      \fi
3990174294Sobrien      % Ignoring space at the beginning and end avoids an occasional spurious
3991174294Sobrien      % blank line, when TeX decides to break the line at the space before the
3992174294Sobrien      % box from the multistrut, so the strut ends up on a line by itself.
3993174294Sobrien      % For example:
3994174294Sobrien      % @multitable @columnfractions .11 .89
3995174294Sobrien      % @item @code{#}
3996174294Sobrien      % @tab Legal holiday which is valid in major parts of the whole country.
3997174294Sobrien      % Is automatically provided with highlighting sequences respectively
3998174294Sobrien      % marking characters.
3999174294Sobrien      \noindent\ignorespaces##\unskip\multistrut
4000174294Sobrien    }\cr
400138494Sobrien}
4002174294Sobrien\def\Emultitable{%
4003174294Sobrien  \crcr
4004174294Sobrien  \egroup % end the \halign
4005174294Sobrien  \global\setpercentfalse
4006174294Sobrien}
400738494Sobrien
4008310490Scy\def\setmultitablespacing{%
4009310490Scy  \def\multistrut{\strut}% just use the standard line spacing
4010310490Scy  %
4011310490Scy  % Compute \multitablelinespace (if not defined by user) for use in
4012310490Scy  % \multitableparskip calculation.  We used define \multistrut based on
4013310490Scy  % this, but (ironically) that caused the spacing to be off.
4014310490Scy  % See bug-texinfo report from Werner Lemberg, 31 Oct 2004 12:52:20 +0100.
401538494Sobrien\ifdim\multitablelinespace=0pt
401682794Sobrien\setbox0=\vbox{X}\global\multitablelinespace=\the\baselineskip
401782794Sobrien\global\advance\multitablelinespace by-\ht0
4018310490Scy\fi
4019310490Scy% Test to see if parskip is larger than space between lines of
4020310490Scy% table. If not, do nothing.
4021310490Scy%        If so, set to same dimension as multitablelinespace.
402238494Sobrien\ifdim\multitableparskip>\multitablelinespace
402338494Sobrien\global\multitableparskip=\multitablelinespace
4024310490Scy\global\advance\multitableparskip-7pt % to keep parskip somewhat smaller
4025310490Scy                                      % than skip between lines in the table.
402638494Sobrien\fi%
402738494Sobrien\ifdim\multitableparskip=0pt
402838494Sobrien\global\multitableparskip=\multitablelinespace
4029310490Scy\global\advance\multitableparskip-7pt % to keep parskip somewhat smaller
4030310490Scy                                      % than skip between lines in the table.
403138494Sobrien\fi}
403238494Sobrien
403338494Sobrien
403482794Sobrien\message{conditionals,}
403582794Sobrien
4036174294Sobrien% @iftex, @ifnotdocbook, @ifnothtml, @ifnotinfo, @ifnotplaintext,
4037174294Sobrien% @ifnotxml always succeed.  They currently do nothing; we don't
4038174294Sobrien% attempt to check whether the conditionals are properly nested.  But we
4039174294Sobrien% have to remember that they are conditionals, so that @end doesn't
4040174294Sobrien% attempt to close an environment group.
404182794Sobrien%
4042174294Sobrien\def\makecond#1{%
4043174294Sobrien  \expandafter\let\csname #1\endcsname = \relax
4044174294Sobrien  \expandafter\let\csname iscond.#1\endcsname = 1
404582794Sobrien}
4046174294Sobrien\makecond{iftex}
4047174294Sobrien\makecond{ifnotdocbook}
4048174294Sobrien\makecond{ifnothtml}
4049174294Sobrien\makecond{ifnotinfo}
4050174294Sobrien\makecond{ifnotplaintext}
4051174294Sobrien\makecond{ifnotxml}
405282794Sobrien
4053174294Sobrien% Ignore @ignore, @ifhtml, @ifinfo, and the like.
405482794Sobrien%
4055174294Sobrien\def\direntry{\doignore{direntry}}
4056174294Sobrien\def\documentdescription{\doignore{documentdescription}}
4057174294Sobrien\def\docbook{\doignore{docbook}}
4058174294Sobrien\def\html{\doignore{html}}
4059174294Sobrien\def\ifdocbook{\doignore{ifdocbook}}
4060119679Smbr\def\ifhtml{\doignore{ifhtml}}
406182794Sobrien\def\ifinfo{\doignore{ifinfo}}
4062174294Sobrien\def\ifnottex{\doignore{ifnottex}}
4063119679Smbr\def\ifplaintext{\doignore{ifplaintext}}
4064174294Sobrien\def\ifxml{\doignore{ifxml}}
4065174294Sobrien\def\ignore{\doignore{ignore}}
406682794Sobrien\def\menu{\doignore{menu}}
4067174294Sobrien\def\xml{\doignore{xml}}
406882794Sobrien
4069174294Sobrien% Ignore text until a line `@end #1', keeping track of nested conditionals.
4070174294Sobrien%
4071174294Sobrien% A count to remember the depth of nesting.
4072174294Sobrien\newcount\doignorecount
407382794Sobrien
407482794Sobrien\def\doignore#1{\begingroup
4075174294Sobrien  % Scan in ``verbatim'' mode:
4076310490Scy  \obeylines
4077174294Sobrien  \catcode`\@ = \other
4078174294Sobrien  \catcode`\{ = \other
4079174294Sobrien  \catcode`\} = \other
408082794Sobrien  %
408182794Sobrien  % Make sure that spaces turn into tokens that match what \doignoretext wants.
4082174294Sobrien  \spaceisspace
408382794Sobrien  %
4084174294Sobrien  % Count number of #1's that we've seen.
4085174294Sobrien  \doignorecount = 0
408682794Sobrien  %
4087174294Sobrien  % Swallow text until we reach the matching `@end #1'.
4088174294Sobrien  \dodoignore{#1}%
4089174294Sobrien}
4090174294Sobrien
4091174294Sobrien{ \catcode`_=11 % We want to use \_STOP_ which cannot appear in texinfo source.
4092174294Sobrien  \obeylines %
409382794Sobrien  %
4094174294Sobrien  \gdef\dodoignore#1{%
4095174294Sobrien    % #1 contains the command name as a string, e.g., `ifinfo'.
4096174294Sobrien    %
4097310490Scy    % Define a command to find the next `@end #1'.
4098310490Scy    \long\def\doignoretext##1^^M@end #1{%
4099310490Scy      \doignoretextyyy##1^^M@#1\_STOP_}%
4100310490Scy    %
4101174294Sobrien    % And this command to find another #1 command, at the beginning of a
4102174294Sobrien    % line.  (Otherwise, we would consider a line `@c @ifset', for
4103174294Sobrien    % example, to count as an @ifset for nesting.)
4104174294Sobrien    \long\def\doignoretextyyy##1^^M@#1##2\_STOP_{\doignoreyyy{##2}\_STOP_}%
4105174294Sobrien    %
4106174294Sobrien    % And now expand that command.
4107174294Sobrien    \doignoretext ^^M%
4108174294Sobrien  }%
4109174294Sobrien}
4110174294Sobrien
4111174294Sobrien\def\doignoreyyy#1{%
4112174294Sobrien  \def\temp{#1}%
4113174294Sobrien  \ifx\temp\empty			% Nothing found.
4114174294Sobrien    \let\next\doignoretextzzz
4115174294Sobrien  \else					% Found a nested condition, ...
4116174294Sobrien    \advance\doignorecount by 1
4117174294Sobrien    \let\next\doignoretextyyy		% ..., look for another.
4118174294Sobrien    % If we're here, #1 ends with ^^M\ifinfo (for example).
4119119679Smbr  \fi
4120174294Sobrien  \next #1% the token \_STOP_ is present just after this macro.
412182794Sobrien}
412282794Sobrien
4123174294Sobrien% We have to swallow the remaining "\_STOP_".
412482794Sobrien%
4125174294Sobrien\def\doignoretextzzz#1{%
4126174294Sobrien  \ifnum\doignorecount = 0	% We have just found the outermost @end.
4127174294Sobrien    \let\next\enddoignore
4128174294Sobrien  \else				% Still inside a nested condition.
4129174294Sobrien    \advance\doignorecount by -1
4130174294Sobrien    \let\next\doignoretext      % Look for the next @end.
4131174294Sobrien  \fi
4132174294Sobrien  \next
413382794Sobrien}
413482794Sobrien
4135174294Sobrien% Finish off ignored text.
4136310490Scy{ \obeylines%
4137310490Scy  % Ignore anything after the last `@end #1'; this matters in verbatim
4138310490Scy  % environments, where otherwise the newline after an ignored conditional
4139310490Scy  % would result in a blank line in the output.
4140310490Scy  \gdef\enddoignore#1^^M{\endgroup\ignorespaces}%
4141310490Scy}
414282794Sobrien
414382794Sobrien
414482794Sobrien% @set VAR sets the variable VAR to an empty value.
414582794Sobrien% @set VAR REST-OF-LINE sets VAR to the value REST-OF-LINE.
414682794Sobrien%
414782794Sobrien% Since we want to separate VAR from REST-OF-LINE (which might be
414882794Sobrien% empty), we can't just use \parsearg; we have to insert a space of our
414982794Sobrien% own to delimit the rest of the line, and then take it out again if we
4150174294Sobrien% didn't need it.
4151174294Sobrien% We rely on the fact that \parsearg sets \catcode`\ =10.
415282794Sobrien%
4153174294Sobrien\parseargdef\set{\setyyy#1 \endsetyyy}
415482794Sobrien\def\setyyy#1 #2\endsetyyy{%
4155174294Sobrien  {%
4156174294Sobrien    \makevalueexpandable
4157174294Sobrien    \def\temp{#2}%
4158174294Sobrien    \edef\next{\gdef\makecsname{SET#1}}%
4159174294Sobrien    \ifx\temp\empty
4160174294Sobrien      \next{}%
4161174294Sobrien    \else
4162174294Sobrien      \setzzz#2\endsetzzz
4163174294Sobrien    \fi
4164174294Sobrien  }%
416582794Sobrien}
4166174294Sobrien% Remove the trailing space \setxxx inserted.
4167174294Sobrien\def\setzzz#1 \endsetzzz{\next{#1}}
416882794Sobrien
416982794Sobrien% @clear VAR clears (i.e., unsets) the variable VAR.
417082794Sobrien%
4171174294Sobrien\parseargdef\clear{%
4172174294Sobrien  {%
4173174294Sobrien    \makevalueexpandable
4174174294Sobrien    \global\expandafter\let\csname SET#1\endcsname=\relax
4175174294Sobrien  }%
4176174294Sobrien}
417782794Sobrien
417882794Sobrien% @value{foo} gets the text saved in variable foo.
4179174294Sobrien\def\value{\begingroup\makevalueexpandable\valuexxx}
4180174294Sobrien\def\valuexxx#1{\expandablevalue{#1}\endgroup}
418182794Sobrien{
4182174294Sobrien  \catcode`\- = \active \catcode`\_ = \active
418382794Sobrien  %
4184174294Sobrien  \gdef\makevalueexpandable{%
4185174294Sobrien    \let\value = \expandablevalue
4186174294Sobrien    % We don't want these characters active, ...
4187174294Sobrien    \catcode`\-=\other \catcode`\_=\other
4188174294Sobrien    % ..., but we might end up with active ones in the argument if
4189174294Sobrien    % we're called from @code, as @code{@value{foo-bar_}}, though.
4190174294Sobrien    % So \let them to their normal equivalents.
4191310490Scy    \let-\normaldash \let_\normalunderscore
4192174294Sobrien  }
419382794Sobrien}
419482794Sobrien
419582794Sobrien% We have this subroutine so that we can handle at least some @value's
4196174294Sobrien% properly in indexes (we call \makevalueexpandable in \indexdummies).
4197174294Sobrien% The command has to be fully expandable (if the variable is set), since
4198174294Sobrien% the result winds up in the index file.  This means that if the
4199174294Sobrien% variable's value contains other Texinfo commands, it's almost certain
4200174294Sobrien% it will fail (although perhaps we could fix that with sufficient work
4201174294Sobrien% to do a one-level expansion on the result, instead of complete).
420282794Sobrien%
420382794Sobrien\def\expandablevalue#1{%
420482794Sobrien  \expandafter\ifx\csname SET#1\endcsname\relax
420582794Sobrien    {[No value for ``#1'']}%
4206174294Sobrien    \message{Variable `#1', used in @value, is not set.}%
420782794Sobrien  \else
420882794Sobrien    \csname SET#1\endcsname
420982794Sobrien  \fi
421082794Sobrien}
421182794Sobrien
421282794Sobrien% @ifset VAR ... @end ifset reads the `...' iff VAR has been defined
421382794Sobrien% with @set.
421482794Sobrien%
4215174294Sobrien% To get special treatment of `@end ifset,' call \makeond and the redefine.
4216174294Sobrien%
4217174294Sobrien\makecond{ifset}
4218174294Sobrien\def\ifset{\parsearg{\doifset{\let\next=\ifsetfail}}}
4219174294Sobrien\def\doifset#1#2{%
4220174294Sobrien  {%
4221174294Sobrien    \makevalueexpandable
4222174294Sobrien    \let\next=\empty
4223174294Sobrien    \expandafter\ifx\csname SET#2\endcsname\relax
4224174294Sobrien      #1% If not set, redefine \next.
4225174294Sobrien    \fi
4226174294Sobrien    \expandafter
4227174294Sobrien  }\next
422882794Sobrien}
4229174294Sobrien\def\ifsetfail{\doignore{ifset}}
423082794Sobrien
4231310490Scy% @ifclear VAR ... @end executes the `...' iff VAR has never been
423282794Sobrien% defined with @set, or has been undefined with @clear.
423382794Sobrien%
4234174294Sobrien% The `\else' inside the `\doifset' parameter is a trick to reuse the
4235174294Sobrien% above code: if the variable is not set, do nothing, if it is set,
4236174294Sobrien% then redefine \next to \ifclearfail.
423782794Sobrien%
4238174294Sobrien\makecond{ifclear}
4239174294Sobrien\def\ifclear{\parsearg{\doifset{\else \let\next=\ifclearfail}}}
4240174294Sobrien\def\ifclearfail{\doignore{ifclear}}
424182794Sobrien
4242310490Scy% @ifcommandisdefined CMD ... @end executes the `...' if CMD (written
4243310490Scy% without the @) is in fact defined.  We can only feasibly check at the
4244310490Scy% TeX level, so something like `mathcode' is going to considered
4245310490Scy% defined even though it is not a Texinfo command.
4246310490Scy% 
4247310490Scy\makecond{ifcommanddefined}
4248310490Scy\def\ifcommanddefined{\parsearg{\doifcmddefined{\let\next=\ifcmddefinedfail}}}
4249310490Scy%
4250310490Scy\def\doifcmddefined#1#2{{%
4251310490Scy    \makevalueexpandable
4252310490Scy    \let\next=\empty
4253310490Scy    \expandafter\ifx\csname #2\endcsname\relax
4254310490Scy      #1% If not defined, \let\next as above.
4255310490Scy    \fi
4256310490Scy    \expandafter
4257310490Scy  }\next
4258310490Scy}
4259310490Scy\def\ifcmddefinedfail{\doignore{ifcommanddefined}}
4260310490Scy
4261310490Scy% @ifcommandnotdefined CMD ... handled similar to @ifclear above.
4262310490Scy\makecond{ifcommandnotdefined}
4263310490Scy\def\ifcommandnotdefined{%
4264310490Scy  \parsearg{\doifcmddefined{\else \let\next=\ifcmdnotdefinedfail}}}
4265310490Scy\def\ifcmdnotdefinedfail{\doignore{ifcommandnotdefined}}
4266310490Scy
4267310490Scy% Set the `txicommandconditionals' variable, so documents have a way to
4268310490Scy% test if the @ifcommand...defined conditionals are available.
4269310490Scy\set txicommandconditionals
4270310490Scy
4271174294Sobrien% @dircategory CATEGORY  -- specify a category of the dir file
4272174294Sobrien% which this file should belong to.  Ignore this in TeX.
4273174294Sobrien\let\dircategory=\comment
427482794Sobrien
427582794Sobrien% @defininfoenclose.
427682794Sobrien\let\definfoenclose=\comment
427782794Sobrien
427882794Sobrien
427938494Sobrien\message{indexing,}
428038494Sobrien% Index generation facilities
428138494Sobrien
428238494Sobrien% Define \newwrite to be identical to plain tex's \newwrite
4283310490Scy% except not \outer, so it can be used within macros and \if's.
4284310490Scy\edef\newwrite{\makecsname{ptexnewwrite}}
428538494Sobrien
428638494Sobrien% \newindex {foo} defines an index named foo.
428738494Sobrien% It automatically defines \fooindex such that
428838494Sobrien% \fooindex ...rest of line... puts an entry in the index foo.
428938494Sobrien% It also defines \fooindfile to be the number of the output channel for
429038494Sobrien% the file that accumulates this index.  The file's extension is foo.
429138494Sobrien% The name of an index should be no more than 2 characters long
429238494Sobrien% for the sake of vms.
429342629Sobrien%
429442629Sobrien\def\newindex#1{%
429542629Sobrien  \iflinks
429642629Sobrien    \expandafter\newwrite \csname#1indfile\endcsname
429742629Sobrien    \openout \csname#1indfile\endcsname \jobname.#1 % Open the file
429842629Sobrien  \fi
429942629Sobrien  \expandafter\xdef\csname#1index\endcsname{%     % Define @#1index
430042629Sobrien    \noexpand\doindex{#1}}
430138494Sobrien}
430238494Sobrien
430338494Sobrien% @defindex foo  ==  \newindex{foo}
430482794Sobrien%
430538494Sobrien\def\defindex{\parsearg\newindex}
430638494Sobrien
430738494Sobrien% Define @defcodeindex, like @defindex except put all entries in @code.
430882794Sobrien%
430982794Sobrien\def\defcodeindex{\parsearg\newcodeindex}
431082794Sobrien%
431142629Sobrien\def\newcodeindex#1{%
431242629Sobrien  \iflinks
431342629Sobrien    \expandafter\newwrite \csname#1indfile\endcsname
431442629Sobrien    \openout \csname#1indfile\endcsname \jobname.#1
431542629Sobrien  \fi
431642629Sobrien  \expandafter\xdef\csname#1index\endcsname{%
431782794Sobrien    \noexpand\docodeindex{#1}}%
431838494Sobrien}
431938494Sobrien
432038494Sobrien
432138494Sobrien% @synindex foo bar    makes index foo feed into index bar.
432238494Sobrien% Do this instead of @defindex foo if you don't want it as a separate index.
4323174294Sobrien%
432438494Sobrien% @syncodeindex foo bar   similar, but put all entries made for index foo
432538494Sobrien% inside @code.
4326174294Sobrien%
432782794Sobrien\def\synindex#1 #2 {\dosynindex\doindex{#1}{#2}}
432882794Sobrien\def\syncodeindex#1 #2 {\dosynindex\docodeindex{#1}{#2}}
432982794Sobrien
433082794Sobrien% #1 is \doindex or \docodeindex, #2 the index getting redefined (foo),
433182794Sobrien% #3 the target index (bar).
433282794Sobrien\def\dosynindex#1#2#3{%
433382794Sobrien  % Only do \closeout if we haven't already done it, else we'll end up
433482794Sobrien  % closing the target index.
4335310490Scy  \expandafter \ifx\csname donesynindex#2\endcsname \relax
433682794Sobrien    % The \closeout helps reduce unnecessary open files; the limit on the
433782794Sobrien    % Acorn RISC OS is a mere 16 files.
433882794Sobrien    \expandafter\closeout\csname#2indfile\endcsname
4339310490Scy    \expandafter\let\csname donesynindex#2\endcsname = 1
434082794Sobrien  \fi
434182794Sobrien  % redefine \fooindfile:
434282794Sobrien  \expandafter\let\expandafter\temp\expandafter=\csname#3indfile\endcsname
434382794Sobrien  \expandafter\let\csname#2indfile\endcsname=\temp
434482794Sobrien  % redefine \fooindex:
434582794Sobrien  \expandafter\xdef\csname#2index\endcsname{\noexpand#1{#3}}%
434638494Sobrien}
434738494Sobrien
434838494Sobrien% Define \doindex, the driver for all \fooindex macros.
434938494Sobrien% Argument #1 is generated by the calling \fooindex macro,
435038494Sobrien%  and it is "foo", the name of the index.
435138494Sobrien
435238494Sobrien% \doindex just uses \parsearg; it calls \doind for the actual work.
435338494Sobrien% This is because \doind is more useful to call from other macros.
435438494Sobrien
435538494Sobrien% There is also \dosubind {index}{topic}{subtopic}
435638494Sobrien% which makes an entry in a two-level index such as the operation index.
435738494Sobrien
435838494Sobrien\def\doindex#1{\edef\indexname{#1}\parsearg\singleindexer}
435938494Sobrien\def\singleindexer #1{\doind{\indexname}{#1}}
436038494Sobrien
436138494Sobrien% like the previous two, but they put @code around the argument.
436238494Sobrien\def\docodeindex#1{\edef\indexname{#1}\parsearg\singlecodeindexer}
436338494Sobrien\def\singlecodeindexer #1{\doind{\indexname}{\code{#1}}}
436438494Sobrien
4365174294Sobrien% Take care of Texinfo commands that can appear in an index entry.
4366174294Sobrien% Since there are some commands we want to expand, and others we don't,
4367174294Sobrien% we have to laboriously prevent expansion for those that we don't.
4368174294Sobrien%
436938494Sobrien\def\indexdummies{%
4370310490Scy  \escapechar = `\\     % use backslash in output files.
4371174294Sobrien  \def\@{@}% change to @@ when we switch to @ as escape char in index files.
4372174294Sobrien  \def\ {\realbackslash\space }%
4373174294Sobrien  %
4374310490Scy  % Need these unexpandable (because we define \tt as a dummy)
4375310490Scy  % definitions when @{ or @} appear in index entry text.  Also, more
4376310490Scy  % complicated, when \tex is in effect and \{ is a \delimiter again.
4377310490Scy  % We can't use \lbracecmd and \rbracecmd because texindex assumes
4378310490Scy  % braces and backslashes are used only as delimiters.  Perhaps we
4379310490Scy  % should define @lbrace and @rbrace commands a la @comma.
4380310490Scy  \def\{{{\tt\char123}}%
4381310490Scy  \def\}{{\tt\char125}}%
4382174294Sobrien  %
4383310490Scy  % I don't entirely understand this, but when an index entry is
4384310490Scy  % generated from a macro call, the \endinput which \scanmacro inserts
4385310490Scy  % causes processing to be prematurely terminated.  This is,
4386310490Scy  % apparently, because \indexsorttmp is fully expanded, and \endinput
4387310490Scy  % is an expandable command.  The redefinition below makes \endinput
4388310490Scy  % disappear altogether for that purpose -- although logging shows that
4389310490Scy  % processing continues to some further point.  On the other hand, it
4390310490Scy  % seems \endinput does not hurt in the printed index arg, since that
4391310490Scy  % is still getting written without apparent harm.
4392174294Sobrien  %
4393310490Scy  % Sample source (mac-idx3.tex, reported by Graham Percival to
4394310490Scy  % help-texinfo, 22may06):
4395310490Scy  % @macro funindex {WORD}
4396310490Scy  % @findex xyz
4397310490Scy  % @end macro
4398310490Scy  % ...
4399310490Scy  % @funindex commtest
4400174294Sobrien  %
4401310490Scy  % The above is not enough to reproduce the bug, but it gives the flavor.
4402174294Sobrien  %
4403310490Scy  % Sample whatsit resulting:
4404310490Scy  % .@write3{\entry{xyz}{@folio }{@code {xyz@endinput }}}
4405310490Scy  %
4406310490Scy  % So:
4407310490Scy  \let\endinput = \empty
4408310490Scy  %
4409174294Sobrien  % Do the redefinitions.
4410174294Sobrien  \commondummies
4411174294Sobrien}
4412174294Sobrien
4413310490Scy% For the aux and toc files, @ is the escape character.  So we want to
4414310490Scy% redefine everything using @ as the escape character (instead of
4415310490Scy% \realbackslash, still used for index files).  When everything uses @,
4416310490Scy% this will be simpler.
4417119679Smbr%
4418174294Sobrien\def\atdummies{%
4419174294Sobrien  \def\@{@@}%
4420174294Sobrien  \def\ {@ }%
4421174294Sobrien  \let\{ = \lbraceatcmd
4422174294Sobrien  \let\} = \rbraceatcmd
4423174294Sobrien  %
4424174294Sobrien  % Do the redefinitions.
4425174294Sobrien  \commondummies
4426310490Scy  \otherbackslash
4427174294Sobrien}
4428174294Sobrien
4429310490Scy% Called from \indexdummies and \atdummies.
4430119679Smbr%
4431174294Sobrien\def\commondummies{%
4432174294Sobrien  %
4433310490Scy  % \definedummyword defines \#1 as \string\#1\space, thus effectively
4434310490Scy  % preventing its expansion.  This is used only for control words,
4435310490Scy  % not control letters, because the \space would be incorrect for
4436310490Scy  % control characters, but is needed to separate the control word
4437310490Scy  % from whatever follows.
4438174294Sobrien  %
4439310490Scy  % For control letters, we have \definedummyletter, which omits the
4440310490Scy  % space.
4441310490Scy  %
4442310490Scy  % These can be used both for control words that take an argument and
4443310490Scy  % those that do not.  If it is followed by {arg} in the input, then
4444310490Scy  % that will dutifully get written to the index (or wherever).
4445310490Scy  %
4446310490Scy  \def\definedummyword  ##1{\def##1{\string##1\space}}%
4447310490Scy  \def\definedummyletter##1{\def##1{\string##1}}%
4448310490Scy  \let\definedummyaccent\definedummyletter
4449310490Scy  %
4450174294Sobrien  \commondummiesnofonts
4451174294Sobrien  %
4452310490Scy  \definedummyletter\_%
4453310490Scy  \definedummyletter\-%
4454174294Sobrien  %
4455174294Sobrien  % Non-English letters.
4456310490Scy  \definedummyword\AA
4457310490Scy  \definedummyword\AE
4458310490Scy  \definedummyword\DH
4459310490Scy  \definedummyword\L
4460310490Scy  \definedummyword\O
4461310490Scy  \definedummyword\OE
4462310490Scy  \definedummyword\TH
4463310490Scy  \definedummyword\aa
4464310490Scy  \definedummyword\ae
4465310490Scy  \definedummyword\dh
4466310490Scy  \definedummyword\exclamdown
4467310490Scy  \definedummyword\l
4468310490Scy  \definedummyword\o
4469310490Scy  \definedummyword\oe
4470310490Scy  \definedummyword\ordf
4471310490Scy  \definedummyword\ordm
4472310490Scy  \definedummyword\questiondown
4473310490Scy  \definedummyword\ss
4474310490Scy  \definedummyword\th
4475174294Sobrien  %
4476174294Sobrien  % Although these internal commands shouldn't show up, sometimes they do.
4477310490Scy  \definedummyword\bf
4478310490Scy  \definedummyword\gtr
4479310490Scy  \definedummyword\hat
4480310490Scy  \definedummyword\less
4481310490Scy  \definedummyword\sf
4482310490Scy  \definedummyword\sl
4483310490Scy  \definedummyword\tclose
4484310490Scy  \definedummyword\tt
4485174294Sobrien  %
4486310490Scy  \definedummyword\LaTeX
4487310490Scy  \definedummyword\TeX
4488174294Sobrien  %
4489174294Sobrien  % Assorted special characters.
4490310490Scy  \definedummyword\arrow
4491310490Scy  \definedummyword\bullet
4492310490Scy  \definedummyword\comma
4493310490Scy  \definedummyword\copyright
4494310490Scy  \definedummyword\registeredsymbol
4495310490Scy  \definedummyword\dots
4496310490Scy  \definedummyword\enddots
4497310490Scy  \definedummyword\entrybreak
4498310490Scy  \definedummyword\equiv
4499310490Scy  \definedummyword\error
4500310490Scy  \definedummyword\euro
4501310490Scy  \definedummyword\expansion
4502310490Scy  \definedummyword\geq
4503310490Scy  \definedummyword\guillemetleft
4504310490Scy  \definedummyword\guillemetright
4505310490Scy  \definedummyword\guilsinglleft
4506310490Scy  \definedummyword\guilsinglright
4507310490Scy  \definedummyword\lbracechar
4508310490Scy  \definedummyword\leq
4509310490Scy  \definedummyword\minus
4510310490Scy  \definedummyword\ogonek
4511310490Scy  \definedummyword\pounds
4512310490Scy  \definedummyword\point
4513310490Scy  \definedummyword\print
4514310490Scy  \definedummyword\quotedblbase
4515310490Scy  \definedummyword\quotedblleft
4516310490Scy  \definedummyword\quotedblright
4517310490Scy  \definedummyword\quoteleft
4518310490Scy  \definedummyword\quoteright
4519310490Scy  \definedummyword\quotesinglbase
4520310490Scy  \definedummyword\rbracechar
4521310490Scy  \definedummyword\result
4522310490Scy  \definedummyword\textdegree
4523174294Sobrien  %
4524310490Scy  % We want to disable all macros so that they are not expanded by \write.
4525310490Scy  \macrolist
4526310490Scy  %
4527310490Scy  \normalturnoffactive
4528310490Scy  %
4529174294Sobrien  % Handle some cases of @value -- where it does not contain any
4530174294Sobrien  % (non-fully-expandable) commands.
4531174294Sobrien  \makevalueexpandable
4532174294Sobrien}
4533174294Sobrien
4534174294Sobrien% \commondummiesnofonts: common to \commondummies and \indexnofonts.
4535119679Smbr%
4536310490Scy\def\commondummiesnofonts{%
4537310490Scy  % Control letters and accents.
4538310490Scy  \definedummyletter\!%
4539310490Scy  \definedummyaccent\"%
4540310490Scy  \definedummyaccent\'%
4541310490Scy  \definedummyletter\*%
4542310490Scy  \definedummyaccent\,%
4543310490Scy  \definedummyletter\.%
4544310490Scy  \definedummyletter\/%
4545310490Scy  \definedummyletter\:%
4546310490Scy  \definedummyaccent\=%
4547310490Scy  \definedummyletter\?%
4548310490Scy  \definedummyaccent\^%
4549310490Scy  \definedummyaccent\`%
4550310490Scy  \definedummyaccent\~%
4551310490Scy  \definedummyword\u
4552310490Scy  \definedummyword\v
4553310490Scy  \definedummyword\H
4554310490Scy  \definedummyword\dotaccent
4555310490Scy  \definedummyword\ogonek
4556310490Scy  \definedummyword\ringaccent
4557310490Scy  \definedummyword\tieaccent
4558310490Scy  \definedummyword\ubaraccent
4559310490Scy  \definedummyword\udotaccent
4560310490Scy  \definedummyword\dotless
4561310490Scy  %
4562310490Scy  % Texinfo font commands.
4563310490Scy  \definedummyword\b
4564310490Scy  \definedummyword\i
4565310490Scy  \definedummyword\r
4566310490Scy  \definedummyword\sansserif
4567310490Scy  \definedummyword\sc
4568310490Scy  \definedummyword\slanted
4569310490Scy  \definedummyword\t
4570310490Scy  %
4571310490Scy  % Commands that take arguments.
4572310490Scy  \definedummyword\abbr
4573310490Scy  \definedummyword\acronym
4574310490Scy  \definedummyword\anchor
4575310490Scy  \definedummyword\cite
4576310490Scy  \definedummyword\code
4577310490Scy  \definedummyword\command
4578310490Scy  \definedummyword\dfn
4579310490Scy  \definedummyword\dmn
4580310490Scy  \definedummyword\email
4581310490Scy  \definedummyword\emph
4582310490Scy  \definedummyword\env
4583310490Scy  \definedummyword\file
4584310490Scy  \definedummyword\image
4585310490Scy  \definedummyword\indicateurl
4586310490Scy  \definedummyword\inforef
4587310490Scy  \definedummyword\kbd
4588310490Scy  \definedummyword\key
4589310490Scy  \definedummyword\math
4590310490Scy  \definedummyword\option
4591310490Scy  \definedummyword\pxref
4592310490Scy  \definedummyword\ref
4593310490Scy  \definedummyword\samp
4594310490Scy  \definedummyword\strong
4595310490Scy  \definedummyword\tie
4596310490Scy  \definedummyword\uref
4597310490Scy  \definedummyword\url
4598310490Scy  \definedummyword\var
4599310490Scy  \definedummyword\verb
4600310490Scy  \definedummyword\w
4601310490Scy  \definedummyword\xref
460238494Sobrien}
460338494Sobrien
4604174294Sobrien% \indexnofonts is used when outputting the strings to sort the index
4605174294Sobrien% by, and when constructing control sequence names.  It eliminates all
4606174294Sobrien% control sequences and just writes whatever the best ASCII sort string
4607174294Sobrien% would be for a given command (usually its argument).
4608174294Sobrien%
460938494Sobrien\def\indexnofonts{%
4610174294Sobrien  % Accent commands should become @asis.
4611310490Scy  \def\definedummyaccent##1{\let##1\asis}%
4612174294Sobrien  % We can just ignore other control letters.
4613310490Scy  \def\definedummyletter##1{\let##1\empty}%
4614310490Scy  % All control words become @asis by default; overrides below.
4615174294Sobrien  \let\definedummyword\definedummyaccent
4616174294Sobrien  %
4617174294Sobrien  \commondummiesnofonts
4618174294Sobrien  %
4619174294Sobrien  % Don't no-op \tt, since it isn't a user-level command
4620174294Sobrien  % and is used in the definitions of the active chars like <, >, |, etc.
4621174294Sobrien  % Likewise with the other plain tex font commands.
4622174294Sobrien  %\let\tt=\asis
4623174294Sobrien  %
4624174294Sobrien  \def\ { }%
4625174294Sobrien  \def\@{@}%
4626174294Sobrien  \def\_{\normalunderscore}%
4627310490Scy  \def\-{}% @- shouldn't affect sorting
4628174294Sobrien  %
4629310490Scy  % Unfortunately, texindex is not prepared to handle braces in the
4630310490Scy  % content at all.  So for index sorting, we map @{ and @} to strings
4631310490Scy  % starting with |, since that ASCII character is between ASCII { and }.
4632310490Scy  \def\{{|a}%
4633310490Scy  \def\lbracechar{|a}%
4634310490Scy  %
4635310490Scy  \def\}{|b}%
4636310490Scy  \def\rbracechar{|b}%
4637310490Scy  %
4638174294Sobrien  % Non-English letters.
4639174294Sobrien  \def\AA{AA}%
4640174294Sobrien  \def\AE{AE}%
4641310490Scy  \def\DH{DZZ}%
4642174294Sobrien  \def\L{L}%
4643174294Sobrien  \def\OE{OE}%
4644174294Sobrien  \def\O{O}%
4645310490Scy  \def\TH{ZZZ}%
4646174294Sobrien  \def\aa{aa}%
4647174294Sobrien  \def\ae{ae}%
4648310490Scy  \def\dh{dzz}%
4649310490Scy  \def\exclamdown{!}%
4650174294Sobrien  \def\l{l}%
4651174294Sobrien  \def\oe{oe}%
4652310490Scy  \def\ordf{a}%
4653310490Scy  \def\ordm{o}%
4654174294Sobrien  \def\o{o}%
4655310490Scy  \def\questiondown{?}%
4656174294Sobrien  \def\ss{ss}%
4657310490Scy  \def\th{zzz}%
4658174294Sobrien  %
4659174294Sobrien  \def\LaTeX{LaTeX}%
4660174294Sobrien  \def\TeX{TeX}%
4661174294Sobrien  %
4662174294Sobrien  % Assorted special characters.
4663174294Sobrien  % (The following {} will end up in the sort string, but that's ok.)
4664310490Scy  \def\arrow{->}%
4665174294Sobrien  \def\bullet{bullet}%
4666174294Sobrien  \def\comma{,}%
4667174294Sobrien  \def\copyright{copyright}%
4668174294Sobrien  \def\dots{...}%
4669174294Sobrien  \def\enddots{...}%
4670174294Sobrien  \def\equiv{==}%
4671174294Sobrien  \def\error{error}%
4672310490Scy  \def\euro{euro}%
4673174294Sobrien  \def\expansion{==>}%
4674310490Scy  \def\geq{>=}%
4675310490Scy  \def\guillemetleft{<<}%
4676310490Scy  \def\guillemetright{>>}%
4677310490Scy  \def\guilsinglleft{<}%
4678310490Scy  \def\guilsinglright{>}%
4679310490Scy  \def\leq{<=}%
4680174294Sobrien  \def\minus{-}%
4681310490Scy  \def\point{.}%
4682174294Sobrien  \def\pounds{pounds}%
4683174294Sobrien  \def\print{-|}%
4684310490Scy  \def\quotedblbase{"}%
4685310490Scy  \def\quotedblleft{"}%
4686310490Scy  \def\quotedblright{"}%
4687310490Scy  \def\quoteleft{`}%
4688310490Scy  \def\quoteright{'}%
4689310490Scy  \def\quotesinglbase{,}%
4690310490Scy  \def\registeredsymbol{R}%
4691174294Sobrien  \def\result{=>}%
4692310490Scy  \def\textdegree{o}%
4693174294Sobrien  %
4694310490Scy  \expandafter\ifx\csname SETtxiindexlquoteignore\endcsname\relax
4695310490Scy  \else \indexlquoteignore \fi
4696310490Scy  %
4697310490Scy  % We need to get rid of all macros, leaving only the arguments (if present).
4698310490Scy  % Of course this is not nearly correct, but it is the best we can do for now.
4699310490Scy  % makeinfo does not expand macros in the argument to @deffn, which ends up
4700310490Scy  % writing an index entry, and texindex isn't prepared for an index sort entry
4701310490Scy  % that starts with \.
4702310490Scy  %
4703310490Scy  % Since macro invocations are followed by braces, we can just redefine them
4704310490Scy  % to take a single TeX argument.  The case of a macro invocation that
4705310490Scy  % goes to end-of-line is not handled.
4706310490Scy  %
4707310490Scy  \macrolist
470838494Sobrien}
470938494Sobrien
4710310490Scy% Undocumented (for FSFS 2nd ed.): @set txiindexlquoteignore makes us
4711310490Scy% ignore left quotes in the sort term.
4712310490Scy{\catcode`\`=\active
4713310490Scy \gdef\indexlquoteignore{\let`=\empty}}
4714310490Scy
471538494Sobrien\let\indexbackslash=0  %overridden during \printindex.
471642629Sobrien\let\SETmarginindex=\relax % put index entries in margin (undocumented)?
471738494Sobrien
471842629Sobrien% Most index entries go through here, but \dosubind is the general case.
4719174294Sobrien% #1 is the index name, #2 is the entry text.
4720174294Sobrien\def\doind#1#2{\dosubind{#1}{#2}{}}
472142629Sobrien
472242629Sobrien% Workhorse for all \fooindexes.
472342629Sobrien% #1 is name of index, #2 is stuff to put there, #3 is subentry --
4724174294Sobrien% empty if called from \doind, as we usually are (the main exception
4725174294Sobrien% is with most defuns, which call us directly).
472682794Sobrien%
472742629Sobrien\def\dosubind#1#2#3{%
4728174294Sobrien  \iflinks
4729174294Sobrien  {%
4730174294Sobrien    % Store the main index entry text (including the third arg).
4731174294Sobrien    \toks0 = {#2}%
4732174294Sobrien    % If third arg is present, precede it with a space.
4733174294Sobrien    \def\thirdarg{#3}%
4734174294Sobrien    \ifx\thirdarg\empty \else
4735174294Sobrien      \toks0 = \expandafter{\the\toks0 \space #3}%
4736174294Sobrien    \fi
4737174294Sobrien    %
4738174294Sobrien    \edef\writeto{\csname#1indfile\endcsname}%
4739174294Sobrien    %
4740310490Scy    \safewhatsit\dosubindwrite
4741174294Sobrien  }%
4742174294Sobrien  \fi
4743174294Sobrien}
4744174294Sobrien
4745174294Sobrien% Write the entry in \toks0 to the index file:
4746174294Sobrien%
4747174294Sobrien\def\dosubindwrite{%
474838494Sobrien  % Put the index entry in the margin if desired.
474938494Sobrien  \ifx\SETmarginindex\relax\else
4750174294Sobrien    \insert\margin{\hbox{\vrule height8pt depth3pt width0pt \the\toks0}}%
475138494Sobrien  \fi
4752174294Sobrien  %
4753174294Sobrien  % Remember, we are within a group.
4754174294Sobrien  \indexdummies % Must do this here, since \bf, etc expand at this stage
4755174294Sobrien  \def\backslashcurfont{\indexbackslash}% \indexbackslash isn't defined now
4756174294Sobrien      % so it will be output as is; and it will print as backslash.
4757174294Sobrien  %
4758174294Sobrien  % Process the index entry with all font commands turned off, to
4759174294Sobrien  % get the string to sort by.
4760174294Sobrien  {\indexnofonts
4761174294Sobrien   \edef\temp{\the\toks0}% need full expansion
4762174294Sobrien   \xdef\indexsorttmp{\temp}%
476338494Sobrien  }%
4764174294Sobrien  %
4765174294Sobrien  % Set up the complete index entry, with both the sort key and
4766174294Sobrien  % the original text, including any font commands.  We write
4767174294Sobrien  % three arguments to \entry to the .?? file (four in the
4768174294Sobrien  % subentry case), texindex reduces to two when writing the .??s
4769174294Sobrien  % sorted result.
4770174294Sobrien  \edef\temp{%
4771174294Sobrien    \write\writeto{%
4772174294Sobrien      \string\entry{\indexsorttmp}{\noexpand\folio}{\the\toks0}}%
4773174294Sobrien  }%
4774174294Sobrien  \temp
477538494Sobrien}
477638494Sobrien
4777310490Scy% Take care of unwanted page breaks/skips around a whatsit:
4778174294Sobrien%
4779174294Sobrien% If a skip is the last thing on the list now, preserve it
4780174294Sobrien% by backing up by \lastskip, doing the \write, then inserting
4781174294Sobrien% the skip again.  Otherwise, the whatsit generated by the
4782310490Scy% \write or \pdfdest will make \lastskip zero.  The result is that
4783310490Scy% sequences like this:
4784174294Sobrien% @end defun
4785174294Sobrien% @tindex whatever
4786174294Sobrien% @defun ...
4787174294Sobrien% will have extra space inserted, because the \medbreak in the
4788174294Sobrien% start of the @defun won't see the skip inserted by the @end of
4789174294Sobrien% the previous defun.
4790174294Sobrien%
4791174294Sobrien% But don't do any of this if we're not in vertical mode.  We
4792174294Sobrien% don't want to do a \vskip and prematurely end a paragraph.
4793174294Sobrien%
4794174294Sobrien% Avoid page breaks due to these extra skips, too.
4795174294Sobrien%
4796174294Sobrien% But wait, there is a catch there:
4797174294Sobrien% We'll have to check whether \lastskip is zero skip.  \ifdim is not
4798174294Sobrien% sufficient for this purpose, as it ignores stretch and shrink parts
4799174294Sobrien% of the skip.  The only way seems to be to check the textual
4800174294Sobrien% representation of the skip.
4801174294Sobrien%
4802174294Sobrien% The following is almost like \def\zeroskipmacro{0.0pt} except that
4803174294Sobrien% the ``p'' and ``t'' characters have catcode \other, not 11 (letter).
4804174294Sobrien%
4805174294Sobrien\edef\zeroskipmacro{\expandafter\the\csname z@skip\endcsname}
4806174294Sobrien%
4807310490Scy\newskip\whatsitskip
4808310490Scy\newcount\whatsitpenalty
4809310490Scy%
4810174294Sobrien% ..., ready, GO:
4811174294Sobrien%
4812310490Scy\def\safewhatsit#1{\ifhmode
4813310490Scy  #1%
4814310490Scy \else
4815174294Sobrien  % \lastskip and \lastpenalty cannot both be nonzero simultaneously.
4816310490Scy  \whatsitskip = \lastskip
4817174294Sobrien  \edef\lastskipmacro{\the\lastskip}%
4818310490Scy  \whatsitpenalty = \lastpenalty
4819174294Sobrien  %
4820174294Sobrien  % If \lastskip is nonzero, that means the last item was a
4821174294Sobrien  % skip.  And since a skip is discardable, that means this
4822310490Scy  % -\whatsitskip glue we're inserting is preceded by a
4823174294Sobrien  % non-discardable item, therefore it is not a potential
4824174294Sobrien  % breakpoint, therefore no \nobreak needed.
4825174294Sobrien  \ifx\lastskipmacro\zeroskipmacro
4826174294Sobrien  \else
4827310490Scy    \vskip-\whatsitskip
4828174294Sobrien  \fi
4829174294Sobrien  %
4830310490Scy  #1%
4831174294Sobrien  %
4832174294Sobrien  \ifx\lastskipmacro\zeroskipmacro
4833174294Sobrien    % If \lastskip was zero, perhaps the last item was a penalty, and
4834174294Sobrien    % perhaps it was >=10000, e.g., a \nobreak.  In that case, we want
4835174294Sobrien    % to re-insert the same penalty (values >10000 are used for various
4836174294Sobrien    % signals); since we just inserted a non-discardable item, any
4837174294Sobrien    % following glue (such as a \parskip) would be a breakpoint.  For example:
4838174294Sobrien    %   @deffn deffn-whatever
4839174294Sobrien    %   @vindex index-whatever
4840174294Sobrien    %   Description.
4841174294Sobrien    % would allow a break between the index-whatever whatsit
4842174294Sobrien    % and the "Description." paragraph.
4843310490Scy    \ifnum\whatsitpenalty>9999 \penalty\whatsitpenalty \fi
4844174294Sobrien  \else
4845174294Sobrien    % On the other hand, if we had a nonzero \lastskip,
4846174294Sobrien    % this make-up glue would be preceded by a non-discardable item
4847174294Sobrien    % (the whatsit from the \write), so we must insert a \nobreak.
4848310490Scy    \nobreak\vskip\whatsitskip
4849174294Sobrien  \fi
4850310490Scy\fi}
4851174294Sobrien
485238494Sobrien% The index entry written in the file actually looks like
485338494Sobrien%  \entry {sortstring}{page}{topic}
485438494Sobrien% or
485538494Sobrien%  \entry {sortstring}{page}{topic}{subtopic}
485638494Sobrien% The texindex program reads in these files and writes files
485738494Sobrien% containing these kinds of lines:
485838494Sobrien%  \initial {c}
485938494Sobrien%     before the first topic whose initial is c
486038494Sobrien%  \entry {topic}{pagelist}
486138494Sobrien%     for a topic that is used without subtopics
486238494Sobrien%  \primary {topic}
486338494Sobrien%     for the beginning of a topic that is used with subtopics
486438494Sobrien%  \secondary {subtopic}{pagelist}
486538494Sobrien%     for each subtopic.
486638494Sobrien
486738494Sobrien% Define the user-accessible indexing commands
486838494Sobrien% @findex, @vindex, @kindex, @cindex.
486938494Sobrien
487038494Sobrien\def\findex {\fnindex}
487138494Sobrien\def\kindex {\kyindex}
487238494Sobrien\def\cindex {\cpindex}
487338494Sobrien\def\vindex {\vrindex}
487438494Sobrien\def\tindex {\tpindex}
487538494Sobrien\def\pindex {\pgindex}
487638494Sobrien
487738494Sobrien\def\cindexsub {\begingroup\obeylines\cindexsub}
487838494Sobrien{\obeylines %
487938494Sobrien\gdef\cindexsub "#1" #2^^M{\endgroup %
488038494Sobrien\dosubind{cp}{#2}{#1}}}
488138494Sobrien
488238494Sobrien% Define the macros used in formatting output of the sorted index material.
488338494Sobrien
488438494Sobrien% @printindex causes a particular index (the ??s file) to get printed.
488538494Sobrien% It does not print any chapter heading (usually an @unnumbered).
488638494Sobrien%
4887174294Sobrien\parseargdef\printindex{\begingroup
488838494Sobrien  \dobreak \chapheadingskip{10000}%
488938494Sobrien  %
489082794Sobrien  \smallfonts \rm
489138494Sobrien  \tolerance = 9500
4892310490Scy  \plainfrenchspacing
4893174294Sobrien  \everypar = {}% don't want the \kern\-parindent from indentation suppression.
489438494Sobrien  %
489538494Sobrien  % See if the index file exists and is nonempty.
489642629Sobrien  % Change catcode of @ here so that if the index file contains
489742629Sobrien  % \initial {@}
489842629Sobrien  % as its first line, TeX doesn't complain about mismatched braces
489942629Sobrien  % (because it thinks @} is a control sequence).
490042629Sobrien  \catcode`\@ = 11
490138494Sobrien  \openin 1 \jobname.#1s
490238494Sobrien  \ifeof 1
490338494Sobrien    % \enddoublecolumns gets confused if there is no text in the index,
490438494Sobrien    % and it loses the chapter title and the aux file entries for the
490538494Sobrien    % index.  The easiest way to prevent this problem is to make sure
490638494Sobrien    % there is some text.
490782794Sobrien    \putwordIndexNonexistent
490838494Sobrien  \else
490938494Sobrien    %
491038494Sobrien    % If the index file exists but is empty, then \openin leaves \ifeof
491138494Sobrien    % false.  We have to make TeX try to read something from the file, so
491238494Sobrien    % it can discover if there is anything in it.
491338494Sobrien    \read 1 to \temp
491438494Sobrien    \ifeof 1
491582794Sobrien      \putwordIndexIsEmpty
491638494Sobrien    \else
491738494Sobrien      % Index files are almost Texinfo source, but we use \ as the escape
491838494Sobrien      % character.  It would be better to use @, but that's too big a change
491938494Sobrien      % to make right now.
4920174294Sobrien      \def\indexbackslash{\backslashcurfont}%
492138494Sobrien      \catcode`\\ = 0
492238494Sobrien      \escapechar = `\\
492338494Sobrien      \begindoublecolumns
492438494Sobrien      \input \jobname.#1s
492538494Sobrien      \enddoublecolumns
492638494Sobrien    \fi
492738494Sobrien  \fi
492838494Sobrien  \closein 1
492938494Sobrien\endgroup}
493038494Sobrien
493138494Sobrien% These macros are used by the sorted index file itself.
493238494Sobrien% Change them to control the appearance of the index.
493338494Sobrien
493442629Sobrien\def\initial#1{{%
493542629Sobrien  % Some minor font changes for the special characters.
493642629Sobrien  \let\tentt=\sectt \let\tt=\sectt \let\sf=\sectt
493742629Sobrien  %
493842629Sobrien  % Remove any glue we may have, we'll be inserting our own.
493942629Sobrien  \removelastskip
494082794Sobrien  %
494142629Sobrien  % We like breaks before the index initials, so insert a bonus.
4942174294Sobrien  \nobreak
4943174294Sobrien  \vskip 0pt plus 3\baselineskip
4944174294Sobrien  \penalty 0
4945174294Sobrien  \vskip 0pt plus -3\baselineskip
494642629Sobrien  %
494742629Sobrien  % Typeset the initial.  Making this add up to a whole number of
494842629Sobrien  % baselineskips increases the chance of the dots lining up from column
494942629Sobrien  % to column.  It still won't often be perfect, because of the stretch
495042629Sobrien  % we need before each entry, but it's better.
495182794Sobrien  %
495242629Sobrien  % No shrink because it confuses \balancecolumns.
495342629Sobrien  \vskip 1.67\baselineskip plus .5\baselineskip
495442629Sobrien  \leftline{\secbf #1}%
495542629Sobrien  % Do our best not to break after the initial.
495642629Sobrien  \nobreak
4957174294Sobrien  \vskip .33\baselineskip plus .1\baselineskip
495842629Sobrien}}
495938494Sobrien
4960174294Sobrien% \entry typesets a paragraph consisting of the text (#1), dot leaders, and
4961174294Sobrien% then page number (#2) flushed to the right margin.  It is used for index
4962174294Sobrien% and table of contents entries.  The paragraph is indented by \leftskip.
496338494Sobrien%
4964174294Sobrien% A straightforward implementation would start like this:
4965174294Sobrien%	\def\entry#1#2{...
4966310490Scy% But this freezes the catcodes in the argument, and can cause problems to
4967174294Sobrien% @code, which sets - active.  This problem was fixed by a kludge---
4968174294Sobrien% ``-'' was active throughout whole index, but this isn't really right.
4969174294Sobrien% The right solution is to prevent \entry from swallowing the whole text.
4970174294Sobrien%                                 --kasal, 21nov03
4971174294Sobrien\def\entry{%
4972174294Sobrien  \begingroup
497338494Sobrien    %
4974174294Sobrien    % Start a new paragraph if necessary, so our assignments below can't
4975174294Sobrien    % affect previous text.
4976174294Sobrien    \par
497738494Sobrien    %
4978174294Sobrien    % Do not fill out the last line with white space.
4979174294Sobrien    \parfillskip = 0in
4980174294Sobrien    %
4981174294Sobrien    % No extra space above this paragraph.
4982174294Sobrien    \parskip = 0in
4983174294Sobrien    %
4984174294Sobrien    % Do not prefer a separate line ending with a hyphen to fewer lines.
4985174294Sobrien    \finalhyphendemerits = 0
4986174294Sobrien    %
4987174294Sobrien    % \hangindent is only relevant when the entry text and page number
4988174294Sobrien    % don't both fit on one line.  In that case, bob suggests starting the
4989174294Sobrien    % dots pretty far over on the line.  Unfortunately, a large
4990174294Sobrien    % indentation looks wrong when the entry text itself is broken across
4991174294Sobrien    % lines.  So we use a small indentation and put up with long leaders.
4992174294Sobrien    %
4993174294Sobrien    % \hangafter is reset to 1 (which is the value we want) at the start
4994174294Sobrien    % of each paragraph, so we need not do anything with that.
4995174294Sobrien    \hangindent = 2em
4996174294Sobrien    %
4997174294Sobrien    % When the entry text needs to be broken, just fill out the first line
4998174294Sobrien    % with blank space.
4999174294Sobrien    \rightskip = 0pt plus1fil
5000174294Sobrien    %
5001174294Sobrien    % A bit of stretch before each entry for the benefit of balancing
5002174294Sobrien    % columns.
5003174294Sobrien    \vskip 0pt plus1pt
5004174294Sobrien    %
5005310490Scy    % When reading the text of entry, convert explicit line breaks
5006310490Scy    % from @* into spaces.  The user might give these in long section
5007310490Scy    % titles, for instance.
5008310490Scy    \def\*{\unskip\space\ignorespaces}%
5009310490Scy    \def\entrybreak{\hfil\break}%
5010310490Scy    %
5011174294Sobrien    % Swallow the left brace of the text (first parameter):
5012174294Sobrien    \afterassignment\doentry
5013174294Sobrien    \let\temp =
5014174294Sobrien}
5015310490Scy\def\entrybreak{\unskip\space\ignorespaces}%
5016174294Sobrien\def\doentry{%
5017174294Sobrien    \bgroup % Instead of the swallowed brace.
5018174294Sobrien      \noindent
5019174294Sobrien      \aftergroup\finishentry
5020174294Sobrien      % And now comes the text of the entry.
5021174294Sobrien}
5022174294Sobrien\def\finishentry#1{%
5023174294Sobrien    % #1 is the page number.
5024174294Sobrien    %
5025174294Sobrien    % The following is kludged to not output a line of dots in the index if
5026174294Sobrien    % there are no page numbers.  The next person who breaks this will be
5027174294Sobrien    % cursed by a Unix daemon.
5028310490Scy    \setbox\boxA = \hbox{#1}%
5029310490Scy    \ifdim\wd\boxA = 0pt
5030174294Sobrien      \ %
503182794Sobrien    \else
5032174294Sobrien      %
5033174294Sobrien      % If we must, put the page number on a line of its own, and fill out
5034174294Sobrien      % this line with blank space.  (The \hfil is overwhelmed with the
5035174294Sobrien      % fill leaders glue in \indexdotfill if the page number does fit.)
5036174294Sobrien      \hfil\penalty50
5037174294Sobrien      \null\nobreak\indexdotfill % Have leaders before the page number.
5038174294Sobrien      %
5039174294Sobrien      % The `\ ' here is removed by the implicit \unskip that TeX does as
5040174294Sobrien      % part of (the primitive) \par.  Without it, a spurious underfull
5041174294Sobrien      % \hbox ensues.
5042174294Sobrien      \ifpdf
5043174294Sobrien	\pdfgettoks#1.%
5044174294Sobrien	\ \the\toksA
5045174294Sobrien      \else
5046174294Sobrien	\ #1%
5047174294Sobrien      \fi
504882794Sobrien    \fi
5049174294Sobrien    \par
5050174294Sobrien  \endgroup
5051174294Sobrien}
505238494Sobrien
5053310490Scy% Like plain.tex's \dotfill, except uses up at least 1 em.
505438494Sobrien\def\indexdotfill{\cleaders
5055310490Scy  \hbox{$\mathsurround=0pt \mkern1.5mu.\mkern1.5mu$}\hskip 1em plus 1fill}
505638494Sobrien
505738494Sobrien\def\primary #1{\line{#1\hfil}}
505838494Sobrien
505938494Sobrien\newskip\secondaryindent \secondaryindent=0.5cm
506082794Sobrien\def\secondary#1#2{{%
506182794Sobrien  \parfillskip=0in
506282794Sobrien  \parskip=0in
506382794Sobrien  \hangindent=1in
506482794Sobrien  \hangafter=1
506582794Sobrien  \noindent\hskip\secondaryindent\hbox{#1}\indexdotfill
506682794Sobrien  \ifpdf
506782794Sobrien    \pdfgettoks#2.\ \the\toksA % The page number ends the paragraph.
506882794Sobrien  \else
506982794Sobrien    #2
507082794Sobrien  \fi
507182794Sobrien  \par
507238494Sobrien}}
507338494Sobrien
507438494Sobrien% Define two-column mode, which we use to typeset indexes.
507538494Sobrien% Adapted from the TeXbook, page 416, which is to say,
507638494Sobrien% the manmac.tex format used to print the TeXbook itself.
507738494Sobrien\catcode`\@=11
507838494Sobrien
507938494Sobrien\newbox\partialpage
508038494Sobrien\newdimen\doublecolumnhsize
508138494Sobrien
508238494Sobrien\def\begindoublecolumns{\begingroup % ended by \enddoublecolumns
508338494Sobrien  % Grab any single-column material above us.
508482794Sobrien  \output = {%
508582794Sobrien    %
508638494Sobrien    % Here is a possibility not foreseen in manmac: if we accumulate a
508738494Sobrien    % whole lot of material, we might end up calling this \output
508838494Sobrien    % routine twice in a row (see the doublecol-lose test, which is
508938494Sobrien    % essentially a couple of indexes with @setchapternewpage off).  In
509082794Sobrien    % that case we just ship out what is in \partialpage with the normal
509182794Sobrien    % output routine.  Generally, \partialpage will be empty when this
509282794Sobrien    % runs and this will be a no-op.  See the indexspread.tex test case.
509382794Sobrien    \ifvoid\partialpage \else
509482794Sobrien      \onepageout{\pagecontents\partialpage}%
509582794Sobrien    \fi
509638494Sobrien    %
509782794Sobrien    \global\setbox\partialpage = \vbox{%
509882794Sobrien      % Unvbox the main output page.
509982794Sobrien      \unvbox\PAGE
510082794Sobrien      \kern-\topskip \kern\baselineskip
510182794Sobrien    }%
510282794Sobrien  }%
510382794Sobrien  \eject % run that output routine to set \partialpage
510438494Sobrien  %
510538494Sobrien  % Use the double-column output routine for subsequent pages.
510638494Sobrien  \output = {\doublecolumnout}%
510738494Sobrien  %
510838494Sobrien  % Change the page size parameters.  We could do this once outside this
510938494Sobrien  % routine, in each of @smallbook, @afourpaper, and the default 8.5x11
511038494Sobrien  % format, but then we repeat the same computation.  Repeating a couple
511138494Sobrien  % of assignments once per index is clearly meaningless for the
511238494Sobrien  % execution time, so we may as well do it in one place.
511338494Sobrien  %
511438494Sobrien  % First we halve the line length, less a little for the gutter between
511538494Sobrien  % the columns.  We compute the gutter based on the line length, so it
511638494Sobrien  % changes automatically with the paper format.  The magic constant
511738494Sobrien  % below is chosen so that the gutter has the same value (well, +-<1pt)
511838494Sobrien  % as it did when we hard-coded it.
511938494Sobrien  %
512038494Sobrien  % We put the result in a separate register, \doublecolumhsize, so we
512138494Sobrien  % can restore it in \pagesofar, after \hsize itself has (potentially)
512238494Sobrien  % been clobbered.
512338494Sobrien  %
512438494Sobrien  \doublecolumnhsize = \hsize
512538494Sobrien    \advance\doublecolumnhsize by -.04154\hsize
512638494Sobrien    \divide\doublecolumnhsize by 2
512738494Sobrien  \hsize = \doublecolumnhsize
512838494Sobrien  %
512938494Sobrien  % Double the \vsize as well.  (We don't need a separate register here,
513038494Sobrien  % since nobody clobbers \vsize.)
513138494Sobrien  \vsize = 2\vsize
513238494Sobrien}
513342629Sobrien
513442629Sobrien% The double-column output routine for all double-column pages except
513542629Sobrien% the last.
513682794Sobrien%
513738494Sobrien\def\doublecolumnout{%
513838494Sobrien  \splittopskip=\topskip \splitmaxdepth=\maxdepth
513938494Sobrien  % Get the available space for the double columns -- the normal
514038494Sobrien  % (undoubled) page height minus any material left over from the
514138494Sobrien  % previous page.
514242629Sobrien  \dimen@ = \vsize
514342629Sobrien  \divide\dimen@ by 2
514482794Sobrien  \advance\dimen@ by -\ht\partialpage
514542629Sobrien  %
514638494Sobrien  % box0 will be the left-hand column, box2 the right.
514738494Sobrien  \setbox0=\vsplit255 to\dimen@ \setbox2=\vsplit255 to\dimen@
514838494Sobrien  \onepageout\pagesofar
514938494Sobrien  \unvbox255
515038494Sobrien  \penalty\outputpenalty
515138494Sobrien}
515282794Sobrien%
515382794Sobrien% Re-output the contents of the output page -- any previous material,
515482794Sobrien% followed by the two boxes we just split, in box0 and box2.
515538494Sobrien\def\pagesofar{%
515638494Sobrien  \unvbox\partialpage
515742629Sobrien  %
515838494Sobrien  \hsize = \doublecolumnhsize
515942629Sobrien  \wd0=\hsize \wd2=\hsize
516042629Sobrien  \hbox to\pagewidth{\box0\hfil\box2}%
516138494Sobrien}
5162174294Sobrien%
516382794Sobrien% All done with double columns.
516438494Sobrien\def\enddoublecolumns{%
5165310490Scy  % The following penalty ensures that the page builder is exercised
5166310490Scy  % _before_ we change the output routine.  This is necessary in the
5167310490Scy  % following situation:
5168310490Scy  %
5169310490Scy  % The last section of the index consists only of a single entry.
5170310490Scy  % Before this section, \pagetotal is less than \pagegoal, so no
5171310490Scy  % break occurs before the last section starts.  However, the last
5172310490Scy  % section, consisting of \initial and the single \entry, does not
5173310490Scy  % fit on the page and has to be broken off.  Without the following
5174310490Scy  % penalty the page builder will not be exercised until \eject
5175310490Scy  % below, and by that time we'll already have changed the output
5176310490Scy  % routine to the \balancecolumns version, so the next-to-last
5177310490Scy  % double-column page will be processed with \balancecolumns, which
5178310490Scy  % is wrong:  The two columns will go to the main vertical list, with
5179310490Scy  % the broken-off section in the recent contributions.  As soon as
5180310490Scy  % the output routine finishes, TeX starts reconsidering the page
5181310490Scy  % break.  The two columns and the broken-off section both fit on the
5182310490Scy  % page, because the two columns now take up only half of the page
5183310490Scy  % goal.  When TeX sees \eject from below which follows the final
5184310490Scy  % section, it invokes the new output routine that we've set after
5185310490Scy  % \balancecolumns below; \onepageout will try to fit the two columns
5186310490Scy  % and the final section into the vbox of \pageheight (see
5187310490Scy  % \pagebody), causing an overfull box.
5188310490Scy  %
5189310490Scy  % Note that glue won't work here, because glue does not exercise the
5190310490Scy  % page builder, unlike penalties (see The TeXbook, pp. 280-281).
5191310490Scy  \penalty0
5192310490Scy  %
519342629Sobrien  \output = {%
519482794Sobrien    % Split the last of the double-column material.  Leave it on the
519542629Sobrien    % current page, no automatic page break.
519642629Sobrien    \balancecolumns
519742629Sobrien    %
519842629Sobrien    % If we end up splitting too much material for the current page,
519942629Sobrien    % though, there will be another page break right after this \output
520042629Sobrien    % invocation ends.  Having called \balancecolumns once, we do not
520142629Sobrien    % want to call it again.  Therefore, reset \output to its normal
520242629Sobrien    % definition right away.  (We hope \balancecolumns will never be
520342629Sobrien    % called on to balance too much material, but if it is, this makes
520442629Sobrien    % the output somewhat more palatable.)
520542629Sobrien    \global\output = {\onepageout{\pagecontents\PAGE}}%
520642629Sobrien  }%
520742629Sobrien  \eject
520838494Sobrien  \endgroup % started in \begindoublecolumns
520982794Sobrien  %
521082794Sobrien  % \pagegoal was set to the doubled \vsize above, since we restarted
521182794Sobrien  % the current page.  We're now back to normal single-column
521282794Sobrien  % typesetting, so reset \pagegoal to the normal \vsize (after the
521382794Sobrien  % \endgroup where \vsize got restored).
521482794Sobrien  \pagegoal = \vsize
521538494Sobrien}
521682794Sobrien%
521782794Sobrien% Called at the end of the double column material.
521838494Sobrien\def\balancecolumns{%
521942629Sobrien  \setbox0 = \vbox{\unvbox255}% like \box255 but more efficient, see p.120.
522038494Sobrien  \dimen@ = \ht0
522138494Sobrien  \advance\dimen@ by \topskip
522238494Sobrien  \advance\dimen@ by-\baselineskip
522342629Sobrien  \divide\dimen@ by 2 % target to split to
522442629Sobrien  %debug\message{final 2-column material height=\the\ht0, target=\the\dimen@.}%
522538494Sobrien  \splittopskip = \topskip
522638494Sobrien  % Loop until we get a decent breakpoint.
522742629Sobrien  {%
522842629Sobrien    \vbadness = 10000
522942629Sobrien    \loop
523042629Sobrien      \global\setbox3 = \copy0
523142629Sobrien      \global\setbox1 = \vsplit3 to \dimen@
523242629Sobrien    \ifdim\ht3>\dimen@
523342629Sobrien      \global\advance\dimen@ by 1pt
523442629Sobrien    \repeat
523542629Sobrien  }%
523642629Sobrien  %debug\message{split to \the\dimen@, column heights: \the\ht1, \the\ht3.}%
523738494Sobrien  \setbox0=\vbox to\dimen@{\unvbox1}%
523838494Sobrien  \setbox2=\vbox to\dimen@{\unvbox3}%
523942629Sobrien  %
524038494Sobrien  \pagesofar
524138494Sobrien}
524238494Sobrien\catcode`\@ = \other
524338494Sobrien
524438494Sobrien
524538494Sobrien\message{sectioning,}
524682794Sobrien% Chapters, sections, etc.
524738494Sobrien
5248310490Scy% Let's start with @part.
5249310490Scy\outer\parseargdef\part{\partzzz{#1}}
5250310490Scy\def\partzzz#1{%
5251310490Scy  \chapoddpage
5252310490Scy  \null
5253310490Scy  \vskip.3\vsize  % move it down on the page a bit
5254310490Scy  \begingroup
5255310490Scy    \noindent \titlefonts\rmisbold #1\par % the text
5256310490Scy    \let\lastnode=\empty      % no node to associate with
5257310490Scy    \writetocentry{part}{#1}{}% but put it in the toc
5258310490Scy    \headingsoff              % no headline or footline on the part page
5259310490Scy    \chapoddpage
5260310490Scy  \endgroup
5261310490Scy}
5262310490Scy
5263310490Scy% \unnumberedno is an oxymoron.  But we count the unnumbered
5264174294Sobrien% sections so that we can refer to them unambiguously in the pdf
5265174294Sobrien% outlines by their "section number".  We avoid collisions with chapter
5266174294Sobrien% numbers by starting them at 10000.  (If a document ever has 10000
5267174294Sobrien% chapters, we're in trouble anyway, I'm sure.)
5268174294Sobrien\newcount\unnumberedno \unnumberedno = 10000
526938494Sobrien\newcount\chapno
527038494Sobrien\newcount\secno        \secno=0
527138494Sobrien\newcount\subsecno     \subsecno=0
527238494Sobrien\newcount\subsubsecno  \subsubsecno=0
527338494Sobrien
527438494Sobrien% This counter is funny since it counts through charcodes of letters A, B, ...
527538494Sobrien\newcount\appendixno  \appendixno = `\@
5276174294Sobrien%
527782794Sobrien% \def\appendixletter{\char\the\appendixno}
5278174294Sobrien% We do the following ugly conditional instead of the above simple
5279174294Sobrien% construct for the sake of pdftex, which needs the actual
528082794Sobrien% letter in the expansion, not just typeset.
5281174294Sobrien%
528282794Sobrien\def\appendixletter{%
528382794Sobrien  \ifnum\appendixno=`A A%
528482794Sobrien  \else\ifnum\appendixno=`B B%
528582794Sobrien  \else\ifnum\appendixno=`C C%
528682794Sobrien  \else\ifnum\appendixno=`D D%
528782794Sobrien  \else\ifnum\appendixno=`E E%
528882794Sobrien  \else\ifnum\appendixno=`F F%
528982794Sobrien  \else\ifnum\appendixno=`G G%
529082794Sobrien  \else\ifnum\appendixno=`H H%
529182794Sobrien  \else\ifnum\appendixno=`I I%
529282794Sobrien  \else\ifnum\appendixno=`J J%
529382794Sobrien  \else\ifnum\appendixno=`K K%
529482794Sobrien  \else\ifnum\appendixno=`L L%
529582794Sobrien  \else\ifnum\appendixno=`M M%
529682794Sobrien  \else\ifnum\appendixno=`N N%
529782794Sobrien  \else\ifnum\appendixno=`O O%
529882794Sobrien  \else\ifnum\appendixno=`P P%
529982794Sobrien  \else\ifnum\appendixno=`Q Q%
530082794Sobrien  \else\ifnum\appendixno=`R R%
530182794Sobrien  \else\ifnum\appendixno=`S S%
530282794Sobrien  \else\ifnum\appendixno=`T T%
530382794Sobrien  \else\ifnum\appendixno=`U U%
530482794Sobrien  \else\ifnum\appendixno=`V V%
530582794Sobrien  \else\ifnum\appendixno=`W W%
530682794Sobrien  \else\ifnum\appendixno=`X X%
530782794Sobrien  \else\ifnum\appendixno=`Y Y%
530882794Sobrien  \else\ifnum\appendixno=`Z Z%
530982794Sobrien  % The \the is necessary, despite appearances, because \appendixletter is
531082794Sobrien  % expanded while writing the .toc file.  \char\appendixno is not
531182794Sobrien  % expandable, thus it is written literally, thus all appendixes come out
531282794Sobrien  % with the same letter (or @) in the toc without it.
531382794Sobrien  \else\char\the\appendixno
531482794Sobrien  \fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi
531582794Sobrien  \fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi}
531638494Sobrien
5317310490Scy% Each @chapter defines these (using marks) as the number+name, number
5318310490Scy% and name of the chapter.  Page headings and footings can use
5319310490Scy% these.  @section does likewise.
532042629Sobrien\def\thischapter{}
5321310490Scy\def\thischapternum{}
5322310490Scy\def\thischaptername{}
532342629Sobrien\def\thissection{}
5324310490Scy\def\thissectionnum{}
5325310490Scy\def\thissectionname{}
532638494Sobrien
532738494Sobrien\newcount\absseclevel % used to calculate proper heading level
5328174294Sobrien\newcount\secbase\secbase=0 % @raisesections/@lowersections modify this count
532938494Sobrien
533038494Sobrien% @raisesections: treat @section as chapter, @subsection as section, etc.
533138494Sobrien\def\raisesections{\global\advance\secbase by -1}
533238494Sobrien\let\up=\raisesections % original BFox name
533338494Sobrien
533438494Sobrien% @lowersections: treat @chapter as section, @section as subsection, etc.
533538494Sobrien\def\lowersections{\global\advance\secbase by 1}
533638494Sobrien\let\down=\lowersections % original BFox name
533738494Sobrien
5338174294Sobrien% we only have subsub.
5339174294Sobrien\chardef\maxseclevel = 3
5340174294Sobrien%
5341174294Sobrien% A numbered section within an unnumbered changes to unnumbered too.
5342310490Scy% To achieve this, remember the "biggest" unnum. sec. we are currently in:
5343310490Scy\chardef\unnlevel = \maxseclevel
5344174294Sobrien%
5345174294Sobrien% Trace whether the current chapter is an appendix or not:
5346174294Sobrien% \chapheadtype is "N" or "A", unnumbered chapters are ignored.
5347174294Sobrien\def\chapheadtype{N}
5348174294Sobrien
5349174294Sobrien% Choose a heading macro
5350174294Sobrien% #1 is heading type
5351174294Sobrien% #2 is heading level
5352174294Sobrien% #3 is text for heading
5353174294Sobrien\def\genhead#1#2#3{%
5354174294Sobrien  % Compute the abs. sec. level:
5355174294Sobrien  \absseclevel=#2
5356174294Sobrien  \advance\absseclevel by \secbase
5357174294Sobrien  % Make sure \absseclevel doesn't fall outside the range:
5358174294Sobrien  \ifnum \absseclevel < 0
5359174294Sobrien    \absseclevel = 0
536038494Sobrien  \else
5361174294Sobrien    \ifnum \absseclevel > 3
5362174294Sobrien      \absseclevel = 3
5363174294Sobrien    \fi
536438494Sobrien  \fi
5365174294Sobrien  % The heading type:
5366174294Sobrien  \def\headtype{#1}%
5367174294Sobrien  \if \headtype U%
5368310490Scy    \ifnum \absseclevel < \unnlevel
5369310490Scy      \chardef\unnlevel = \absseclevel
5370174294Sobrien    \fi
537138494Sobrien  \else
5372174294Sobrien    % Check for appendix sections:
5373174294Sobrien    \ifnum \absseclevel = 0
5374174294Sobrien      \edef\chapheadtype{\headtype}%
5375174294Sobrien    \else
5376174294Sobrien      \if \headtype A\if \chapheadtype N%
5377174294Sobrien	\errmessage{@appendix... within a non-appendix chapter}%
5378174294Sobrien      \fi\fi
5379174294Sobrien    \fi
5380174294Sobrien    % Check for numbered within unnumbered:
5381310490Scy    \ifnum \absseclevel > \unnlevel
5382174294Sobrien      \def\headtype{U}%
5383174294Sobrien    \else
5384310490Scy      \chardef\unnlevel = 3
5385174294Sobrien    \fi
538638494Sobrien  \fi
5387174294Sobrien  % Now print the heading:
5388174294Sobrien  \if \headtype U%
5389174294Sobrien    \ifcase\absseclevel
5390174294Sobrien	\unnumberedzzz{#3}%
5391174294Sobrien    \or \unnumberedseczzz{#3}%
5392174294Sobrien    \or \unnumberedsubseczzz{#3}%
5393174294Sobrien    \or \unnumberedsubsubseczzz{#3}%
5394174294Sobrien    \fi
539538494Sobrien  \else
5396174294Sobrien    \if \headtype A%
5397174294Sobrien      \ifcase\absseclevel
5398174294Sobrien	  \appendixzzz{#3}%
5399174294Sobrien      \or \appendixsectionzzz{#3}%
5400174294Sobrien      \or \appendixsubseczzz{#3}%
5401174294Sobrien      \or \appendixsubsubseczzz{#3}%
5402174294Sobrien      \fi
5403174294Sobrien    \else
5404174294Sobrien      \ifcase\absseclevel
5405174294Sobrien	  \chapterzzz{#3}%
5406174294Sobrien      \or \seczzz{#3}%
5407174294Sobrien      \or \numberedsubseczzz{#3}%
5408174294Sobrien      \or \numberedsubsubseczzz{#3}%
5409174294Sobrien      \fi
5410174294Sobrien    \fi
541138494Sobrien  \fi
5412174294Sobrien  \suppressfirstparagraphindent
541338494Sobrien}
541438494Sobrien
5415174294Sobrien% an interface:
5416174294Sobrien\def\numhead{\genhead N}
5417174294Sobrien\def\apphead{\genhead A}
5418174294Sobrien\def\unnmhead{\genhead U}
5419174294Sobrien
5420174294Sobrien% @chapter, @appendix, @unnumbered.  Increment top-level counter, reset
5421174294Sobrien% all lower-level sectioning counters to zero.
5422174294Sobrien%
5423174294Sobrien% Also set \chaplevelprefix, which we prepend to @float sequence numbers
5424174294Sobrien% (e.g., figures), q.v.  By default (before any chapter), that is empty.
5425174294Sobrien\let\chaplevelprefix = \empty
5426174294Sobrien%
5427174294Sobrien\outer\parseargdef\chapter{\numhead0{#1}} % normally numhead0 calls chapterzzz
5428174294Sobrien\def\chapterzzz#1{%
5429174294Sobrien  % section resetting is \global in case the chapter is in a group, such
5430174294Sobrien  % as an @include file.
5431174294Sobrien  \global\secno=0 \global\subsecno=0 \global\subsubsecno=0
5432174294Sobrien    \global\advance\chapno by 1
5433174294Sobrien  %
5434174294Sobrien  % Used for \float.
5435174294Sobrien  \gdef\chaplevelprefix{\the\chapno.}%
5436174294Sobrien  \resetallfloatnos
5437174294Sobrien  %
5438310490Scy  % \putwordChapter can contain complex things in translations.
5439310490Scy  \toks0=\expandafter{\putwordChapter}%
5440310490Scy  \message{\the\toks0 \space \the\chapno}%
5441174294Sobrien  %
5442174294Sobrien  % Write the actual heading.
5443174294Sobrien  \chapmacro{#1}{Ynumbered}{\the\chapno}%
5444174294Sobrien  %
5445174294Sobrien  % So @section and the like are numbered underneath this chapter.
5446174294Sobrien  \global\let\section = \numberedsec
5447174294Sobrien  \global\let\subsection = \numberedsubsec
5448174294Sobrien  \global\let\subsubsection = \numberedsubsubsec
544942629Sobrien}
545038494Sobrien
5451310490Scy\outer\parseargdef\appendix{\apphead0{#1}} % normally calls appendixzzz
5452310490Scy%
5453174294Sobrien\def\appendixzzz#1{%
5454174294Sobrien  \global\secno=0 \global\subsecno=0 \global\subsubsecno=0
5455174294Sobrien    \global\advance\appendixno by 1
5456174294Sobrien  \gdef\chaplevelprefix{\appendixletter.}%
5457174294Sobrien  \resetallfloatnos
5458174294Sobrien  %
5459310490Scy  % \putwordAppendix can contain complex things in translations.
5460310490Scy  \toks0=\expandafter{\putwordAppendix}%
5461310490Scy  \message{\the\toks0 \space \appendixletter}%
5462174294Sobrien  %
5463174294Sobrien  \chapmacro{#1}{Yappendix}{\appendixletter}%
5464174294Sobrien  %
5465174294Sobrien  \global\let\section = \appendixsec
5466174294Sobrien  \global\let\subsection = \appendixsubsec
5467174294Sobrien  \global\let\subsubsection = \appendixsubsubsec
546842629Sobrien}
546938494Sobrien
5470310490Scy% normally unnmhead0 calls unnumberedzzz:
5471310490Scy\outer\parseargdef\unnumbered{\unnmhead0{#1}}
5472174294Sobrien\def\unnumberedzzz#1{%
5473174294Sobrien  \global\secno=0 \global\subsecno=0 \global\subsubsecno=0
5474174294Sobrien    \global\advance\unnumberedno by 1
5475174294Sobrien  %
5476174294Sobrien  % Since an unnumbered has no number, no prefix for figures.
5477174294Sobrien  \global\let\chaplevelprefix = \empty
5478174294Sobrien  \resetallfloatnos
5479174294Sobrien  %
5480174294Sobrien  % This used to be simply \message{#1}, but TeX fully expands the
5481174294Sobrien  % argument to \message.  Therefore, if #1 contained @-commands, TeX
5482174294Sobrien  % expanded them.  For example, in `@unnumbered The @cite{Book}', TeX
5483174294Sobrien  % expanded @cite (which turns out to cause errors because \cite is meant
5484174294Sobrien  % to be executed, not expanded).
5485174294Sobrien  %
5486174294Sobrien  % Anyway, we don't want the fully-expanded definition of @cite to appear
5487174294Sobrien  % as a result of the \message, we just want `@cite' itself.  We use
5488174294Sobrien  % \the<toks register> to achieve this: TeX expands \the<toks> only once,
5489174294Sobrien  % simply yielding the contents of <toks register>.  (We also do this for
5490174294Sobrien  % the toc entries.)
5491174294Sobrien  \toks0 = {#1}%
5492174294Sobrien  \message{(\the\toks0)}%
5493174294Sobrien  %
5494174294Sobrien  \chapmacro{#1}{Ynothing}{\the\unnumberedno}%
5495174294Sobrien  %
5496174294Sobrien  \global\let\section = \unnumberedsec
5497174294Sobrien  \global\let\subsection = \unnumberedsubsec
5498174294Sobrien  \global\let\subsubsection = \unnumberedsubsubsec
5499174294Sobrien}
5500174294Sobrien
550138494Sobrien% @centerchap is like @unnumbered, but the heading is centered.
5502174294Sobrien\outer\parseargdef\centerchap{%
5503174294Sobrien  % Well, we could do the following in a group, but that would break
5504174294Sobrien  % an assumption that \chapmacro is called at the outermost level.
5505174294Sobrien  % Thus we are safer this way:		--kasal, 24feb04
5506174294Sobrien  \let\centerparametersmaybe = \centerparameters
5507174294Sobrien  \unnmhead0{#1}%
5508174294Sobrien  \let\centerparametersmaybe = \relax
5509174294Sobrien}
551038494Sobrien
551142629Sobrien% @top is like @unnumbered.
5512174294Sobrien\let\top\unnumbered
551342629Sobrien
551442629Sobrien% Sections.
5515310490Scy% 
5516174294Sobrien\outer\parseargdef\numberedsec{\numhead1{#1}} % normally calls seczzz
5517174294Sobrien\def\seczzz#1{%
5518174294Sobrien  \global\subsecno=0 \global\subsubsecno=0  \global\advance\secno by 1
5519174294Sobrien  \sectionheading{#1}{sec}{Ynumbered}{\the\chapno.\the\secno}%
552042629Sobrien}
552138494Sobrien
5522310490Scy% normally calls appendixsectionzzz:
5523310490Scy\outer\parseargdef\appendixsection{\apphead1{#1}}
5524174294Sobrien\def\appendixsectionzzz#1{%
5525174294Sobrien  \global\subsecno=0 \global\subsubsecno=0  \global\advance\secno by 1
5526174294Sobrien  \sectionheading{#1}{sec}{Yappendix}{\appendixletter.\the\secno}%
552742629Sobrien}
5528174294Sobrien\let\appendixsec\appendixsection
552938494Sobrien
5530310490Scy% normally calls unnumberedseczzz:
5531310490Scy\outer\parseargdef\unnumberedsec{\unnmhead1{#1}}
5532174294Sobrien\def\unnumberedseczzz#1{%
5533174294Sobrien  \global\subsecno=0 \global\subsubsecno=0  \global\advance\secno by 1
5534174294Sobrien  \sectionheading{#1}{sec}{Ynothing}{\the\unnumberedno.\the\secno}%
553542629Sobrien}
553638494Sobrien
553742629Sobrien% Subsections.
5538310490Scy% 
5539310490Scy% normally calls numberedsubseczzz:
5540310490Scy\outer\parseargdef\numberedsubsec{\numhead2{#1}}
5541174294Sobrien\def\numberedsubseczzz#1{%
5542174294Sobrien  \global\subsubsecno=0  \global\advance\subsecno by 1
5543174294Sobrien  \sectionheading{#1}{subsec}{Ynumbered}{\the\chapno.\the\secno.\the\subsecno}%
554442629Sobrien}
554538494Sobrien
5546310490Scy% normally calls appendixsubseczzz:
5547310490Scy\outer\parseargdef\appendixsubsec{\apphead2{#1}}
5548174294Sobrien\def\appendixsubseczzz#1{%
5549174294Sobrien  \global\subsubsecno=0  \global\advance\subsecno by 1
5550174294Sobrien  \sectionheading{#1}{subsec}{Yappendix}%
5551174294Sobrien                 {\appendixletter.\the\secno.\the\subsecno}%
555242629Sobrien}
555338494Sobrien
5554310490Scy% normally calls unnumberedsubseczzz:
5555310490Scy\outer\parseargdef\unnumberedsubsec{\unnmhead2{#1}}
5556174294Sobrien\def\unnumberedsubseczzz#1{%
5557174294Sobrien  \global\subsubsecno=0  \global\advance\subsecno by 1
5558174294Sobrien  \sectionheading{#1}{subsec}{Ynothing}%
5559174294Sobrien                 {\the\unnumberedno.\the\secno.\the\subsecno}%
556042629Sobrien}
556138494Sobrien
556242629Sobrien% Subsubsections.
5563310490Scy% 
5564310490Scy% normally numberedsubsubseczzz:
5565310490Scy\outer\parseargdef\numberedsubsubsec{\numhead3{#1}}
5566174294Sobrien\def\numberedsubsubseczzz#1{%
5567174294Sobrien  \global\advance\subsubsecno by 1
5568174294Sobrien  \sectionheading{#1}{subsubsec}{Ynumbered}%
5569174294Sobrien                 {\the\chapno.\the\secno.\the\subsecno.\the\subsubsecno}%
557042629Sobrien}
557138494Sobrien
5572310490Scy% normally appendixsubsubseczzz:
5573310490Scy\outer\parseargdef\appendixsubsubsec{\apphead3{#1}}
5574174294Sobrien\def\appendixsubsubseczzz#1{%
5575174294Sobrien  \global\advance\subsubsecno by 1
5576174294Sobrien  \sectionheading{#1}{subsubsec}{Yappendix}%
5577174294Sobrien                 {\appendixletter.\the\secno.\the\subsecno.\the\subsubsecno}%
557842629Sobrien}
557938494Sobrien
5580310490Scy% normally unnumberedsubsubseczzz:
5581310490Scy\outer\parseargdef\unnumberedsubsubsec{\unnmhead3{#1}}
5582174294Sobrien\def\unnumberedsubsubseczzz#1{%
5583174294Sobrien  \global\advance\subsubsecno by 1
5584174294Sobrien  \sectionheading{#1}{subsubsec}{Ynothing}%
5585174294Sobrien                 {\the\unnumberedno.\the\secno.\the\subsecno.\the\subsubsecno}%
558642629Sobrien}
558738494Sobrien
558838494Sobrien% These macros control what the section commands do, according
558938494Sobrien% to what kind of chapter we are in (ordinary, appendix, or unnumbered).
559038494Sobrien% Define them by default for a numbered chapter.
5591174294Sobrien\let\section = \numberedsec
5592174294Sobrien\let\subsection = \numberedsubsec
5593174294Sobrien\let\subsubsection = \numberedsubsubsec
559438494Sobrien
559538494Sobrien% Define @majorheading, @heading and @subheading
559638494Sobrien
5597174294Sobrien\def\majorheading{%
5598174294Sobrien  {\advance\chapheadingskip by 10pt \chapbreak }%
5599174294Sobrien  \parsearg\chapheadingzzz
5600174294Sobrien}
560138494Sobrien
5602174294Sobrien\def\chapheading{\chapbreak \parsearg\chapheadingzzz}
5603174294Sobrien\def\chapheadingzzz#1{%
5604310490Scy  \vbox{\chapfonts \raggedtitlesettings #1\par}%
5605310490Scy  \nobreak\bigskip \nobreak
5606174294Sobrien  \suppressfirstparagraphindent
5607174294Sobrien}
560838494Sobrien
560938494Sobrien% @heading, @subheading, @subsubheading.
5610174294Sobrien\parseargdef\heading{\sectionheading{#1}{sec}{Yomitfromtoc}{}
5611174294Sobrien  \suppressfirstparagraphindent}
5612174294Sobrien\parseargdef\subheading{\sectionheading{#1}{subsec}{Yomitfromtoc}{}
5613174294Sobrien  \suppressfirstparagraphindent}
5614174294Sobrien\parseargdef\subsubheading{\sectionheading{#1}{subsubsec}{Yomitfromtoc}{}
5615174294Sobrien  \suppressfirstparagraphindent}
561638494Sobrien
561738494Sobrien% These macros generate a chapter, section, etc. heading only
561838494Sobrien% (including whitespace, linebreaking, etc. around it),
561938494Sobrien% given all the information in convenient, parsed form.
562038494Sobrien
5621310490Scy% Args are the skip and penalty (usually negative)
562238494Sobrien\def\dobreak#1#2{\par\ifdim\lastskip<#1\removelastskip\penalty#2\vskip#1\fi}
562338494Sobrien
562438494Sobrien% Parameter controlling skip before chapter headings (if needed)
562538494Sobrien\newskip\chapheadingskip
562638494Sobrien
5627310490Scy% Define plain chapter starts, and page on/off switching for it.
562838494Sobrien\def\chapbreak{\dobreak \chapheadingskip {-4000}}
562938494Sobrien\def\chappager{\par\vfill\supereject}
5630310490Scy% Because \domark is called before \chapoddpage, the filler page will
5631310490Scy% get the headings for the next chapter, which is wrong.  But we don't
5632310490Scy% care -- we just disable all headings on the filler page.
5633310490Scy\def\chapoddpage{%
5634310490Scy  \chappager
5635310490Scy  \ifodd\pageno \else
5636310490Scy    \begingroup
5637310490Scy      \headingsoff
5638310490Scy      \null
5639310490Scy      \chappager
5640310490Scy    \endgroup
5641310490Scy  \fi
5642310490Scy}
564338494Sobrien
564438494Sobrien\def\setchapternewpage #1 {\csname CHAPPAG#1\endcsname}
564538494Sobrien
564642629Sobrien\def\CHAPPAGoff{%
564738494Sobrien\global\let\contentsalignmacro = \chappager
564838494Sobrien\global\let\pchapsepmacro=\chapbreak
564938494Sobrien\global\let\pagealignmacro=\chappager}
565038494Sobrien
565142629Sobrien\def\CHAPPAGon{%
565238494Sobrien\global\let\contentsalignmacro = \chappager
565338494Sobrien\global\let\pchapsepmacro=\chappager
565438494Sobrien\global\let\pagealignmacro=\chappager
565538494Sobrien\global\def\HEADINGSon{\HEADINGSsingle}}
565638494Sobrien
5657174294Sobrien\def\CHAPPAGodd{%
565838494Sobrien\global\let\contentsalignmacro = \chapoddpage
565938494Sobrien\global\let\pchapsepmacro=\chapoddpage
566038494Sobrien\global\let\pagealignmacro=\chapoddpage
566138494Sobrien\global\def\HEADINGSon{\HEADINGSdouble}}
566238494Sobrien
566338494Sobrien\CHAPPAGon
566438494Sobrien
5665174294Sobrien% Chapter opening.
5666174294Sobrien%
5667174294Sobrien% #1 is the text, #2 is the section type (Ynumbered, Ynothing,
5668174294Sobrien% Yappendix, Yomitfromtoc), #3 the chapter number.
5669174294Sobrien%
5670174294Sobrien% To test against our argument.
5671174294Sobrien\def\Ynothingkeyword{Ynothing}
5672174294Sobrien\def\Yomitfromtockeyword{Yomitfromtoc}
5673174294Sobrien\def\Yappendixkeyword{Yappendix}
5674174294Sobrien%
5675174294Sobrien\def\chapmacro#1#2#3{%
5676310490Scy  % Insert the first mark before the heading break (see notes for \domark).
5677310490Scy  \let\prevchapterdefs=\lastchapterdefs
5678310490Scy  \let\prevsectiondefs=\lastsectiondefs
5679310490Scy  \gdef\lastsectiondefs{\gdef\thissectionname{}\gdef\thissectionnum{}%
5680310490Scy                        \gdef\thissection{}}%
5681310490Scy  %
5682310490Scy  \def\temptype{#2}%
5683310490Scy  \ifx\temptype\Ynothingkeyword
5684310490Scy    \gdef\lastchapterdefs{\gdef\thischaptername{#1}\gdef\thischapternum{}%
5685310490Scy                          \gdef\thischapter{\thischaptername}}%
5686310490Scy  \else\ifx\temptype\Yomitfromtockeyword
5687310490Scy    \gdef\lastchapterdefs{\gdef\thischaptername{#1}\gdef\thischapternum{}%
5688310490Scy                          \gdef\thischapter{}}%
5689310490Scy  \else\ifx\temptype\Yappendixkeyword
5690310490Scy    \toks0={#1}%
5691310490Scy    \xdef\lastchapterdefs{%
5692310490Scy      \gdef\noexpand\thischaptername{\the\toks0}%
5693310490Scy      \gdef\noexpand\thischapternum{\appendixletter}%
5694310490Scy      % \noexpand\putwordAppendix avoids expanding indigestible
5695310490Scy      % commands in some of the translations.
5696310490Scy      \gdef\noexpand\thischapter{\noexpand\putwordAppendix{}
5697310490Scy                                 \noexpand\thischapternum:
5698310490Scy                                 \noexpand\thischaptername}%
5699310490Scy    }%
5700310490Scy  \else
5701310490Scy    \toks0={#1}%
5702310490Scy    \xdef\lastchapterdefs{%
5703310490Scy      \gdef\noexpand\thischaptername{\the\toks0}%
5704310490Scy      \gdef\noexpand\thischapternum{\the\chapno}%
5705310490Scy      % \noexpand\putwordChapter avoids expanding indigestible
5706310490Scy      % commands in some of the translations.
5707310490Scy      \gdef\noexpand\thischapter{\noexpand\putwordChapter{}
5708310490Scy                                 \noexpand\thischapternum:
5709310490Scy                                 \noexpand\thischaptername}%
5710310490Scy    }%
5711310490Scy  \fi\fi\fi
5712310490Scy  %
5713310490Scy  % Output the mark.  Pass it through \safewhatsit, to take care of
5714310490Scy  % the preceding space.
5715310490Scy  \safewhatsit\domark
5716310490Scy  %
5717310490Scy  % Insert the chapter heading break.
571838494Sobrien  \pchapsepmacro
5719310490Scy  %
5720310490Scy  % Now the second mark, after the heading break.  No break points
5721310490Scy  % between here and the heading.
5722310490Scy  \let\prevchapterdefs=\lastchapterdefs
5723310490Scy  \let\prevsectiondefs=\lastsectiondefs
5724310490Scy  \domark
5725310490Scy  %
572638494Sobrien  {%
5727310490Scy    \chapfonts \rmisbold
5728174294Sobrien    %
5729310490Scy    % Have to define \lastsection before calling \donoderef, because the
5730174294Sobrien    % xref code eventually uses it.  On the other hand, it has to be called
5731174294Sobrien    % after \pchapsepmacro, or the headline will change too soon.
5732310490Scy    \gdef\lastsection{#1}%
5733174294Sobrien    %
5734174294Sobrien    % Only insert the separating space if we have a chapter/appendix
5735174294Sobrien    % number, and don't print the unnumbered ``number''.
5736174294Sobrien    \ifx\temptype\Ynothingkeyword
5737174294Sobrien      \setbox0 = \hbox{}%
5738174294Sobrien      \def\toctype{unnchap}%
5739174294Sobrien    \else\ifx\temptype\Yomitfromtockeyword
5740174294Sobrien      \setbox0 = \hbox{}% contents like unnumbered, but no toc entry
5741174294Sobrien      \def\toctype{omit}%
5742174294Sobrien    \else\ifx\temptype\Yappendixkeyword
5743174294Sobrien      \setbox0 = \hbox{\putwordAppendix{} #3\enspace}%
5744174294Sobrien      \def\toctype{app}%
5745174294Sobrien    \else
5746174294Sobrien      \setbox0 = \hbox{#3\enspace}%
5747174294Sobrien      \def\toctype{numchap}%
5748174294Sobrien    \fi\fi\fi
5749174294Sobrien    %
5750174294Sobrien    % Write the toc entry for this chapter.  Must come before the
5751174294Sobrien    % \donoderef, because we include the current node name in the toc
5752174294Sobrien    % entry, and \donoderef resets it to empty.
5753174294Sobrien    \writetocentry{\toctype}{#1}{#3}%
5754174294Sobrien    %
5755174294Sobrien    % For pdftex, we have to write out the node definition (aka, make
5756174294Sobrien    % the pdfdest) after any page break, but before the actual text has
5757174294Sobrien    % been typeset.  If the destination for the pdf outline is after the
5758174294Sobrien    % text, then jumping from the outline may wind up with the text not
5759174294Sobrien    % being visible, for instance under high magnification.
5760174294Sobrien    \donoderef{#2}%
5761174294Sobrien    %
5762174294Sobrien    % Typeset the actual heading.
5763310490Scy    \nobreak % Avoid page breaks at the interline glue.
5764310490Scy    \vbox{\raggedtitlesettings \hangindent=\wd0 \centerparametersmaybe
576538494Sobrien          \unhbox0 #1\par}%
576638494Sobrien  }%
576738494Sobrien  \nobreak\bigskip % no page break after a chapter title
576838494Sobrien  \nobreak
576938494Sobrien}
577038494Sobrien
577138494Sobrien% @centerchap -- centered and unnumbered.
577238494Sobrien\let\centerparametersmaybe = \relax
5773174294Sobrien\def\centerparameters{%
5774174294Sobrien  \advance\rightskip by 3\rightskip
5775174294Sobrien  \leftskip = \rightskip
5776174294Sobrien  \parfillskip = 0pt
5777174294Sobrien}
577838494Sobrien
577938494Sobrien
5780174294Sobrien% I don't think this chapter style is supported any more, so I'm not
5781174294Sobrien% updating it with the new noderef stuff.  We'll see.  --karl, 11aug03.
5782174294Sobrien%
5783174294Sobrien\def\setchapterstyle #1 {\csname CHAPF#1\endcsname}
5784174294Sobrien%
578538494Sobrien\def\unnchfopen #1{%
5786310490Scy  \chapoddpage
5787310490Scy  \vbox{\chapfonts \raggedtitlesettings #1\par}%
5788310490Scy  \nobreak\bigskip\nobreak
578938494Sobrien}
579038494Sobrien\def\chfopen #1#2{\chapoddpage {\chapfonts
579138494Sobrien\vbox to 3in{\vfil \hbox to\hsize{\hfil #2} \hbox to\hsize{\hfil #1} \vfil}}%
579238494Sobrien\par\penalty 5000 %
579338494Sobrien}
579438494Sobrien\def\centerchfopen #1{%
5795310490Scy  \chapoddpage
5796310490Scy  \vbox{\chapfonts \raggedtitlesettings \hfill #1\hfill}%
5797310490Scy  \nobreak\bigskip \nobreak
579838494Sobrien}
5799174294Sobrien\def\CHAPFopen{%
5800174294Sobrien  \global\let\chapmacro=\chfopen
5801174294Sobrien  \global\let\centerchapmacro=\centerchfopen}
580238494Sobrien
580338494Sobrien
5804174294Sobrien% Section titles.  These macros combine the section number parts and
5805174294Sobrien% call the generic \sectionheading to do the printing.
5806174294Sobrien%
580738494Sobrien\newskip\secheadingskip
5808174294Sobrien\def\secheadingbreak{\dobreak \secheadingskip{-1000}}
580938494Sobrien
581038494Sobrien% Subsection titles.
5811174294Sobrien\newskip\subsecheadingskip
5812174294Sobrien\def\subsecheadingbreak{\dobreak \subsecheadingskip{-500}}
581338494Sobrien
581438494Sobrien% Subsubsection titles.
5815174294Sobrien\def\subsubsecheadingskip{\subsecheadingskip}
5816174294Sobrien\def\subsubsecheadingbreak{\subsecheadingbreak}
581738494Sobrien
581838494Sobrien
5819174294Sobrien% Print any size, any type, section title.
582038494Sobrien%
5821174294Sobrien% #1 is the text, #2 is the section level (sec/subsec/subsubsec), #3 is
5822174294Sobrien% the section type for xrefs (Ynumbered, Ynothing, Yappendix), #4 is the
5823174294Sobrien% section number.
5824174294Sobrien%
5825310490Scy\def\seckeyword{sec}
5826310490Scy%
5827174294Sobrien\def\sectionheading#1#2#3#4{%
582838494Sobrien  {%
5829310490Scy    \checkenv{}% should not be in an environment.
5830310490Scy    %
583138494Sobrien    % Switch to the right set of fonts.
5832310490Scy    \csname #2fonts\endcsname \rmisbold
583338494Sobrien    %
5834310490Scy    \def\sectionlevel{#2}%
5835310490Scy    \def\temptype{#3}%
5836310490Scy    %
5837310490Scy    % Insert first mark before the heading break (see notes for \domark).
5838310490Scy    \let\prevsectiondefs=\lastsectiondefs
5839310490Scy    \ifx\temptype\Ynothingkeyword
5840310490Scy      \ifx\sectionlevel\seckeyword
5841310490Scy        \gdef\lastsectiondefs{\gdef\thissectionname{#1}\gdef\thissectionnum{}%
5842310490Scy                              \gdef\thissection{\thissectionname}}%
5843310490Scy      \fi
5844310490Scy    \else\ifx\temptype\Yomitfromtockeyword
5845310490Scy      % Don't redefine \thissection.
5846310490Scy    \else\ifx\temptype\Yappendixkeyword
5847310490Scy      \ifx\sectionlevel\seckeyword
5848310490Scy        \toks0={#1}%
5849310490Scy        \xdef\lastsectiondefs{%
5850310490Scy          \gdef\noexpand\thissectionname{\the\toks0}%
5851310490Scy          \gdef\noexpand\thissectionnum{#4}%
5852310490Scy          % \noexpand\putwordSection avoids expanding indigestible
5853310490Scy          % commands in some of the translations.
5854310490Scy          \gdef\noexpand\thissection{\noexpand\putwordSection{}
5855310490Scy                                     \noexpand\thissectionnum:
5856310490Scy                                     \noexpand\thissectionname}%
5857310490Scy        }%
5858310490Scy      \fi
5859310490Scy    \else
5860310490Scy      \ifx\sectionlevel\seckeyword
5861310490Scy        \toks0={#1}%
5862310490Scy        \xdef\lastsectiondefs{%
5863310490Scy          \gdef\noexpand\thissectionname{\the\toks0}%
5864310490Scy          \gdef\noexpand\thissectionnum{#4}%
5865310490Scy          % \noexpand\putwordSection avoids expanding indigestible
5866310490Scy          % commands in some of the translations.
5867310490Scy          \gdef\noexpand\thissection{\noexpand\putwordSection{}
5868310490Scy                                     \noexpand\thissectionnum:
5869310490Scy                                     \noexpand\thissectionname}%
5870310490Scy        }%
5871310490Scy      \fi
5872310490Scy    \fi\fi\fi
5873310490Scy    %
5874310490Scy    % Go into vertical mode.  Usually we'll already be there, but we
5875310490Scy    % don't want the following whatsit to end up in a preceding paragraph
5876310490Scy    % if the document didn't happen to have a blank line.
5877310490Scy    \par
5878310490Scy    %
5879310490Scy    % Output the mark.  Pass it through \safewhatsit, to take care of
5880310490Scy    % the preceding space.
5881310490Scy    \safewhatsit\domark
5882310490Scy    %
5883174294Sobrien    % Insert space above the heading.
5884174294Sobrien    \csname #2headingbreak\endcsname
588538494Sobrien    %
5886310490Scy    % Now the second mark, after the heading break.  No break points
5887310490Scy    % between here and the heading.
5888310490Scy    \let\prevsectiondefs=\lastsectiondefs
5889310490Scy    \domark
5890310490Scy    %
5891174294Sobrien    % Only insert the space after the number if we have a section number.
5892174294Sobrien    \ifx\temptype\Ynothingkeyword
5893174294Sobrien      \setbox0 = \hbox{}%
5894174294Sobrien      \def\toctype{unn}%
5895310490Scy      \gdef\lastsection{#1}%
5896174294Sobrien    \else\ifx\temptype\Yomitfromtockeyword
5897174294Sobrien      % for @headings -- no section number, don't include in toc,
5898310490Scy      % and don't redefine \lastsection.
5899174294Sobrien      \setbox0 = \hbox{}%
5900174294Sobrien      \def\toctype{omit}%
5901174294Sobrien      \let\sectionlevel=\empty
5902174294Sobrien    \else\ifx\temptype\Yappendixkeyword
5903174294Sobrien      \setbox0 = \hbox{#4\enspace}%
5904174294Sobrien      \def\toctype{app}%
5905310490Scy      \gdef\lastsection{#1}%
5906174294Sobrien    \else
5907174294Sobrien      \setbox0 = \hbox{#4\enspace}%
5908174294Sobrien      \def\toctype{num}%
5909310490Scy      \gdef\lastsection{#1}%
5910174294Sobrien    \fi\fi\fi
5911174294Sobrien    %
5912310490Scy    % Write the toc entry (before \donoderef).  See comments in \chapmacro.
5913174294Sobrien    \writetocentry{\toctype\sectionlevel}{#1}{#4}%
5914174294Sobrien    %
5915174294Sobrien    % Write the node reference (= pdf destination for pdftex).
5916310490Scy    % Again, see comments in \chapmacro.
5917174294Sobrien    \donoderef{#3}%
5918174294Sobrien    %
5919310490Scy    % Interline glue will be inserted when the vbox is completed.
5920310490Scy    % That glue will be a valid breakpoint for the page, since it'll be
5921310490Scy    % preceded by a whatsit (usually from the \donoderef, or from the
5922310490Scy    % \writetocentry if there was no node).  We don't want to allow that
5923310490Scy    % break, since then the whatsits could end up on page n while the
5924310490Scy    % section is on page n+1, thus toc/etc. are wrong.  Debian bug 276000.
5925310490Scy    \nobreak
5926310490Scy    %
5927174294Sobrien    % Output the actual section heading.
5928310490Scy    \vbox{\hyphenpenalty=10000 \tolerance=5000 \parindent=0pt \ptexraggedright
5929174294Sobrien          \hangindent=\wd0  % zero if no section number
5930174294Sobrien          \unhbox0 #1}%
593138494Sobrien  }%
5932174294Sobrien  % Add extra space after the heading -- half of whatever came above it.
5933174294Sobrien  % Don't allow stretch, though.
5934174294Sobrien  \kern .5 \csname #2headingskip\endcsname
5935174294Sobrien  %
5936174294Sobrien  % Do not let the kern be a potential breakpoint, as it would be if it
5937174294Sobrien  % was followed by glue.
5938174294Sobrien  \nobreak
5939174294Sobrien  %
5940174294Sobrien  % We'll almost certainly start a paragraph next, so don't let that
5941174294Sobrien  % glue accumulate.  (Not a breakpoint because it's preceded by a
5942310490Scy  % discardable item.)  However, when a paragraph is not started next
5943310490Scy  % (\startdefun, \cartouche, \center, etc.), this needs to be wiped out
5944310490Scy  % or the negative glue will cause weirdly wrong output, typically
5945310490Scy  % obscuring the section heading with something else.
5946174294Sobrien  \vskip-\parskip
5947310490Scy  %
5948310490Scy  % This is so the last item on the main vertical list is a known
5949310490Scy  % \penalty > 10000, so \startdefun, etc., can recognize the situation
5950310490Scy  % and do the needful.
5951174294Sobrien  \penalty 10001
595238494Sobrien}
595338494Sobrien
595438494Sobrien
595542629Sobrien\message{toc,}
595682794Sobrien% Table of contents.
595742629Sobrien\newwrite\tocfile
595838494Sobrien
595942629Sobrien% Write an entry to the toc file, opening it if necessary.
5960174294Sobrien% Called from @chapter, etc.
596182794Sobrien%
5962174294Sobrien% Example usage: \writetocentry{sec}{Section Name}{\the\chapno.\the\secno}
5963174294Sobrien% We append the current node name (if any) and page number as additional
5964174294Sobrien% arguments for the \{chap,sec,...}entry macros which will eventually
5965174294Sobrien% read this.  The node name is used in the pdf outlines as the
5966174294Sobrien% destination to jump to.
596782794Sobrien%
5968174294Sobrien% We open the .toc file for writing here instead of at @setfilename (or
5969174294Sobrien% any other fixed time) so that @contents can be anywhere in the document.
5970174294Sobrien% But if #1 is `omit', then we don't do anything.  This is used for the
5971174294Sobrien% table of contents chapter openings themselves.
5972174294Sobrien%
597342629Sobrien\newif\iftocfileopened
5974174294Sobrien\def\omitkeyword{omit}%
5975174294Sobrien%
5976174294Sobrien\def\writetocentry#1#2#3{%
5977174294Sobrien  \edef\writetoctype{#1}%
5978174294Sobrien  \ifx\writetoctype\omitkeyword \else
5979174294Sobrien    \iftocfileopened\else
5980174294Sobrien      \immediate\openout\tocfile = \jobname.toc
5981174294Sobrien      \global\tocfileopenedtrue
5982174294Sobrien    \fi
5983174294Sobrien    %
5984174294Sobrien    \iflinks
5985310490Scy      {\atdummies
5986310490Scy       \edef\temp{%
5987310490Scy         \write\tocfile{@#1entry{#2}{#3}{\lastnode}{\noexpand\folio}}}%
5988310490Scy       \temp
5989310490Scy      }%
5990174294Sobrien    \fi
599142629Sobrien  \fi
5992119679Smbr  %
5993174294Sobrien  % Tell \shipout to create a pdf destination on each page, if we're
5994174294Sobrien  % writing pdf.  These are used in the table of contents.  We can't
5995174294Sobrien  % just write one on every page because the title pages are numbered
5996174294Sobrien  % 1 and 2 (the page numbers aren't printed), and so are the first
5997174294Sobrien  % two pages of the document.  Thus, we'd have two destinations named
5998174294Sobrien  % `1', and two named `2'.
5999174294Sobrien  \ifpdf \global\pdfmakepagedesttrue \fi
600042629Sobrien}
600142629Sobrien
6002310490Scy
6003310490Scy% These characters do not print properly in the Computer Modern roman
6004310490Scy% fonts, so we must take special care.  This is more or less redundant
6005310490Scy% with the Texinfo input format setup at the end of this file.
6006310490Scy%
6007310490Scy\def\activecatcodes{%
6008310490Scy  \catcode`\"=\active
6009310490Scy  \catcode`\$=\active
6010310490Scy  \catcode`\<=\active
6011310490Scy  \catcode`\>=\active
6012310490Scy  \catcode`\\=\active
6013310490Scy  \catcode`\^=\active
6014310490Scy  \catcode`\_=\active
6015310490Scy  \catcode`\|=\active
6016310490Scy  \catcode`\~=\active
6017310490Scy}
6018310490Scy
6019310490Scy
6020310490Scy% Read the toc file, which is essentially Texinfo input.
6021310490Scy\def\readtocfile{%
6022310490Scy  \setupdatafile
6023310490Scy  \activecatcodes
6024310490Scy  \input \tocreadfilename
6025310490Scy}
6026310490Scy
602738494Sobrien\newskip\contentsrightmargin \contentsrightmargin=1in
602842629Sobrien\newcount\savepageno
602942629Sobrien\newcount\lastnegativepageno \lastnegativepageno = -1
603042629Sobrien
6031174294Sobrien% Prepare to read what we've written to \tocfile.
603282794Sobrien%
603338494Sobrien\def\startcontents#1{%
6034174294Sobrien  % If @setchapternewpage on, and @headings double, the contents should
6035174294Sobrien  % start on an odd page, unlike chapters.  Thus, we maintain
6036174294Sobrien  % \contentsalignmacro in parallel with \pagealignmacro.
6037174294Sobrien  % From: Torbjorn Granlund <tege@matematik.su.se>
6038174294Sobrien  \contentsalignmacro
6039174294Sobrien  \immediate\closeout\tocfile
6040174294Sobrien  %
6041174294Sobrien  % Don't need to put `Contents' or `Short Contents' in the headline.
6042174294Sobrien  % It is abundantly clear what they are.
6043174294Sobrien  \chapmacro{#1}{Yomitfromtoc}{}%
6044174294Sobrien  %
6045174294Sobrien  \savepageno = \pageno
6046174294Sobrien  \begingroup                  % Set up to handle contents files properly.
6047310490Scy    \raggedbottom              % Worry more about breakpoints than the bottom.
6048174294Sobrien    \advance\hsize by -\contentsrightmargin % Don't use the full line length.
6049174294Sobrien    %
6050174294Sobrien    % Roman numerals for page numbers.
6051174294Sobrien    \ifnum \pageno>0 \global\pageno = \lastnegativepageno \fi
605238494Sobrien}
605338494Sobrien
6054310490Scy% redefined for the two-volume lispref.  We always output on
6055310490Scy% \jobname.toc even if this is redefined.
6056310490Scy%
6057310490Scy\def\tocreadfilename{\jobname.toc}
605838494Sobrien
605938494Sobrien% Normal (long) toc.
6060310490Scy%
606142629Sobrien\def\contents{%
6062174294Sobrien  \startcontents{\putwordTOC}%
6063310490Scy    \openin 1 \tocreadfilename\space
6064174294Sobrien    \ifeof 1 \else
6065310490Scy      \readtocfile
6066174294Sobrien    \fi
6067174294Sobrien    \vfill \eject
6068174294Sobrien    \contentsalignmacro % in case @setchapternewpage odd is in effect
6069174294Sobrien    \ifeof 1 \else
6070174294Sobrien      \pdfmakeoutlines
6071174294Sobrien    \fi
6072174294Sobrien    \closein 1
6073174294Sobrien  \endgroup
6074174294Sobrien  \lastnegativepageno = \pageno
6075174294Sobrien  \global\pageno = \savepageno
607638494Sobrien}
607738494Sobrien
607838494Sobrien% And just the chapters.
607942629Sobrien\def\summarycontents{%
6080174294Sobrien  \startcontents{\putwordShortTOC}%
6081174294Sobrien    %
6082310490Scy    \let\partentry = \shortpartentry
6083174294Sobrien    \let\numchapentry = \shortchapentry
6084174294Sobrien    \let\appentry = \shortchapentry
6085174294Sobrien    \let\unnchapentry = \shortunnchapentry
6086174294Sobrien    % We want a true roman here for the page numbers.
6087174294Sobrien    \secfonts
6088174294Sobrien    \let\rm=\shortcontrm \let\bf=\shortcontbf
6089174294Sobrien    \let\sl=\shortcontsl \let\tt=\shortconttt
6090174294Sobrien    \rm
6091174294Sobrien    \hyphenpenalty = 10000
6092174294Sobrien    \advance\baselineskip by 1pt % Open it up a little.
6093174294Sobrien    \def\numsecentry##1##2##3##4{}
6094174294Sobrien    \let\appsecentry = \numsecentry
6095174294Sobrien    \let\unnsecentry = \numsecentry
6096174294Sobrien    \let\numsubsecentry = \numsecentry
6097174294Sobrien    \let\appsubsecentry = \numsecentry
6098174294Sobrien    \let\unnsubsecentry = \numsecentry
6099174294Sobrien    \let\numsubsubsecentry = \numsecentry
6100174294Sobrien    \let\appsubsubsecentry = \numsecentry
6101174294Sobrien    \let\unnsubsubsecentry = \numsecentry
6102310490Scy    \openin 1 \tocreadfilename\space
6103174294Sobrien    \ifeof 1 \else
6104310490Scy      \readtocfile
6105174294Sobrien    \fi
6106174294Sobrien    \closein 1
6107174294Sobrien    \vfill \eject
6108174294Sobrien    \contentsalignmacro % in case @setchapternewpage odd is in effect
6109174294Sobrien  \endgroup
6110174294Sobrien  \lastnegativepageno = \pageno
6111174294Sobrien  \global\pageno = \savepageno
611238494Sobrien}
611338494Sobrien\let\shortcontents = \summarycontents
611438494Sobrien
6115174294Sobrien% Typeset the label for a chapter or appendix for the short contents.
6116174294Sobrien% The arg is, e.g., `A' for an appendix, or `3' for a chapter.
6117174294Sobrien%
6118174294Sobrien\def\shortchaplabel#1{%
6119174294Sobrien  % This space should be enough, since a single number is .5em, and the
6120174294Sobrien  % widest letter (M) is 1em, at least in the Computer Modern fonts.
6121174294Sobrien  % But use \hss just in case.
6122174294Sobrien  % (This space doesn't include the extra space that gets added after
6123174294Sobrien  % the label; that gets put in by \shortchapentry above.)
6124174294Sobrien  %
6125174294Sobrien  % We'd like to right-justify chapter numbers, but that looks strange
6126174294Sobrien  % with appendix letters.  And right-justifying numbers and
6127174294Sobrien  % left-justifying letters looks strange when there is less than 10
6128174294Sobrien  % chapters.  Have to read the whole toc once to know how many chapters
6129174294Sobrien  % there are before deciding ...
6130174294Sobrien  \hbox to 1em{#1\hss}%
6131174294Sobrien}
613282794Sobrien
613338494Sobrien% These macros generate individual entries in the table of contents.
613438494Sobrien% The first argument is the chapter or section name.
613538494Sobrien% The last argument is the page number.
613638494Sobrien% The arguments in between are the chapter number, section number, ...
613738494Sobrien
6138310490Scy% Parts, in the main contents.  Replace the part number, which doesn't
6139310490Scy% exist, with an empty box.  Let's hope all the numbers have the same width.
6140310490Scy% Also ignore the page number, which is conventionally not printed.
6141310490Scy\def\numeralbox{\setbox0=\hbox{8}\hbox to \wd0{\hfil}}
6142310490Scy\def\partentry#1#2#3#4{\dochapentry{\numeralbox\labelspace#1}{}}
6143310490Scy%
6144310490Scy% Parts, in the short toc.
6145310490Scy\def\shortpartentry#1#2#3#4{%
6146310490Scy  \penalty-300
6147310490Scy  \vskip.5\baselineskip plus.15\baselineskip minus.1\baselineskip
6148310490Scy  \shortchapentry{{\bf #1}}{\numeralbox}{}{}%
6149310490Scy}
6150310490Scy
6151119679Smbr% Chapters, in the main contents.
6152174294Sobrien\def\numchapentry#1#2#3#4{\dochapentry{#2\labelspace#1}{#4}}
6153119679Smbr%
6154119679Smbr% Chapters, in the short toc.
6155119679Smbr% See comments in \dochapentry re vbox and related settings.
6156174294Sobrien\def\shortchapentry#1#2#3#4{%
6157174294Sobrien  \tocentry{\shortchaplabel{#2}\labelspace #1}{\doshortpageno\bgroup#4\egroup}%
615838494Sobrien}
615938494Sobrien
6160119679Smbr% Appendices, in the main contents.
6161174294Sobrien% Need the word Appendix, and a fixed-size box.
6162119679Smbr%
6163174294Sobrien\def\appendixbox#1{%
6164174294Sobrien  % We use M since it's probably the widest letter.
6165174294Sobrien  \setbox0 = \hbox{\putwordAppendix{} M}%
6166174294Sobrien  \hbox to \wd0{\putwordAppendix{} #1\hss}}
616782794Sobrien%
6168174294Sobrien\def\appentry#1#2#3#4{\dochapentry{\appendixbox{#2}\labelspace#1}{#4}}
616938494Sobrien
6170119679Smbr% Unnumbered chapters.
6171174294Sobrien\def\unnchapentry#1#2#3#4{\dochapentry{#1}{#4}}
6172174294Sobrien\def\shortunnchapentry#1#2#3#4{\tocentry{#1}{\doshortpageno\bgroup#4\egroup}}
617338494Sobrien
617438494Sobrien% Sections.
6175174294Sobrien\def\numsecentry#1#2#3#4{\dosecentry{#2\labelspace#1}{#4}}
6176174294Sobrien\let\appsecentry=\numsecentry
6177174294Sobrien\def\unnsecentry#1#2#3#4{\dosecentry{#1}{#4}}
617838494Sobrien
617938494Sobrien% Subsections.
6180174294Sobrien\def\numsubsecentry#1#2#3#4{\dosubsecentry{#2\labelspace#1}{#4}}
6181174294Sobrien\let\appsubsecentry=\numsubsecentry
6182174294Sobrien\def\unnsubsecentry#1#2#3#4{\dosubsecentry{#1}{#4}}
618338494Sobrien
618438494Sobrien% And subsubsections.
6185174294Sobrien\def\numsubsubsecentry#1#2#3#4{\dosubsubsecentry{#2\labelspace#1}{#4}}
6186174294Sobrien\let\appsubsubsecentry=\numsubsubsecentry
6187174294Sobrien\def\unnsubsubsecentry#1#2#3#4{\dosubsubsecentry{#1}{#4}}
618838494Sobrien
618938494Sobrien% This parameter controls the indentation of the various levels.
6190174294Sobrien% Same as \defaultparindent.
6191174294Sobrien\newdimen\tocindent \tocindent = 15pt
619238494Sobrien
619338494Sobrien% Now for the actual typesetting. In all these, #1 is the text and #2 is the
619438494Sobrien% page number.
619538494Sobrien%
619638494Sobrien% If the toc has to be broken over pages, we want it to be at chapters
619738494Sobrien% if at all possible; hence the \penalty.
619838494Sobrien\def\dochapentry#1#2{%
619938494Sobrien   \penalty-300 \vskip1\baselineskip plus.33\baselineskip minus.25\baselineskip
620038494Sobrien   \begingroup
620138494Sobrien     \chapentryfonts
620282794Sobrien     \tocentry{#1}{\dopageno\bgroup#2\egroup}%
620338494Sobrien   \endgroup
620438494Sobrien   \nobreak\vskip .25\baselineskip plus.1\baselineskip
620538494Sobrien}
620638494Sobrien
620738494Sobrien\def\dosecentry#1#2{\begingroup
620838494Sobrien  \secentryfonts \leftskip=\tocindent
620982794Sobrien  \tocentry{#1}{\dopageno\bgroup#2\egroup}%
621038494Sobrien\endgroup}
621138494Sobrien
621238494Sobrien\def\dosubsecentry#1#2{\begingroup
621338494Sobrien  \subsecentryfonts \leftskip=2\tocindent
621482794Sobrien  \tocentry{#1}{\dopageno\bgroup#2\egroup}%
621538494Sobrien\endgroup}
621638494Sobrien
621738494Sobrien\def\dosubsubsecentry#1#2{\begingroup
621838494Sobrien  \subsubsecentryfonts \leftskip=3\tocindent
621982794Sobrien  \tocentry{#1}{\dopageno\bgroup#2\egroup}%
622038494Sobrien\endgroup}
622138494Sobrien
6222174294Sobrien% We use the same \entry macro as for the index entries.
6223174294Sobrien\let\tocentry = \entry
622438494Sobrien
622538494Sobrien% Space between chapter (or whatever) number and the title.
622638494Sobrien\def\labelspace{\hskip1em \relax}
622738494Sobrien
622838494Sobrien\def\dopageno#1{{\rm #1}}
622938494Sobrien\def\doshortpageno#1{{\rm #1}}
623038494Sobrien
623138494Sobrien\def\chapentryfonts{\secfonts \rm}
623238494Sobrien\def\secentryfonts{\textfonts}
6233174294Sobrien\def\subsecentryfonts{\textfonts}
6234174294Sobrien\def\subsubsecentryfonts{\textfonts}
623538494Sobrien
623638494Sobrien
623738494Sobrien\message{environments,}
623882794Sobrien% @foo ... @end foo.
623938494Sobrien
6240310490Scy% @tex ... @end tex    escapes into raw TeX temporarily.
624138494Sobrien% One exception: @ is still an escape character, so that @end tex works.
6242310490Scy% But \@ or @@ will get a plain @ character.
624338494Sobrien
6244174294Sobrien\envdef\tex{%
6245310490Scy  \setupmarkupstyle{tex}%
624642629Sobrien  \catcode `\\=0 \catcode `\{=1 \catcode `\}=2
624742629Sobrien  \catcode `\$=3 \catcode `\&=4 \catcode `\#=6
6248174294Sobrien  \catcode `\^=7 \catcode `\_=8 \catcode `\~=\active \let~=\tie
624942629Sobrien  \catcode `\%=14
6250174294Sobrien  \catcode `\+=\other
6251174294Sobrien  \catcode `\"=\other
6252174294Sobrien  \catcode `\|=\other
6253174294Sobrien  \catcode `\<=\other
6254174294Sobrien  \catcode `\>=\other
6255310490Scy  \catcode`\`=\other
6256310490Scy  \catcode`\'=\other
625742629Sobrien  \escapechar=`\\
625842629Sobrien  %
6259310490Scy  % ' is active in math mode (mathcode"8000).  So reset it, and all our
6260310490Scy  % other math active characters (just in case), to plain's definitions.
6261310490Scy  \mathactive
6262310490Scy  %
626342629Sobrien  \let\b=\ptexb
626442629Sobrien  \let\bullet=\ptexbullet
626542629Sobrien  \let\c=\ptexc
626642629Sobrien  \let\,=\ptexcomma
626742629Sobrien  \let\.=\ptexdot
626842629Sobrien  \let\dots=\ptexdots
626942629Sobrien  \let\equiv=\ptexequiv
627042629Sobrien  \let\!=\ptexexclam
627142629Sobrien  \let\i=\ptexi
6272174294Sobrien  \let\indent=\ptexindent
6273174294Sobrien  \let\noindent=\ptexnoindent
627442629Sobrien  \let\{=\ptexlbrace
627542629Sobrien  \let\+=\tabalign
627642629Sobrien  \let\}=\ptexrbrace
6277174294Sobrien  \let\/=\ptexslash
627842629Sobrien  \let\*=\ptexstar
627942629Sobrien  \let\t=\ptext
6280310490Scy  \expandafter \let\csname top\endcsname=\ptextop  % outer
6281310490Scy  \let\frenchspacing=\plainfrenchspacing
628242629Sobrien  %
628342629Sobrien  \def\endldots{\mathinner{\ldots\ldots\ldots\ldots}}%
628442629Sobrien  \def\enddots{\relax\ifmmode\endldots\else$\mathsurround=0pt \endldots\,$\fi}%
628542629Sobrien  \def\@{@}%
6286174294Sobrien}
6287174294Sobrien% There is no need to define \Etex.
628838494Sobrien
6289119679Smbr% Define @lisp ... @end lisp.
6290174294Sobrien% @lisp environment forms a group so it can rebind things,
6291119679Smbr% including the definition of @end lisp (which normally is erroneous).
629238494Sobrien
629338494Sobrien% Amount to narrow the margins by for @lisp.
629438494Sobrien\newskip\lispnarrowing \lispnarrowing=0.4in
629538494Sobrien
629638494Sobrien% This is the definition that ^^M gets inside @lisp, @example, and other
629738494Sobrien% such environments.  \null is better than a space, since it doesn't
629838494Sobrien% have any width.
629938494Sobrien\def\lisppar{\null\endgraf}
630038494Sobrien
630138494Sobrien% This space is always present above and below environments.
630238494Sobrien\newskip\envskipamount \envskipamount = 0pt
630338494Sobrien
630438494Sobrien% Make spacing and below environment symmetrical.  We use \parskip here
630538494Sobrien% to help in doing that, since in @example-like environments \parskip
630638494Sobrien% is reset to zero; thus the \afterenvbreak inserts no space -- but the
6307174294Sobrien% start of the next paragraph will insert \parskip.
630838494Sobrien%
630982794Sobrien\def\aboveenvbreak{{%
6310174294Sobrien  % =10000 instead of <10000 because of a special case in \itemzzz and
6311174294Sobrien  % \sectionheading, q.v.
6312174294Sobrien  \ifnum \lastpenalty=10000 \else
631382794Sobrien    \advance\envskipamount by \parskip
631482794Sobrien    \endgraf
631582794Sobrien    \ifdim\lastskip<\envskipamount
631682794Sobrien      \removelastskip
6317174294Sobrien      % it's not a good place to break if the last penalty was \nobreak
6318174294Sobrien      % or better ...
6319174294Sobrien      \ifnum\lastpenalty<10000 \penalty-50 \fi
632082794Sobrien      \vskip\envskipamount
632182794Sobrien    \fi
632282794Sobrien  \fi
632382794Sobrien}}
632438494Sobrien
632538494Sobrien\let\afterenvbreak = \aboveenvbreak
632638494Sobrien
6327310490Scy% \nonarrowing is a flag.  If "set", @lisp etc don't narrow margins; it will
6328310490Scy% also clear it, so that its embedded environments do the narrowing again.
632938494Sobrien\let\nonarrowing=\relax
633038494Sobrien
633142629Sobrien% @cartouche ... @end cartouche: draw rectangle w/rounded corners around
633242629Sobrien% environment contents.
633338494Sobrien\font\circle=lcircle10
633438494Sobrien\newdimen\circthick
633538494Sobrien\newdimen\cartouter\newdimen\cartinner
633638494Sobrien\newskip\normbskip\newskip\normpskip\newskip\normlskip
633738494Sobrien\circthick=\fontdimen8\circle
633838494Sobrien%
633938494Sobrien\def\ctl{{\circle\char'013\hskip -6pt}}% 6pt from pl file: 1/2charwidth
634038494Sobrien\def\ctr{{\hskip 6pt\circle\char'010}}
634138494Sobrien\def\cbl{{\circle\char'012\hskip -6pt}}
634238494Sobrien\def\cbr{{\hskip 6pt\circle\char'011}}
634338494Sobrien\def\carttop{\hbox to \cartouter{\hskip\lskip
634438494Sobrien        \ctl\leaders\hrule height\circthick\hfil\ctr
634538494Sobrien        \hskip\rskip}}
634638494Sobrien\def\cartbot{\hbox to \cartouter{\hskip\lskip
634738494Sobrien        \cbl\leaders\hrule height\circthick\hfil\cbr
634838494Sobrien        \hskip\rskip}}
634938494Sobrien%
635038494Sobrien\newskip\lskip\newskip\rskip
635138494Sobrien
6352174294Sobrien\envdef\cartouche{%
6353174294Sobrien  \ifhmode\par\fi  % can't be in the midst of a paragraph.
6354174294Sobrien  \startsavinginserts
6355174294Sobrien  \lskip=\leftskip \rskip=\rightskip
6356174294Sobrien  \leftskip=0pt\rightskip=0pt % we want these *outside*.
6357174294Sobrien  \cartinner=\hsize \advance\cartinner by-\lskip
6358174294Sobrien  \advance\cartinner by-\rskip
6359174294Sobrien  \cartouter=\hsize
6360174294Sobrien  \advance\cartouter by 18.4pt	% allow for 3pt kerns on either
6361174294Sobrien				% side, and for 6pt waste from
6362174294Sobrien				% each corner char, and rule thickness
6363174294Sobrien  \normbskip=\baselineskip \normpskip=\parskip \normlskip=\lineskip
6364174294Sobrien  % Flag to tell @lisp, etc., not to narrow margin.
6365310490Scy  \let\nonarrowing = t%
6366310490Scy  %
6367310490Scy  % If this cartouche directly follows a sectioning command, we need the
6368310490Scy  % \parskip glue (backspaced over by default) or the cartouche can
6369310490Scy  % collide with the section heading.
6370310490Scy  \ifnum\lastpenalty>10000 \vskip\parskip \penalty\lastpenalty \fi
6371310490Scy  %
6372174294Sobrien  \vbox\bgroup
6373174294Sobrien      \baselineskip=0pt\parskip=0pt\lineskip=0pt
6374174294Sobrien      \carttop
6375174294Sobrien      \hbox\bgroup
6376174294Sobrien	  \hskip\lskip
6377174294Sobrien	  \vrule\kern3pt
6378174294Sobrien	  \vbox\bgroup
6379174294Sobrien	      \kern3pt
6380174294Sobrien	      \hsize=\cartinner
6381174294Sobrien	      \baselineskip=\normbskip
6382174294Sobrien	      \lineskip=\normlskip
6383174294Sobrien	      \parskip=\normpskip
6384174294Sobrien	      \vskip -\parskip
6385310490Scy	      \comment % For explanation, see the end of def\group.
6386174294Sobrien}
638738494Sobrien\def\Ecartouche{%
6388174294Sobrien              \ifhmode\par\fi
6389174294Sobrien	      \kern3pt
6390174294Sobrien	  \egroup
6391174294Sobrien	  \kern3pt\vrule
6392174294Sobrien	  \hskip\rskip
6393174294Sobrien      \egroup
6394174294Sobrien      \cartbot
6395174294Sobrien  \egroup
6396174294Sobrien  \checkinserts
6397174294Sobrien}
639838494Sobrien
639938494Sobrien
640038494Sobrien% This macro is called at the beginning of all the @example variants,
640138494Sobrien% inside a group.
6402310490Scy\newdimen\nonfillparindent
640338494Sobrien\def\nonfillstart{%
640438494Sobrien  \aboveenvbreak
640538494Sobrien  \hfuzz = 12pt % Don't be fussy
640638494Sobrien  \sepspaces % Make spaces be word-separators rather than space tokens.
640738494Sobrien  \let\par = \lisppar % don't ignore blank lines
640838494Sobrien  \obeylines % each line of input is a line of output
640938494Sobrien  \parskip = 0pt
6410310490Scy  % Turn off paragraph indentation but redefine \indent to emulate
6411310490Scy  % the normal \indent.
6412310490Scy  \nonfillparindent=\parindent
641338494Sobrien  \parindent = 0pt
6414310490Scy  \let\indent\nonfillindent
6415310490Scy  %
641638494Sobrien  \emergencystretch = 0pt % don't try to avoid overfull boxes
641738494Sobrien  \ifx\nonarrowing\relax
641838494Sobrien    \advance \leftskip by \lispnarrowing
641938494Sobrien    \exdentamount=\lispnarrowing
6420310490Scy  \else
6421310490Scy    \let\nonarrowing = \relax
642238494Sobrien  \fi
6423174294Sobrien  \let\exdent=\nofillexdent
642438494Sobrien}
642538494Sobrien
6426310490Scy\begingroup
6427310490Scy\obeyspaces
6428310490Scy% We want to swallow spaces (but not other tokens) after the fake
6429310490Scy% @indent in our nonfill-environments, where spaces are normally
6430310490Scy% active and set to @tie, resulting in them not being ignored after
6431310490Scy% @indent.
6432310490Scy\gdef\nonfillindent{\futurelet\temp\nonfillindentcheck}%
6433310490Scy\gdef\nonfillindentcheck{%
6434310490Scy\ifx\temp %
6435310490Scy\expandafter\nonfillindentgobble%
6436310490Scy\else%
6437310490Scy\leavevmode\nonfillindentbox%
6438310490Scy\fi%
6439310490Scy}%
6440310490Scy\endgroup
6441310490Scy\def\nonfillindentgobble#1{\nonfillindent}
6442310490Scy\def\nonfillindentbox{\hbox to \nonfillparindent{\hss}}
6443310490Scy
6444174294Sobrien% If you want all examples etc. small: @set dispenvsize small.
6445174294Sobrien% If you want even small examples the full size: @set dispenvsize nosmall.
6446174294Sobrien% This affects the following displayed environments:
6447174294Sobrien%    @example, @display, @format, @lisp
644882794Sobrien%
6449174294Sobrien\def\smallword{small}
6450174294Sobrien\def\nosmallword{nosmall}
6451174294Sobrien\let\SETdispenvsize\relax
6452174294Sobrien\def\setnormaldispenv{%
6453174294Sobrien  \ifx\SETdispenvsize\smallword
6454310490Scy    % end paragraph for sake of leading, in case document has no blank
6455310490Scy    % line.  This is redundant with what happens in \aboveenvbreak, but
6456310490Scy    % we need to do it before changing the fonts, and it's inconvenient
6457310490Scy    % to change the fonts afterward.
6458310490Scy    \ifnum \lastpenalty=10000 \else \endgraf \fi
6459174294Sobrien    \smallexamplefonts \rm
6460174294Sobrien  \fi
6461174294Sobrien}
6462174294Sobrien\def\setsmalldispenv{%
6463174294Sobrien  \ifx\SETdispenvsize\nosmallword
6464174294Sobrien  \else
6465310490Scy    \ifnum \lastpenalty=10000 \else \endgraf \fi
6466174294Sobrien    \smallexamplefonts \rm
6467174294Sobrien  \fi
6468174294Sobrien}
6469174294Sobrien
6470174294Sobrien% We often define two environments, @foo and @smallfoo.
6471310490Scy% Let's do it in one command.  #1 is the env name, #2 the definition.
6472310490Scy\def\makedispenvdef#1#2{%
6473310490Scy  \expandafter\envdef\csname#1\endcsname {\setnormaldispenv #2}%
6474310490Scy  \expandafter\envdef\csname small#1\endcsname {\setsmalldispenv #2}%
6475174294Sobrien  \expandafter\let\csname E#1\endcsname \afterenvbreak
6476174294Sobrien  \expandafter\let\csname Esmall#1\endcsname \afterenvbreak
6477174294Sobrien}
6478174294Sobrien
6479310490Scy% Define two environment synonyms (#1 and #2) for an environment.
6480310490Scy\def\maketwodispenvdef#1#2#3{%
6481310490Scy  \makedispenvdef{#1}{#3}%
6482310490Scy  \makedispenvdef{#2}{#3}%
6483174294Sobrien}
648438494Sobrien%
6485310490Scy% @lisp: indented, narrowed, typewriter font;
6486310490Scy% @example: same as @lisp.
6487310490Scy%
6488174294Sobrien% @smallexample and @smalllisp: use smaller fonts.
6489174294Sobrien% Originally contributed by Pavel@xerox.
6490174294Sobrien%
6491310490Scy\maketwodispenvdef{lisp}{example}{%
649238494Sobrien  \nonfillstart
6493310490Scy  \tt\setupmarkupstyle{example}%
649442629Sobrien  \let\kbdfont = \kbdexamplefont % Allow @kbd to do something special.
6495310490Scy  \gobble % eat return
649638494Sobrien}
6497174294Sobrien% @display/@smalldisplay: same as @lisp except keep current font.
649882794Sobrien%
6499310490Scy\makedispenvdef{display}{%
6500174294Sobrien  \nonfillstart
6501174294Sobrien  \gobble
650238494Sobrien}
650338494Sobrien
6504174294Sobrien% @format/@smallformat: same as @display except don't narrow margins.
650538494Sobrien%
6506310490Scy\makedispenvdef{format}{%
6507174294Sobrien  \let\nonarrowing = t%
650838494Sobrien  \nonfillstart
650938494Sobrien  \gobble
651038494Sobrien}
651142629Sobrien
6512174294Sobrien% @flushleft: same as @format, but doesn't obey \SETdispenvsize.
6513174294Sobrien\envdef\flushleft{%
6514174294Sobrien  \let\nonarrowing = t%
651538494Sobrien  \nonfillstart
651638494Sobrien  \gobble
651738494Sobrien}
6518174294Sobrien\let\Eflushleft = \afterenvbreak
651942629Sobrien
652042629Sobrien% @flushright.
652182794Sobrien%
6522174294Sobrien\envdef\flushright{%
6523174294Sobrien  \let\nonarrowing = t%
652438494Sobrien  \nonfillstart
6525310490Scy  \advance\leftskip by 0pt plus 1fill\relax
652642629Sobrien  \gobble
652742629Sobrien}
6528174294Sobrien\let\Eflushright = \afterenvbreak
652938494Sobrien
653082794Sobrien
6531310490Scy% @raggedright does more-or-less normal line breaking but no right
6532310490Scy% justification.  From plain.tex.
6533310490Scy\envdef\raggedright{%
6534310490Scy  \rightskip0pt plus2em \spaceskip.3333em \xspaceskip.5em\relax
6535310490Scy}
6536310490Scy\let\Eraggedright\par
6537310490Scy
6538310490Scy\envdef\raggedleft{%
6539310490Scy  \parindent=0pt \leftskip0pt plus2em
6540310490Scy  \spaceskip.3333em \xspaceskip.5em \parfillskip=0pt
6541310490Scy  \hbadness=10000 % Last line will usually be underfull, so turn off
6542310490Scy                  % badness reporting.
6543310490Scy}
6544310490Scy\let\Eraggedleft\par
6545310490Scy
6546310490Scy\envdef\raggedcenter{%
6547310490Scy  \parindent=0pt \rightskip0pt plus1em \leftskip0pt plus1em
6548310490Scy  \spaceskip.3333em \xspaceskip.5em \parfillskip=0pt
6549310490Scy  \hbadness=10000 % Last line will usually be underfull, so turn off
6550310490Scy                  % badness reporting.
6551310490Scy}
6552310490Scy\let\Eraggedcenter\par
6553310490Scy
6554310490Scy
655538494Sobrien% @quotation does normal linebreaking (hence we can't use \nonfillstart)
6556174294Sobrien% and narrows the margins.  We keep \parskip nonzero in general, since
6557174294Sobrien% we're doing normal filling.  So, when using \aboveenvbreak and
6558174294Sobrien% \afterenvbreak, temporarily make \parskip 0.
655938494Sobrien%
6560310490Scy\makedispenvdef{quotation}{\quotationstart}
6561310490Scy%
6562310490Scy\def\quotationstart{%
6563310490Scy  \indentedblockstart % same as \indentedblock, but increase right margin too.
656438494Sobrien  \ifx\nonarrowing\relax
656538494Sobrien    \advance\rightskip by \lispnarrowing
656638494Sobrien  \fi
6567174294Sobrien  \parsearg\quotationlabel
656838494Sobrien}
656938494Sobrien
6570174294Sobrien% We have retained a nonzero parskip for the environment, since we're
6571174294Sobrien% doing normal filling.
6572174294Sobrien%
6573174294Sobrien\def\Equotation{%
6574174294Sobrien  \par
6575310490Scy  \ifx\quotationauthor\thisisundefined\else
6576174294Sobrien    % indent a bit.
6577174294Sobrien    \leftline{\kern 2\leftskip \sl ---\quotationauthor}%
6578174294Sobrien  \fi
6579174294Sobrien  {\parskip=0pt \afterenvbreak}%
6580174294Sobrien}
6581310490Scy\def\Esmallquotation{\Equotation}
658242629Sobrien
6583174294Sobrien% If we're given an argument, typeset it in bold with a colon after.
6584174294Sobrien\def\quotationlabel#1{%
6585174294Sobrien  \def\temp{#1}%
6586174294Sobrien  \ifx\temp\empty \else
6587174294Sobrien    {\bf #1: }%
6588174294Sobrien  \fi
6589174294Sobrien}
6590174294Sobrien
6591310490Scy% @indentedblock is like @quotation, but indents only on the left and
6592310490Scy% has no optional argument.
6593310490Scy% 
6594310490Scy\makedispenvdef{indentedblock}{\indentedblockstart}
6595310490Scy%
6596310490Scy\def\indentedblockstart{%
6597310490Scy  {\parskip=0pt \aboveenvbreak}% because \aboveenvbreak inserts \parskip
6598310490Scy  \parindent=0pt
6599310490Scy  %
6600310490Scy  % @cartouche defines \nonarrowing to inhibit narrowing at next level down.
6601310490Scy  \ifx\nonarrowing\relax
6602310490Scy    \advance\leftskip by \lispnarrowing
6603310490Scy    \exdentamount = \lispnarrowing
6604310490Scy  \else
6605310490Scy    \let\nonarrowing = \relax
6606310490Scy  \fi
6607310490Scy}
6608174294Sobrien
6609310490Scy% Keep a nonzero parskip for the environment, since we're doing normal filling.
6610310490Scy%
6611310490Scy\def\Eindentedblock{%
6612310490Scy  \par
6613310490Scy  {\parskip=0pt \afterenvbreak}%
6614310490Scy}
6615310490Scy\def\Esmallindentedblock{\Eindentedblock}
6616310490Scy
6617310490Scy
661882794Sobrien% LaTeX-like @verbatim...@end verbatim and @verb{<char>...<char>}
6619174294Sobrien% If we want to allow any <char> as delimiter,
662082794Sobrien% we need the curly braces so that makeinfo sees the @verb command, eg:
662182794Sobrien% `@verbx...x' would look like the '@verbx' command.  --janneke@gnu.org
662282794Sobrien%
662382794Sobrien% [Knuth]: Donald Ervin Knuth, 1996.  The TeXbook.
662482794Sobrien%
6625174294Sobrien% [Knuth] p.344; only we need to do the other characters Texinfo sets
6626174294Sobrien% active too.  Otherwise, they get lost as the first character on a
6627174294Sobrien% verbatim line.
662882794Sobrien\def\dospecials{%
6629174294Sobrien  \do\ \do\\\do\{\do\}\do\$\do\&%
6630174294Sobrien  \do\#\do\^\do\^^K\do\_\do\^^A\do\%\do\~%
6631174294Sobrien  \do\<\do\>\do\|\do\@\do+\do\"%
6632310490Scy  % Don't do the quotes -- if we do, @set txicodequoteundirected and
6633310490Scy  % @set txicodequotebacktick will not have effect on @verb and
6634310490Scy  % @verbatim, and ?` and !` ligatures won't get disabled.
6635310490Scy  %\do\`\do\'%
6636174294Sobrien}
663782794Sobrien%
663882794Sobrien% [Knuth] p. 380
663982794Sobrien\def\uncatcodespecials{%
6640174294Sobrien  \def\do##1{\catcode`##1=\other}\dospecials}
664182794Sobrien%
664282794Sobrien% Setup for the @verb command.
664382794Sobrien%
664482794Sobrien% Eight spaces for a tab
664582794Sobrien\begingroup
664682794Sobrien  \catcode`\^^I=\active
664782794Sobrien  \gdef\tabeightspaces{\catcode`\^^I=\active\def^^I{\ \ \ \ \ \ \ \ }}
664882794Sobrien\endgroup
664982794Sobrien%
665082794Sobrien\def\setupverb{%
665182794Sobrien  \tt  % easiest (and conventionally used) font for verbatim
665282794Sobrien  \def\par{\leavevmode\endgraf}%
6653310490Scy  \setupmarkupstyle{verb}%
665482794Sobrien  \tabeightspaces
665582794Sobrien  % Respect line breaks,
665682794Sobrien  % print special symbols as themselves, and
665782794Sobrien  % make each space count
665882794Sobrien  % must do in this order:
665982794Sobrien  \obeylines \uncatcodespecials \sepspaces
666082794Sobrien}
666182794Sobrien
666282794Sobrien% Setup for the @verbatim environment
666382794Sobrien%
6664310490Scy% Real tab expansion.
666582794Sobrien\newdimen\tabw \setbox0=\hbox{\tt\space} \tabw=8\wd0 % tab amount
666682794Sobrien%
6667310490Scy% We typeset each line of the verbatim in an \hbox, so we can handle
6668310490Scy% tabs.  The \global is in case the verbatim line starts with an accent,
6669310490Scy% or some other command that starts with a begin-group.  Otherwise, the
6670310490Scy% entire \verbbox would disappear at the corresponding end-group, before
6671310490Scy% it is typeset.  Meanwhile, we can't have nested verbatim commands
6672310490Scy% (can we?), so the \global won't be overwriting itself.
6673310490Scy\newbox\verbbox
6674310490Scy\def\starttabbox{\global\setbox\verbbox=\hbox\bgroup}
6675310490Scy%
667682794Sobrien\begingroup
667782794Sobrien  \catcode`\^^I=\active
667882794Sobrien  \gdef\tabexpand{%
667982794Sobrien    \catcode`\^^I=\active
668082794Sobrien    \def^^I{\leavevmode\egroup
6681310490Scy      \dimen\verbbox=\wd\verbbox % the width so far, or since the previous tab
6682310490Scy      \divide\dimen\verbbox by\tabw
6683310490Scy      \multiply\dimen\verbbox by\tabw % compute previous multiple of \tabw
6684310490Scy      \advance\dimen\verbbox by\tabw  % advance to next multiple of \tabw
6685310490Scy      \wd\verbbox=\dimen\verbbox \box\verbbox \starttabbox
668682794Sobrien    }%
668782794Sobrien  }
668882794Sobrien\endgroup
6689310490Scy
6690310490Scy% start the verbatim environment.
669182794Sobrien\def\setupverbatim{%
6692310490Scy  \let\nonarrowing = t%
6693174294Sobrien  \nonfillstart
6694310490Scy  \tt % easiest (and conventionally used) font for verbatim
6695310490Scy  % The \leavevmode here is for blank lines.  Otherwise, we would
6696310490Scy  % never \starttabox and the \egroup would end verbatim mode.
6697310490Scy  \def\par{\leavevmode\egroup\box\verbbox\endgraf}%
669882794Sobrien  \tabexpand
6699310490Scy  \setupmarkupstyle{verbatim}%
670082794Sobrien  % Respect line breaks,
670182794Sobrien  % print special symbols as themselves, and
6702310490Scy  % make each space count.
6703310490Scy  % Must do in this order:
670482794Sobrien  \obeylines \uncatcodespecials \sepspaces
670582794Sobrien  \everypar{\starttabbox}%
670682794Sobrien}
670782794Sobrien
6708174294Sobrien% Do the @verb magic: verbatim text is quoted by unique
6709174294Sobrien% delimiter characters.  Before first delimiter expect a
671082794Sobrien% right brace, after last delimiter expect closing brace:
671182794Sobrien%
671282794Sobrien%    \def\doverb'{'<char>#1<char>'}'{#1}
671382794Sobrien%
671482794Sobrien% [Knuth] p. 382; only eat outer {}
671582794Sobrien\begingroup
6716174294Sobrien  \catcode`[=1\catcode`]=2\catcode`\{=\other\catcode`\}=\other
671782794Sobrien  \gdef\doverb{#1[\def\next##1#1}[##1\endgroup]\next]
671882794Sobrien\endgroup
671982794Sobrien%
672082794Sobrien\def\verb{\begingroup\setupverb\doverb}
672182794Sobrien%
672282794Sobrien%
672382794Sobrien% Do the @verbatim magic: define the macro \doverbatim so that
672482794Sobrien% the (first) argument ends when '@end verbatim' is reached, ie:
672582794Sobrien%
672682794Sobrien%     \def\doverbatim#1@end verbatim{#1}
672782794Sobrien%
6728174294Sobrien% For Texinfo it's a lot easier than for LaTeX,
672982794Sobrien% because texinfo's \verbatim doesn't stop at '\end{verbatim}':
6730174294Sobrien% we need not redefine '\', '{' and '}'.
673182794Sobrien%
673282794Sobrien% Inspired by LaTeX's verbatim command set [latex.ltx]
6733174294Sobrien%
673482794Sobrien\begingroup
673582794Sobrien  \catcode`\ =\active
6736174294Sobrien  \obeylines %
6737174294Sobrien  % ignore everything up to the first ^^M, that's the newline at the end
6738174294Sobrien  % of the @verbatim input line itself.  Otherwise we get an extra blank
6739174294Sobrien  % line in the output.
6740174294Sobrien  \xdef\doverbatim#1^^M#2@end verbatim{#2\noexpand\end\gobble verbatim}%
6741174294Sobrien  % We really want {...\end verbatim} in the body of the macro, but
6742174294Sobrien  % without the active space; thus we have to use \xdef and \gobble.
674382794Sobrien\endgroup
674482794Sobrien%
6745174294Sobrien\envdef\verbatim{%
6746174294Sobrien    \setupverbatim\doverbatim
674782794Sobrien}
6748174294Sobrien\let\Everbatim = \afterenvbreak
674982794Sobrien
6750174294Sobrien
675182794Sobrien% @verbatiminclude FILE - insert text of file in verbatim environment.
675282794Sobrien%
6753174294Sobrien\def\verbatiminclude{\parseargusing\filenamecatcodes\doverbatiminclude}
675482794Sobrien%
675582794Sobrien\def\doverbatiminclude#1{%
6756174294Sobrien  {%
6757174294Sobrien    \makevalueexpandable
6758174294Sobrien    \setupverbatim
6759310490Scy    \indexnofonts       % Allow `@@' and other weird things in file names.
6760310490Scy    \wlog{texinfo.tex: doing @verbatiminclude of #1^^J}%
6761174294Sobrien    \input #1
6762174294Sobrien    \afterenvbreak
6763174294Sobrien  }%
676482794Sobrien}
676582794Sobrien
6766119679Smbr% @copying ... @end copying.
6767119679Smbr% Save the text away for @insertcopying later.
6768119679Smbr%
6769174294Sobrien% We save the uninterpreted tokens, rather than creating a box.
6770174294Sobrien% Saving the text in a box would be much easier, but then all the
6771174294Sobrien% typesetting commands (@smallbook, font changes, etc.) have to be done
6772174294Sobrien% beforehand -- and a) we want @copying to be done first in the source
6773174294Sobrien% file; b) letting users define the frontmatter in as flexible order as
6774174294Sobrien% possible is very desirable.
6775174294Sobrien%
6776174294Sobrien\def\copying{\checkenv{}\begingroup\scanargctxt\docopying}
6777174294Sobrien\def\docopying#1@end copying{\endgroup\def\copyingtext{#1}}
6778174294Sobrien%
6779174294Sobrien\def\insertcopying{%
6780174294Sobrien  \begingroup
6781174294Sobrien    \parindent = 0pt  % paragraph indentation looks wrong on title page
6782174294Sobrien    \scanexp\copyingtext
6783174294Sobrien  \endgroup
6784119679Smbr}
678582794Sobrien
6786310490Scy
678738494Sobrien\message{defuns,}
678882794Sobrien% @defun etc.
678982794Sobrien
679038494Sobrien\newskip\defbodyindent \defbodyindent=.4in
679138494Sobrien\newskip\defargsindent \defargsindent=50pt
679238494Sobrien\newskip\deflastargmargin \deflastargmargin=18pt
6793310490Scy\newcount\defunpenalty
679438494Sobrien
6795174294Sobrien% Start the processing of @deffn:
6796174294Sobrien\def\startdefun{%
6797174294Sobrien  \ifnum\lastpenalty<10000
6798174294Sobrien    \medbreak
6799310490Scy    \defunpenalty=10003 % Will keep this @deffn together with the
6800310490Scy                        % following @def command, see below.
6801174294Sobrien  \else
6802174294Sobrien    % If there are two @def commands in a row, we'll have a \nobreak,
6803174294Sobrien    % which is there to keep the function description together with its
6804174294Sobrien    % header.  But if there's nothing but headers, we need to allow a
6805174294Sobrien    % break somewhere.  Check specifically for penalty 10002, inserted
6806310490Scy    % by \printdefunline, instead of 10000, since the sectioning
6807174294Sobrien    % commands also insert a nobreak penalty, and we don't want to allow
6808174294Sobrien    % a break between a section heading and a defun.
6809174294Sobrien    %
6810310490Scy    % As a further refinement, we avoid "club" headers by signalling
6811310490Scy    % with penalty of 10003 after the very first @deffn in the
6812310490Scy    % sequence (see above), and penalty of 10002 after any following
6813310490Scy    % @def command.
6814310490Scy    \ifnum\lastpenalty=10002 \penalty2000 \else \defunpenalty=10002 \fi
6815310490Scy    %
6816174294Sobrien    % Similarly, after a section heading, do not allow a break.
6817174294Sobrien    % But do insert the glue.
6818174294Sobrien    \medskip  % preceded by discardable penalty, so not a breakpoint
6819174294Sobrien  \fi
6820119679Smbr  %
6821119679Smbr  \parindent=0in
6822119679Smbr  \advance\leftskip by \defbodyindent
6823119679Smbr  \exdentamount=\defbodyindent
6824119679Smbr}
682538494Sobrien
6826174294Sobrien\def\dodefunx#1{%
6827174294Sobrien  % First, check whether we are in the right environment:
6828174294Sobrien  \checkenv#1%
6829174294Sobrien  %
6830174294Sobrien  % As above, allow line break if we have multiple x headers in a row.
6831174294Sobrien  % It's not a great place, though.
6832310490Scy  \ifnum\lastpenalty=10002 \penalty3000 \else \defunpenalty=10002 \fi
6833174294Sobrien  %
6834174294Sobrien  % And now, it's time to reuse the body of the original defun:
6835174294Sobrien  \expandafter\gobbledefun#1%
6836119679Smbr}
6837174294Sobrien\def\gobbledefun#1\startdefun{}
683838494Sobrien
6839174294Sobrien% \printdefunline \deffnheader{text}
684082794Sobrien%
6841174294Sobrien\def\printdefunline#1#2{%
6842174294Sobrien  \begingroup
6843174294Sobrien    % call \deffnheader:
6844174294Sobrien    #1#2 \endheader
6845174294Sobrien    % common ending:
6846174294Sobrien    \interlinepenalty = 10000
6847310490Scy    \advance\rightskip by 0pt plus 1fil\relax
6848174294Sobrien    \endgraf
6849174294Sobrien    \nobreak\vskip -\parskip
6850310490Scy    \penalty\defunpenalty  % signal to \startdefun and \dodefunx
6851174294Sobrien    % Some of the @defun-type tags do not enable magic parentheses,
6852174294Sobrien    % rendering the following check redundant.  But we don't optimize.
6853174294Sobrien    \checkparencounts
6854174294Sobrien  \endgroup
6855119679Smbr}
685638494Sobrien
6857174294Sobrien\def\Edefun{\endgraf\medbreak}
685882794Sobrien
6859174294Sobrien% \makedefun{deffn} creates \deffn, \deffnx and \Edeffn;
6860310490Scy% the only thing remaining is to define \deffnheader.
686138494Sobrien%
6862174294Sobrien\def\makedefun#1{%
6863174294Sobrien  \expandafter\let\csname E#1\endcsname = \Edefun
6864174294Sobrien  \edef\temp{\noexpand\domakedefun
6865174294Sobrien    \makecsname{#1}\makecsname{#1x}\makecsname{#1header}}%
6866174294Sobrien  \temp
686738494Sobrien}
686838494Sobrien
6869174294Sobrien% \domakedefun \deffn \deffnx \deffnheader
687038494Sobrien%
6871174294Sobrien% Define \deffn and \deffnx, without parameters.
6872174294Sobrien% \deffnheader has to be defined explicitly.
687338494Sobrien%
6874174294Sobrien\def\domakedefun#1#2#3{%
6875174294Sobrien  \envdef#1{%
6876174294Sobrien    \startdefun
6877310490Scy    \doingtypefnfalse    % distinguish typed functions from all else
6878174294Sobrien    \parseargusing\activeparens{\printdefunline#3}%
6879174294Sobrien  }%
6880174294Sobrien  \def#2{\dodefunx#1}%
6881174294Sobrien  \def#3%
688238494Sobrien}
688338494Sobrien
6884310490Scy\newif\ifdoingtypefn       % doing typed function?
6885310490Scy\newif\ifrettypeownline    % typeset return type on its own line?
688638494Sobrien
6887310490Scy% @deftypefnnewline on|off says whether the return type of typed functions
6888310490Scy% are printed on their own line.  This affects @deftypefn, @deftypefun,
6889310490Scy% @deftypeop, and @deftypemethod.
6890310490Scy% 
6891310490Scy\parseargdef\deftypefnnewline{%
6892310490Scy  \def\temp{#1}%
6893310490Scy  \ifx\temp\onword
6894310490Scy    \expandafter\let\csname SETtxideftypefnnl\endcsname
6895310490Scy      = \empty
6896310490Scy  \else\ifx\temp\offword
6897310490Scy    \expandafter\let\csname SETtxideftypefnnl\endcsname
6898310490Scy      = \relax
6899310490Scy  \else
6900310490Scy    \errhelp = \EMsimple
6901310490Scy    \errmessage{Unknown @txideftypefnnl value `\temp',
6902310490Scy                must be on|off}%
6903310490Scy  \fi\fi
6904310490Scy}
6905310490Scy
6906310490Scy% Untyped functions:
6907310490Scy
6908174294Sobrien% @deffn category name args
6909174294Sobrien\makedefun{deffn}{\deffngeneral{}}
691038494Sobrien
6911174294Sobrien% @deffn category class name args
6912174294Sobrien\makedefun{defop}#1 {\defopon{#1\ \putwordon}}
691338494Sobrien
6914174294Sobrien% \defopon {category on}class name args
6915174294Sobrien\def\defopon#1#2 {\deffngeneral{\putwordon\ \code{#2}}{#1\ \code{#2}} }
691638494Sobrien
6917174294Sobrien% \deffngeneral {subind}category name args
6918174294Sobrien%
6919174294Sobrien\def\deffngeneral#1#2 #3 #4\endheader{%
6920174294Sobrien  % Remember that \dosubind{fn}{foo}{} is equivalent to \doind{fn}{foo}.
6921174294Sobrien  \dosubind{fn}{\code{#3}}{#1}%
6922174294Sobrien  \defname{#2}{}{#3}\magicamp\defunargs{#4\unskip}%
692338494Sobrien}
692438494Sobrien
6925310490Scy% Typed functions:
692638494Sobrien
6927174294Sobrien% @deftypefn category type name args
6928174294Sobrien\makedefun{deftypefn}{\deftypefngeneral{}}
692938494Sobrien
6930174294Sobrien% @deftypeop category class type name args
6931174294Sobrien\makedefun{deftypeop}#1 {\deftypeopon{#1\ \putwordon}}
693238494Sobrien
6933174294Sobrien% \deftypeopon {category on}class type name args
6934174294Sobrien\def\deftypeopon#1#2 {\deftypefngeneral{\putwordon\ \code{#2}}{#1\ \code{#2}} }
693538494Sobrien
6936174294Sobrien% \deftypefngeneral {subind}category type name args
6937174294Sobrien%
6938174294Sobrien\def\deftypefngeneral#1#2 #3 #4 #5\endheader{%
6939174294Sobrien  \dosubind{fn}{\code{#4}}{#1}%
6940310490Scy  \doingtypefntrue
6941174294Sobrien  \defname{#2}{#3}{#4}\defunargs{#5\unskip}%
694238494Sobrien}
694338494Sobrien
6944310490Scy% Typed variables:
694538494Sobrien
6946174294Sobrien% @deftypevr category type var args
6947174294Sobrien\makedefun{deftypevr}{\deftypecvgeneral{}}
694838494Sobrien
6949174294Sobrien% @deftypecv category class type var args
6950174294Sobrien\makedefun{deftypecv}#1 {\deftypecvof{#1\ \putwordof}}
695138494Sobrien
6952174294Sobrien% \deftypecvof {category of}class type var args
6953174294Sobrien\def\deftypecvof#1#2 {\deftypecvgeneral{\putwordof\ \code{#2}}{#1\ \code{#2}} }
695438494Sobrien
6955174294Sobrien% \deftypecvgeneral {subind}category type var args
6956174294Sobrien%
6957174294Sobrien\def\deftypecvgeneral#1#2 #3 #4 #5\endheader{%
6958174294Sobrien  \dosubind{vr}{\code{#4}}{#1}%
6959174294Sobrien  \defname{#2}{#3}{#4}\defunargs{#5\unskip}%
696038494Sobrien}
696138494Sobrien
6962310490Scy% Untyped variables:
696338494Sobrien
6964174294Sobrien% @defvr category var args
6965174294Sobrien\makedefun{defvr}#1 {\deftypevrheader{#1} {} }
696638494Sobrien
6967174294Sobrien% @defcv category class var args
6968174294Sobrien\makedefun{defcv}#1 {\defcvof{#1\ \putwordof}}
696938494Sobrien
6970174294Sobrien% \defcvof {category of}class var args
6971174294Sobrien\def\defcvof#1#2 {\deftypecvof{#1}#2 {} }
697238494Sobrien
6973310490Scy% Types:
6974310490Scy
6975174294Sobrien% @deftp category name args
6976174294Sobrien\makedefun{deftp}#1 #2 #3\endheader{%
6977174294Sobrien  \doind{tp}{\code{#2}}%
6978174294Sobrien  \defname{#1}{}{#2}\defunargs{#3\unskip}%
697938494Sobrien}
698038494Sobrien
6981174294Sobrien% Remaining @defun-like shortcuts:
6982174294Sobrien\makedefun{defun}{\deffnheader{\putwordDeffunc} }
6983174294Sobrien\makedefun{defmac}{\deffnheader{\putwordDefmac} }
6984174294Sobrien\makedefun{defspec}{\deffnheader{\putwordDefspec} }
6985174294Sobrien\makedefun{deftypefun}{\deftypefnheader{\putwordDeffunc} }
6986174294Sobrien\makedefun{defvar}{\defvrheader{\putwordDefvar} }
6987174294Sobrien\makedefun{defopt}{\defvrheader{\putwordDefopt} }
6988174294Sobrien\makedefun{deftypevar}{\deftypevrheader{\putwordDefvar} }
6989174294Sobrien\makedefun{defmethod}{\defopon\putwordMethodon}
6990174294Sobrien\makedefun{deftypemethod}{\deftypeopon\putwordMethodon}
6991174294Sobrien\makedefun{defivar}{\defcvof\putwordInstanceVariableof}
6992174294Sobrien\makedefun{deftypeivar}{\deftypecvof\putwordInstanceVariableof}
699338494Sobrien
6994174294Sobrien% \defname, which formats the name of the @def (not the args).
6995174294Sobrien% #1 is the category, such as "Function".
6996174294Sobrien% #2 is the return type, if any.
6997174294Sobrien% #3 is the function name.
699882794Sobrien%
6999174294Sobrien% We are followed by (but not passed) the arguments, if any.
700082794Sobrien%
7001174294Sobrien\def\defname#1#2#3{%
7002310490Scy  \par
7003174294Sobrien  % Get the values of \leftskip and \rightskip as they were outside the @def...
7004174294Sobrien  \advance\leftskip by -\defbodyindent
7005174294Sobrien  %
7006310490Scy  % Determine if we are typesetting the return type of a typed function
7007310490Scy  % on a line by itself.
7008310490Scy  \rettypeownlinefalse
7009310490Scy  \ifdoingtypefn  % doing a typed function specifically?
7010310490Scy    % then check user option for putting return type on its own line:
7011310490Scy    \expandafter\ifx\csname SETtxideftypefnnl\endcsname\relax \else
7012310490Scy      \rettypeownlinetrue
7013310490Scy    \fi
7014310490Scy  \fi
7015310490Scy  %
7016310490Scy  % How we'll format the category name.  Putting it in brackets helps
7017174294Sobrien  % distinguish it from the body text that may end up on the next line
7018174294Sobrien  % just below it.
7019174294Sobrien  \def\temp{#1}%
7020174294Sobrien  \setbox0=\hbox{\kern\deflastargmargin \ifx\temp\empty\else [\rm\temp]\fi}
7021174294Sobrien  %
7022310490Scy  % Figure out line sizes for the paragraph shape.  We'll always have at
7023310490Scy  % least two.
7024310490Scy  \tempnum = 2
7025310490Scy  %
7026174294Sobrien  % The first line needs space for \box0; but if \rightskip is nonzero,
7027174294Sobrien  % we need only space for the part of \box0 which exceeds it:
7028174294Sobrien  \dimen0=\hsize  \advance\dimen0 by -\wd0  \advance\dimen0 by \rightskip
7029310490Scy  %
7030310490Scy  % If doing a return type on its own line, we'll have another line.
7031310490Scy  \ifrettypeownline
7032310490Scy    \advance\tempnum by 1
7033310490Scy    \def\maybeshapeline{0in \hsize}%
7034310490Scy  \else
7035310490Scy    \def\maybeshapeline{}%
7036310490Scy  \fi
7037310490Scy  %
7038174294Sobrien  % The continuations:
7039174294Sobrien  \dimen2=\hsize  \advance\dimen2 by -\defargsindent
7040174294Sobrien  %
7041310490Scy  % The final paragraph shape:
7042310490Scy  \parshape \tempnum  0in \dimen0  \maybeshapeline  \defargsindent \dimen2
7043310490Scy  %
7044310490Scy  % Put the category name at the right margin.
7045174294Sobrien  \noindent
7046174294Sobrien  \hbox to 0pt{%
7047174294Sobrien    \hfil\box0 \kern-\hsize
7048174294Sobrien    % \hsize has to be shortened this way:
7049174294Sobrien    \kern\leftskip
7050174294Sobrien    % Intentionally do not respect \rightskip, since we need the space.
7051174294Sobrien  }%
7052174294Sobrien  %
7053174294Sobrien  % Allow all lines to be underfull without complaint:
7054174294Sobrien  \tolerance=10000 \hbadness=10000
7055174294Sobrien  \exdentamount=\defbodyindent
7056174294Sobrien  {%
7057174294Sobrien    % defun fonts. We use typewriter by default (used to be bold) because:
7058174294Sobrien    % . we're printing identifiers, they should be in tt in principle.
7059174294Sobrien    % . in languages with many accents, such as Czech or French, it's
7060174294Sobrien    %   common to leave accents off identifiers.  The result looks ok in
7061174294Sobrien    %   tt, but exceedingly strange in rm.
7062174294Sobrien    % . we don't want -- and --- to be treated as ligatures.
7063174294Sobrien    % . this still does not fix the ?` and !` ligatures, but so far no
7064174294Sobrien    %   one has made identifiers using them :).
7065174294Sobrien    \df \tt
7066310490Scy    \def\temp{#2}% text of the return type
7067310490Scy    \ifx\temp\empty\else
7068310490Scy      \tclose{\temp}% typeset the return type
7069310490Scy      \ifrettypeownline
7070310490Scy        % put return type on its own line; prohibit line break following:
7071310490Scy        \hfil\vadjust{\nobreak}\break  
7072310490Scy      \else
7073310490Scy        \space  % type on same line, so just followed by a space
7074310490Scy      \fi
7075310490Scy    \fi           % no return type
7076174294Sobrien    #3% output function name
7077174294Sobrien  }%
7078174294Sobrien  {\rm\enskip}% hskip 0.5 em of \tenrm
7079174294Sobrien  %
7080174294Sobrien  \boldbrax
7081174294Sobrien  % arguments will be output next, if any.
708238494Sobrien}
708338494Sobrien
7084174294Sobrien% Print arguments in slanted roman (not ttsl), inconsistently with using
7085174294Sobrien% tt for the name.  This is because literal text is sometimes needed in
7086174294Sobrien% the argument list (groff manual), and ttsl and tt are not very
7087174294Sobrien% distinguishable.  Prevent hyphenation at `-' chars.
708838494Sobrien%
7089174294Sobrien\def\defunargs#1{%
7090174294Sobrien  % use sl by default (not ttsl),
7091174294Sobrien  % tt for the names.
7092174294Sobrien  \df \sl \hyphenchar\font=0
7093174294Sobrien  %
7094174294Sobrien  % On the other hand, if an argument has two dashes (for instance), we
7095310490Scy  % want a way to get ttsl.  We used to recommend @var for that, so
7096310490Scy  % leave the code in, but it's strange for @var to lead to typewriter.
7097310490Scy  % Nowadays we recommend @code, since the difference between a ttsl hyphen
7098310490Scy  % and a tt hyphen is pretty tiny.  @code also disables ?` !`.
7099310490Scy  \def\var##1{{\setupmarkupstyle{var}\ttslanted{##1}}}%
7100174294Sobrien  #1%
7101174294Sobrien  \sl\hyphenchar\font=45
710282794Sobrien}
710382794Sobrien
7104174294Sobrien% We want ()&[] to print specially on the defun line.
710582794Sobrien%
7106174294Sobrien\def\activeparens{%
7107174294Sobrien  \catcode`\(=\active \catcode`\)=\active
7108174294Sobrien  \catcode`\[=\active \catcode`\]=\active
7109174294Sobrien  \catcode`\&=\active
711038494Sobrien}
711138494Sobrien
7112174294Sobrien% Make control sequences which act like normal parenthesis chars.
7113174294Sobrien\let\lparen = ( \let\rparen = )
711482794Sobrien
7115174294Sobrien% Be sure that we always have a definition for `(', etc.  For example,
7116174294Sobrien% if the fn name has parens in it, \boldbrax will not be in effect yet,
7117174294Sobrien% so TeX would otherwise complain about undefined control sequence.
7118174294Sobrien{
7119174294Sobrien  \activeparens
7120174294Sobrien  \global\let(=\lparen \global\let)=\rparen
7121174294Sobrien  \global\let[=\lbrack \global\let]=\rbrack
7122174294Sobrien  \global\let& = \&
7123174294Sobrien
7124174294Sobrien  \gdef\boldbrax{\let(=\opnr\let)=\clnr\let[=\lbrb\let]=\rbrb}
7125174294Sobrien  \gdef\magicamp{\let&=\amprm}
712638494Sobrien}
712738494Sobrien
7128174294Sobrien\newcount\parencount
712938494Sobrien
7130174294Sobrien% If we encounter &foo, then turn on ()-hacking afterwards
7131174294Sobrien\newif\ifampseen
7132174294Sobrien\def\amprm#1 {\ampseentrue{\bf\&#1 }}
713338494Sobrien
7134174294Sobrien\def\parenfont{%
7135174294Sobrien  \ifampseen
7136174294Sobrien    % At the first level, print parens in roman,
7137174294Sobrien    % otherwise use the default font.
7138174294Sobrien    \ifnum \parencount=1 \rm \fi
7139174294Sobrien  \else
7140174294Sobrien    % The \sf parens (in \boldbrax) actually are a little bolder than
7141174294Sobrien    % the contained text.  This is especially needed for [ and ] .
7142174294Sobrien    \sf
7143174294Sobrien  \fi
714438494Sobrien}
7145174294Sobrien\def\infirstlevel#1{%
7146174294Sobrien  \ifampseen
7147174294Sobrien    \ifnum\parencount=1
7148174294Sobrien      #1%
7149174294Sobrien    \fi
7150174294Sobrien  \fi
7151174294Sobrien}
7152174294Sobrien\def\bfafterword#1 {#1 \bf}
715338494Sobrien
7154174294Sobrien\def\opnr{%
7155174294Sobrien  \global\advance\parencount by 1
7156174294Sobrien  {\parenfont(}%
7157174294Sobrien  \infirstlevel \bfafterword
715838494Sobrien}
7159174294Sobrien\def\clnr{%
7160174294Sobrien  {\parenfont)}%
7161174294Sobrien  \infirstlevel \sl
7162174294Sobrien  \global\advance\parencount by -1
7163174294Sobrien}
716438494Sobrien
7165174294Sobrien\newcount\brackcount
7166174294Sobrien\def\lbrb{%
7167174294Sobrien  \global\advance\brackcount by 1
7168174294Sobrien  {\bf[}%
716938494Sobrien}
7170174294Sobrien\def\rbrb{%
7171174294Sobrien  {\bf]}%
7172174294Sobrien  \global\advance\brackcount by -1
7173174294Sobrien}
717438494Sobrien
7175174294Sobrien\def\checkparencounts{%
7176174294Sobrien  \ifnum\parencount=0 \else \badparencount \fi
7177174294Sobrien  \ifnum\brackcount=0 \else \badbrackcount \fi
717838494Sobrien}
7179310490Scy% these should not use \errmessage; the glibc manual, at least, actually
7180310490Scy% has such constructs (when documenting function pointers).
7181174294Sobrien\def\badparencount{%
7182310490Scy  \message{Warning: unbalanced parentheses in @def...}%
7183174294Sobrien  \global\parencount=0
7184174294Sobrien}
7185174294Sobrien\def\badbrackcount{%
7186310490Scy  \message{Warning: unbalanced square brackets in @def...}%
7187174294Sobrien  \global\brackcount=0
7188174294Sobrien}
718938494Sobrien
719038494Sobrien
719142629Sobrien\message{macros,}
719242629Sobrien% @macro.
719338494Sobrien
719482794Sobrien% To do this right we need a feature of e-TeX, \scantokens,
719542629Sobrien% which we arrange to emulate with a temporary file in ordinary TeX.
7196310490Scy\ifx\eTeXversion\thisisundefined
7197174294Sobrien  \newwrite\macscribble
7198174294Sobrien  \def\scantokens#1{%
7199174294Sobrien    \toks0={#1}%
7200174294Sobrien    \immediate\openout\macscribble=\jobname.tmp
7201174294Sobrien    \immediate\write\macscribble{\the\toks0}%
7202174294Sobrien    \immediate\closeout\macscribble
7203174294Sobrien    \input \jobname.tmp
7204174294Sobrien  }
720542629Sobrien\fi
720642629Sobrien
7207310490Scy\def\scanmacro#1{\begingroup
7208310490Scy  \newlinechar`\^^M
7209310490Scy  \let\xeatspaces\eatspaces
7210310490Scy  %
7211310490Scy  % Undo catcode changes of \startcontents and \doprintindex
7212310490Scy  % When called from @insertcopying or (short)caption, we need active
7213310490Scy  % backslash to get it printed correctly.  Previously, we had
7214310490Scy  % \catcode`\\=\other instead.  We'll see whether a problem appears
7215310490Scy  % with macro expansion.				--kasal, 19aug04
7216310490Scy  \catcode`\@=0 \catcode`\\=\active \escapechar=`\@
7217310490Scy  %
7218310490Scy  % ... and for \example:
7219310490Scy  \spaceisspace
7220310490Scy  %
7221310490Scy  % The \empty here causes a following catcode 5 newline to be eaten as
7222310490Scy  % part of reading whitespace after a control sequence.  It does not
7223310490Scy  % eat a catcode 13 newline.  There's no good way to handle the two
7224310490Scy  % cases (untried: maybe e-TeX's \everyeof could help, though plain TeX
7225310490Scy  % would then have different behavior).  See the Macro Details node in
7226310490Scy  % the manual for the workaround we recommend for macros and
7227310490Scy  % line-oriented commands.
7228310490Scy  % 
7229310490Scy  \scantokens{#1\empty}%
7230310490Scy\endgroup}
7231174294Sobrien
7232174294Sobrien\def\scanexp#1{%
7233174294Sobrien  \edef\temp{\noexpand\scanmacro{#1}}%
7234174294Sobrien  \temp
7235174294Sobrien}
7236174294Sobrien
723742629Sobrien\newcount\paramno   % Count of parameters
723842629Sobrien\newtoks\macname    % Macro name
723942629Sobrien\newif\ifrecursive  % Is it recursive?
724042629Sobrien
7241310490Scy% List of all defined macros in the form
7242310490Scy%    \definedummyword\macro1\definedummyword\macro2...
7243310490Scy% Currently is also contains all @aliases; the list can be split
7244310490Scy% if there is a need.
7245310490Scy\def\macrolist{}
7246310490Scy
7247310490Scy% Add the macro to \macrolist
7248310490Scy\def\addtomacrolist#1{\expandafter \addtomacrolistxxx \csname#1\endcsname}
7249310490Scy\def\addtomacrolistxxx#1{%
7250310490Scy     \toks0 = \expandafter{\macrolist\definedummyword#1}%
7251310490Scy     \xdef\macrolist{\the\toks0}%
7252310490Scy}
7253310490Scy
725442629Sobrien% Utility routines.
7255174294Sobrien% This does \let #1 = #2, with \csnames; that is,
7256174294Sobrien%   \let \csname#1\endcsname = \csname#2\endcsname
7257174294Sobrien% (except of course we have to play expansion games).
7258310490Scy%
725942629Sobrien\def\cslet#1#2{%
7260174294Sobrien  \expandafter\let
7261174294Sobrien  \csname#1\expandafter\endcsname
7262174294Sobrien  \csname#2\endcsname
7263174294Sobrien}
726442629Sobrien
726542629Sobrien% Trim leading and trailing spaces off a string.
726642629Sobrien% Concepts from aro-bend problem 15 (see CTAN).
726742629Sobrien{\catcode`\@=11
726842629Sobrien\gdef\eatspaces #1{\expandafter\trim@\expandafter{#1 }}
726942629Sobrien\gdef\trim@ #1{\trim@@ @#1 @ #1 @ @@}
727042629Sobrien\gdef\trim@@ #1@ #2@ #3@@{\trim@@@\empty #2 @}
727142629Sobrien\def\unbrace#1{#1}
727242629Sobrien\unbrace{\gdef\trim@@@ #1 } #2@{#1}
727342629Sobrien}
727442629Sobrien
727542629Sobrien% Trim a single trailing ^^M off a string.
7276174294Sobrien{\catcode`\^^M=\other \catcode`\Q=3%
727742629Sobrien\gdef\eatcr #1{\eatcra #1Q^^MQ}%
727842629Sobrien\gdef\eatcra#1^^MQ{\eatcrb#1Q}%
727942629Sobrien\gdef\eatcrb#1Q#2Q{#1}%
728042629Sobrien}
728142629Sobrien
728242629Sobrien% Macro bodies are absorbed as an argument in a context where
728342629Sobrien% all characters are catcode 10, 11 or 12, except \ which is active
7284310490Scy% (as in normal texinfo). It is necessary to change the definition of \
7285310490Scy% to recognize macro arguments; this is the job of \mbodybackslash.
7286310490Scy%
7287310490Scy% Non-ASCII encodings make 8-bit characters active, so un-activate
7288310490Scy% them to avoid their expansion.  Must do this non-globally, to
7289310490Scy% confine the change to the current group.
7290310490Scy%
729182794Sobrien% It's necessary to have hard CRs when the macro is executed. This is
7292310490Scy% done by making ^^M (\endlinechar) catcode 12 when reading the macro
729342629Sobrien% body, and then making it the \newlinechar in \scanmacro.
7294310490Scy%
7295310490Scy\def\scanctxt{% used as subroutine
7296174294Sobrien  \catcode`\"=\other
7297174294Sobrien  \catcode`\+=\other
7298174294Sobrien  \catcode`\<=\other
7299174294Sobrien  \catcode`\>=\other
7300174294Sobrien  \catcode`\@=\other
7301174294Sobrien  \catcode`\^=\other
7302174294Sobrien  \catcode`\_=\other
7303174294Sobrien  \catcode`\|=\other
7304174294Sobrien  \catcode`\~=\other
7305310490Scy  \ifx\declaredencoding\ascii \else \setnonasciicharscatcodenonglobal\other \fi
7306174294Sobrien}
7307174294Sobrien
7308310490Scy\def\scanargctxt{% used for copying and captions, not macros.
7309174294Sobrien  \scanctxt
7310174294Sobrien  \catcode`\\=\other
7311174294Sobrien  \catcode`\^^M=\other
7312174294Sobrien}
7313174294Sobrien
7314310490Scy\def\macrobodyctxt{% used for @macro definitions
7315174294Sobrien  \scanctxt
7316174294Sobrien  \catcode`\{=\other
7317174294Sobrien  \catcode`\}=\other
7318174294Sobrien  \catcode`\^^M=\other
7319174294Sobrien  \usembodybackslash
7320174294Sobrien}
732142629Sobrien
7322310490Scy\def\macroargctxt{% used when scanning invocations
7323174294Sobrien  \scanctxt
7324310490Scy  \catcode`\\=0
7325174294Sobrien}
7326310490Scy% why catcode 0 for \ in the above?  To recognize \\ \{ \} as "escapes"
7327310490Scy% for the single characters \ { }.  Thus, we end up with the "commands"
7328310490Scy% that would be written @\ @{ @} in a Texinfo document.
7329310490Scy% 
7330310490Scy% We already have @{ and @}.  For @\, we define it here, and only for
7331310490Scy% this purpose, to produce a typewriter backslash (so, the @\ that we
7332310490Scy% define for @math can't be used with @macro calls):
7333310490Scy%
7334310490Scy\def\\{\normalbackslash}%
7335310490Scy% 
7336310490Scy% We would like to do this for \, too, since that is what makeinfo does.
7337310490Scy% But it is not possible, because Texinfo already has a command @, for a
7338310490Scy% cedilla accent.  Documents must use @comma{} instead.
7339310490Scy%
7340310490Scy% \anythingelse will almost certainly be an error of some kind.
734142629Sobrien
7342310490Scy
734342629Sobrien% \mbodybackslash is the definition of \ in @macro bodies.
734482794Sobrien% It maps \foo\ => \csname macarg.foo\endcsname => #N
734542629Sobrien% where N is the macro parameter number.
734642629Sobrien% We define \csname macarg.\endcsname to be \realbackslash, so
734742629Sobrien% \\ in macro replacement text gets you a backslash.
7348310490Scy%
734942629Sobrien{\catcode`@=0 @catcode`@\=@active
735042629Sobrien @gdef@usembodybackslash{@let\=@mbodybackslash}
735142629Sobrien @gdef@mbodybackslash#1\{@csname macarg.#1@endcsname}
735242629Sobrien}
735342629Sobrien\expandafter\def\csname macarg.\endcsname{\realbackslash}
735442629Sobrien
7355310490Scy\def\margbackslash#1{\char`\#1 }
7356310490Scy
735742629Sobrien\def\macro{\recursivefalse\parsearg\macroxxx}
735842629Sobrien\def\rmacro{\recursivetrue\parsearg\macroxxx}
735942629Sobrien
736042629Sobrien\def\macroxxx#1{%
7361310490Scy  \getargs{#1}% now \macname is the macname and \argl the arglist
736242629Sobrien  \ifx\argl\empty       % no arguments
7363310490Scy     \paramno=0\relax
736442629Sobrien  \else
736582794Sobrien     \expandafter\parsemargdef \argl;%
7366310490Scy     \if\paramno>256\relax
7367310490Scy       \ifx\eTeXversion\thisisundefined
7368310490Scy         \errhelp = \EMsimple
7369310490Scy         \errmessage{You need eTeX to compile a file with macros with more than 256 arguments}
7370310490Scy       \fi
7371310490Scy     \fi
737242629Sobrien  \fi
737382794Sobrien  \if1\csname ismacro.\the\macname\endcsname
737482794Sobrien     \message{Warning: redefining \the\macname}%
737542629Sobrien  \else
737682794Sobrien     \expandafter\ifx\csname \the\macname\endcsname \relax
7377119679Smbr     \else \errmessage{Macro name \the\macname\space already defined}\fi
737882794Sobrien     \global\cslet{macsave.\the\macname}{\the\macname}%
737982794Sobrien     \global\expandafter\let\csname ismacro.\the\macname\endcsname=1%
7380310490Scy     \addtomacrolist{\the\macname}%
738142629Sobrien  \fi
738242629Sobrien  \begingroup \macrobodyctxt
738342629Sobrien  \ifrecursive \expandafter\parsermacbody
738482794Sobrien  \else \expandafter\parsemacbody
738542629Sobrien  \fi}
738642629Sobrien
7387174294Sobrien\parseargdef\unmacro{%
738882794Sobrien  \if1\csname ismacro.#1\endcsname
738982794Sobrien    \global\cslet{#1}{macsave.#1}%
739082794Sobrien    \global\expandafter\let \csname ismacro.#1\endcsname=0%
7391174294Sobrien    % Remove the macro name from \macrolist:
739282794Sobrien    \begingroup
7393174294Sobrien      \expandafter\let\csname#1\endcsname \relax
7394310490Scy      \let\definedummyword\unmacrodo
7395174294Sobrien      \xdef\macrolist{\macrolist}%
739682794Sobrien    \endgroup
739742629Sobrien  \else
739882794Sobrien    \errmessage{Macro #1 not defined}%
739942629Sobrien  \fi
740042629Sobrien}
740142629Sobrien
7402174294Sobrien% Called by \do from \dounmacro on each macro.  The idea is to omit any
7403174294Sobrien% macro definitions that have been changed to \relax.
7404174294Sobrien%
7405174294Sobrien\def\unmacrodo#1{%
7406310490Scy  \ifx #1\relax
7407174294Sobrien    % remove this
7408174294Sobrien  \else
7409310490Scy    \noexpand\definedummyword \noexpand#1%
7410174294Sobrien  \fi
7411174294Sobrien}
7412174294Sobrien
741342629Sobrien% This makes use of the obscure feature that if the last token of a
741442629Sobrien% <parameter list> is #, then the preceding argument is delimited by
741542629Sobrien% an opening brace, and that opening brace is not consumed.
741642629Sobrien\def\getargs#1{\getargsxxx#1{}}
741742629Sobrien\def\getargsxxx#1#{\getmacname #1 \relax\getmacargs}
7418310490Scy\def\getmacname#1 #2\relax{\macname={#1}}
741942629Sobrien\def\getmacargs#1{\def\argl{#1}}
742042629Sobrien
7421310490Scy% For macro processing make @ a letter so that we can make Texinfo private macro names.
7422310490Scy\edef\texiatcatcode{\the\catcode`\@}
7423310490Scy\catcode `@=11\relax
7424310490Scy
742542629Sobrien% Parse the optional {params} list.  Set up \paramno and \paramlist
7426310490Scy% so \defmacro knows what to do.  Define \macarg.BLAH for each BLAH
7427310490Scy% in the params list to some hook where the argument si to be expanded.  If
7428310490Scy% there are less than 10 arguments that hook is to be replaced by ##N where N
7429310490Scy% is the position in that list, that is to say the macro arguments are to be
7430310490Scy% defined `a la TeX in the macro body.  
7431310490Scy%
743242629Sobrien% That gets used by \mbodybackslash (above).
7433310490Scy%
743442629Sobrien% We need to get `macro parameter char #' into several definitions.
7435310490Scy% The technique used is stolen from LaTeX: let \hash be something
743642629Sobrien% unexpandable, insert that wherever you need a #, and then redefine
743742629Sobrien% it to # just before using the token list produced.
743842629Sobrien%
743942629Sobrien% The same technique is used to protect \eatspaces till just before
744042629Sobrien% the macro is used.
7441310490Scy%
7442310490Scy% If there are 10 or more arguments, a different technique is used, where the
7443310490Scy% hook remains in the body, and when macro is to be expanded the body is
7444310490Scy% processed again to replace the arguments.
7445310490Scy%
7446310490Scy% In that case, the hook is \the\toks N-1, and we simply set \toks N-1 to the
7447310490Scy% argument N value and then \edef  the body (nothing else will expand because of
7448310490Scy% the catcode regime underwhich the body was input).
7449310490Scy%
7450310490Scy% If you compile with TeX (not eTeX), and you have macros with 10 or more
7451310490Scy% arguments, you need that no macro has more than 256 arguments, otherwise an
7452310490Scy% error is produced.
7453310490Scy\def\parsemargdef#1;{%
7454310490Scy  \paramno=0\def\paramlist{}%
7455310490Scy  \let\hash\relax
7456310490Scy  \let\xeatspaces\relax
7457310490Scy  \parsemargdefxxx#1,;,%
7458310490Scy  % In case that there are 10 or more arguments we parse again the arguments
7459310490Scy  % list to set new definitions for the \macarg.BLAH macros corresponding to
7460310490Scy  % each BLAH argument. It was anyhow needed to parse already once this list
7461310490Scy  % in order to count the arguments, and as macros with at most 9 arguments
7462310490Scy  % are by far more frequent than macro with 10 or more arguments, defining
7463310490Scy  % twice the \macarg.BLAH macros does not cost too much processing power.
7464310490Scy  \ifnum\paramno<10\relax\else
7465310490Scy    \paramno0\relax
7466310490Scy    \parsemmanyargdef@@#1,;,% 10 or more arguments
7467310490Scy  \fi
7468310490Scy}
746942629Sobrien\def\parsemargdefxxx#1,{%
747042629Sobrien  \if#1;\let\next=\relax
747142629Sobrien  \else \let\next=\parsemargdefxxx
7472310490Scy    \advance\paramno by 1
747342629Sobrien    \expandafter\edef\csname macarg.\eatspaces{#1}\endcsname
747442629Sobrien        {\xeatspaces{\hash\the\paramno}}%
747542629Sobrien    \edef\paramlist{\paramlist\hash\the\paramno,}%
747642629Sobrien  \fi\next}
747742629Sobrien
7478310490Scy\def\parsemmanyargdef@@#1,{%
7479310490Scy  \if#1;\let\next=\relax
7480310490Scy  \else 
7481310490Scy    \let\next=\parsemmanyargdef@@
7482310490Scy    \edef\tempb{\eatspaces{#1}}%
7483310490Scy    \expandafter\def\expandafter\tempa
7484310490Scy       \expandafter{\csname macarg.\tempb\endcsname}%
7485310490Scy    % Note that we need some extra \noexpand\noexpand, this is because we
7486310490Scy    % don't want \the  to be expanded in the \parsermacbody  as it uses an
7487310490Scy    % \xdef .
7488310490Scy    \expandafter\edef\tempa
7489310490Scy      {\noexpand\noexpand\noexpand\the\toks\the\paramno}%
7490310490Scy    \advance\paramno by 1\relax
7491310490Scy  \fi\next}
7492310490Scy
749342629Sobrien% These two commands read recursive and nonrecursive macro bodies.
749442629Sobrien% (They're different since rec and nonrec macros end differently.)
7495310490Scy%
749642629Sobrien
7497310490Scy\catcode `\@\texiatcatcode
749842629Sobrien\long\def\parsemacbody#1@end macro%
749942629Sobrien{\xdef\temp{\eatcr{#1}}\endgroup\defmacro}%
750042629Sobrien\long\def\parsermacbody#1@end rmacro%
750142629Sobrien{\xdef\temp{\eatcr{#1}}\endgroup\defmacro}%
7502310490Scy\catcode `\@=11\relax
750342629Sobrien
7504310490Scy\let\endargs@\relax
7505310490Scy\let\nil@\relax
7506310490Scy\def\nilm@{\nil@}%
7507310490Scy\long\def\nillm@{\nil@}%
7508310490Scy
7509310490Scy% This macro is expanded during the Texinfo macro expansion, not during its
7510310490Scy% definition.  It gets all the arguments values and assigns them to macros
7511310490Scy% macarg.ARGNAME
7512310490Scy%
7513310490Scy% #1 is the macro name
7514310490Scy% #2 is the list of argument names
7515310490Scy% #3 is the list of argument values
7516310490Scy\def\getargvals@#1#2#3{%
7517310490Scy  \def\macargdeflist@{}%
7518310490Scy  \def\saveparamlist@{#2}% Need to keep a copy for parameter expansion.
7519310490Scy  \def\paramlist{#2,\nil@}%
7520310490Scy  \def\macroname{#1}%
7521310490Scy  \begingroup
7522310490Scy  \macroargctxt
7523310490Scy  \def\argvaluelist{#3,\nil@}%
7524310490Scy  \def\@tempa{#3}%
7525310490Scy  \ifx\@tempa\empty
7526310490Scy    \setemptyargvalues@
7527310490Scy  \else
7528310490Scy    \getargvals@@
7529310490Scy  \fi
7530310490Scy}
7531310490Scy
7532310490Scy% 
7533310490Scy\def\getargvals@@{%
7534310490Scy  \ifx\paramlist\nilm@
7535310490Scy      % Some sanity check needed here that \argvaluelist is also empty.
7536310490Scy      \ifx\argvaluelist\nillm@
7537310490Scy      \else
7538310490Scy        \errhelp = \EMsimple
7539310490Scy        \errmessage{Too many arguments in macro `\macroname'!}%
7540310490Scy      \fi
7541310490Scy      \let\next\macargexpandinbody@
7542310490Scy  \else
7543310490Scy    \ifx\argvaluelist\nillm@
7544310490Scy       % No more arguments values passed to macro.  Set remaining named-arg
7545310490Scy       % macros to empty.
7546310490Scy       \let\next\setemptyargvalues@
7547310490Scy    \else
7548310490Scy      % pop current arg name into \@tempb
7549310490Scy      \def\@tempa##1{\pop@{\@tempb}{\paramlist}##1\endargs@}%
7550310490Scy      \expandafter\@tempa\expandafter{\paramlist}%
7551310490Scy       % pop current argument value into \@tempc
7552310490Scy      \def\@tempa##1{\longpop@{\@tempc}{\argvaluelist}##1\endargs@}%
7553310490Scy      \expandafter\@tempa\expandafter{\argvaluelist}%
7554310490Scy       % Here \@tempb is the current arg name and \@tempc is the current arg value.
7555310490Scy       % First place the new argument macro definition into \@tempd
7556310490Scy       \expandafter\macname\expandafter{\@tempc}%
7557310490Scy       \expandafter\let\csname macarg.\@tempb\endcsname\relax
7558310490Scy       \expandafter\def\expandafter\@tempe\expandafter{%
7559310490Scy         \csname macarg.\@tempb\endcsname}%
7560310490Scy       \edef\@tempd{\long\def\@tempe{\the\macname}}%
7561310490Scy       \push@\@tempd\macargdeflist@
7562310490Scy       \let\next\getargvals@@
7563310490Scy    \fi
7564310490Scy  \fi
7565310490Scy  \next
7566310490Scy}
7567310490Scy
7568310490Scy\def\push@#1#2{%
7569310490Scy  \expandafter\expandafter\expandafter\def
7570310490Scy  \expandafter\expandafter\expandafter#2%
7571310490Scy  \expandafter\expandafter\expandafter{%
7572310490Scy  \expandafter#1#2}%
7573310490Scy}
7574310490Scy
7575310490Scy% Replace arguments by their values in the macro body, and place the result
7576310490Scy% in macro \@tempa
7577310490Scy\def\macvalstoargs@{%
7578310490Scy  %  To do this we use the property that token registers that are \the'ed
7579310490Scy  % within an \edef  expand only once. So we are going to place all argument
7580310490Scy  % values into respective token registers.
7581310490Scy  %
7582310490Scy  % First we save the token context, and initialize argument numbering.
7583310490Scy  \begingroup
7584310490Scy    \paramno0\relax
7585310490Scy    % Then, for each argument number #N, we place the corresponding argument
7586310490Scy    % value into a new token list register \toks#N
7587310490Scy    \expandafter\putargsintokens@\saveparamlist@,;,%
7588310490Scy    % Then, we expand the body so that argument are replaced by their
7589310490Scy    % values. The trick for values not to be expanded themselves is that they
7590310490Scy    % are within tokens and that tokens expand only once in an \edef .
7591310490Scy    \edef\@tempc{\csname mac.\macroname .body\endcsname}%
7592310490Scy    % Now we restore the token stack pointer to free the token list registers
7593310490Scy    % which we have used, but we make sure that expanded body is saved after
7594310490Scy    % group.
7595310490Scy    \expandafter
7596310490Scy  \endgroup
7597310490Scy  \expandafter\def\expandafter\@tempa\expandafter{\@tempc}%
7598310490Scy  }
7599310490Scy
7600310490Scy\def\macargexpandinbody@{% 
7601310490Scy  %% Define the named-macro outside of this group and then close this group. 
7602310490Scy  \expandafter
7603310490Scy  \endgroup
7604310490Scy  \macargdeflist@
7605310490Scy  % First the replace in body the macro arguments by their values, the result
7606310490Scy  % is in \@tempa .
7607310490Scy  \macvalstoargs@
7608310490Scy  % Then we point at the \norecurse or \gobble (for recursive) macro value
7609310490Scy  % with \@tempb .
7610310490Scy  \expandafter\let\expandafter\@tempb\csname mac.\macroname .recurse\endcsname
7611310490Scy  % Depending on whether it is recursive or not, we need some tailing
7612310490Scy  % \egroup .
7613310490Scy  \ifx\@tempb\gobble
7614310490Scy     \let\@tempc\relax
7615310490Scy  \else
7616310490Scy     \let\@tempc\egroup
7617310490Scy  \fi
7618310490Scy  % And now we do the real job:
7619310490Scy  \edef\@tempd{\noexpand\@tempb{\macroname}\noexpand\scanmacro{\@tempa}\@tempc}%
7620310490Scy  \@tempd
7621310490Scy}
7622310490Scy
7623310490Scy\def\putargsintokens@#1,{%
7624310490Scy  \if#1;\let\next\relax
7625310490Scy  \else
7626310490Scy    \let\next\putargsintokens@
7627310490Scy    % First we allocate the new token list register, and give it a temporary
7628310490Scy    % alias \@tempb .
7629310490Scy    \toksdef\@tempb\the\paramno
7630310490Scy    % Then we place the argument value into that token list register.
7631310490Scy    \expandafter\let\expandafter\@tempa\csname macarg.#1\endcsname
7632310490Scy    \expandafter\@tempb\expandafter{\@tempa}%
7633310490Scy    \advance\paramno by 1\relax
7634310490Scy  \fi
7635310490Scy  \next
7636310490Scy}
7637310490Scy
7638310490Scy% Save the token stack pointer into macro #1
7639310490Scy\def\texisavetoksstackpoint#1{\edef#1{\the\@cclvi}}
7640310490Scy% Restore the token stack pointer from number in macro #1
7641310490Scy\def\texirestoretoksstackpoint#1{\expandafter\mathchardef\expandafter\@cclvi#1\relax}
7642310490Scy% newtoks that can be used non \outer .
7643310490Scy\def\texinonouternewtoks{\alloc@ 5\toks \toksdef \@cclvi}
7644310490Scy
7645310490Scy% Tailing missing arguments are set to empty
7646310490Scy\def\setemptyargvalues@{%
7647310490Scy  \ifx\paramlist\nilm@
7648310490Scy    \let\next\macargexpandinbody@
7649310490Scy  \else
7650310490Scy    \expandafter\setemptyargvaluesparser@\paramlist\endargs@
7651310490Scy    \let\next\setemptyargvalues@
7652310490Scy  \fi
7653310490Scy  \next
7654310490Scy}
7655310490Scy
7656310490Scy\def\setemptyargvaluesparser@#1,#2\endargs@{%
7657310490Scy  \expandafter\def\expandafter\@tempa\expandafter{%
7658310490Scy    \expandafter\def\csname macarg.#1\endcsname{}}%
7659310490Scy  \push@\@tempa\macargdeflist@
7660310490Scy  \def\paramlist{#2}%
7661310490Scy}
7662310490Scy
7663310490Scy% #1 is the element target macro
7664310490Scy% #2 is the list macro
7665310490Scy% #3,#4\endargs@ is the list value
7666310490Scy\def\pop@#1#2#3,#4\endargs@{%
7667310490Scy   \def#1{#3}%
7668310490Scy   \def#2{#4}%
7669310490Scy}
7670310490Scy\long\def\longpop@#1#2#3,#4\endargs@{%
7671310490Scy   \long\def#1{#3}%
7672310490Scy   \long\def#2{#4}%
7673310490Scy}
7674310490Scy
7675310490Scy% This defines a Texinfo @macro. There are eight cases: recursive and
7676310490Scy% nonrecursive macros of zero, one, up to nine, and many arguments.
767742629Sobrien% Much magic with \expandafter here.
767842629Sobrien% \xdef is used so that macro definitions will survive the file
767942629Sobrien% they're defined in; @include reads the file inside a group.
7680310490Scy%
768142629Sobrien\def\defmacro{%
768242629Sobrien  \let\hash=##% convert placeholders to macro parameter chars
768342629Sobrien  \ifrecursive
768442629Sobrien    \ifcase\paramno
768542629Sobrien    % 0
768642629Sobrien      \expandafter\xdef\csname\the\macname\endcsname{%
768742629Sobrien        \noexpand\scanmacro{\temp}}%
768842629Sobrien    \or % 1
768942629Sobrien      \expandafter\xdef\csname\the\macname\endcsname{%
769042629Sobrien         \bgroup\noexpand\macroargctxt
769182794Sobrien         \noexpand\braceorline
769282794Sobrien         \expandafter\noexpand\csname\the\macname xxx\endcsname}%
769342629Sobrien      \expandafter\xdef\csname\the\macname xxx\endcsname##1{%
769442629Sobrien         \egroup\noexpand\scanmacro{\temp}}%
7695310490Scy    \else
7696310490Scy      \ifnum\paramno<10\relax % at most 9
7697310490Scy        \expandafter\xdef\csname\the\macname\endcsname{%
7698310490Scy           \bgroup\noexpand\macroargctxt
7699310490Scy           \noexpand\csname\the\macname xx\endcsname}%
7700310490Scy        \expandafter\xdef\csname\the\macname xx\endcsname##1{%
7701310490Scy            \expandafter\noexpand\csname\the\macname xxx\endcsname ##1,}%
7702310490Scy        \expandafter\expandafter
7703310490Scy        \expandafter\xdef
7704310490Scy        \expandafter\expandafter
7705310490Scy          \csname\the\macname xxx\endcsname
7706310490Scy            \paramlist{\egroup\noexpand\scanmacro{\temp}}%
7707310490Scy      \else % 10 or more
7708310490Scy        \expandafter\xdef\csname\the\macname\endcsname{%
7709310490Scy          \noexpand\getargvals@{\the\macname}{\argl}%
7710310490Scy        }%    
7711310490Scy        \global\expandafter\let\csname mac.\the\macname .body\endcsname\temp
7712310490Scy        \global\expandafter\let\csname mac.\the\macname .recurse\endcsname\gobble
7713310490Scy      \fi
771442629Sobrien    \fi
771542629Sobrien  \else
771642629Sobrien    \ifcase\paramno
771742629Sobrien    % 0
771842629Sobrien      \expandafter\xdef\csname\the\macname\endcsname{%
771942629Sobrien        \noexpand\norecurse{\the\macname}%
772042629Sobrien        \noexpand\scanmacro{\temp}\egroup}%
772142629Sobrien    \or % 1
772242629Sobrien      \expandafter\xdef\csname\the\macname\endcsname{%
772342629Sobrien         \bgroup\noexpand\macroargctxt
772482794Sobrien         \noexpand\braceorline
772582794Sobrien         \expandafter\noexpand\csname\the\macname xxx\endcsname}%
772642629Sobrien      \expandafter\xdef\csname\the\macname xxx\endcsname##1{%
772742629Sobrien        \egroup
772842629Sobrien        \noexpand\norecurse{\the\macname}%
772942629Sobrien        \noexpand\scanmacro{\temp}\egroup}%
7730310490Scy    \else % at most 9
7731310490Scy      \ifnum\paramno<10\relax
7732310490Scy        \expandafter\xdef\csname\the\macname\endcsname{%
7733310490Scy           \bgroup\noexpand\macroargctxt
7734310490Scy           \expandafter\noexpand\csname\the\macname xx\endcsname}%
7735310490Scy        \expandafter\xdef\csname\the\macname xx\endcsname##1{%
7736310490Scy            \expandafter\noexpand\csname\the\macname xxx\endcsname ##1,}%
7737310490Scy        \expandafter\expandafter
7738310490Scy        \expandafter\xdef
7739310490Scy        \expandafter\expandafter
7740310490Scy        \csname\the\macname xxx\endcsname
7741310490Scy        \paramlist{%
7742310490Scy            \egroup
7743310490Scy            \noexpand\norecurse{\the\macname}%
7744310490Scy            \noexpand\scanmacro{\temp}\egroup}%
7745310490Scy      \else % 10 or more:
7746310490Scy        \expandafter\xdef\csname\the\macname\endcsname{%
7747310490Scy          \noexpand\getargvals@{\the\macname}{\argl}%
7748310490Scy        }%
7749310490Scy        \global\expandafter\let\csname mac.\the\macname .body\endcsname\temp
7750310490Scy        \global\expandafter\let\csname mac.\the\macname .recurse\endcsname\norecurse
7751310490Scy      \fi
775242629Sobrien    \fi
775342629Sobrien  \fi}
775442629Sobrien
7755310490Scy\catcode `\@\texiatcatcode\relax
7756310490Scy
775742629Sobrien\def\norecurse#1{\bgroup\cslet{#1}{macsave.#1}}
775842629Sobrien
775942629Sobrien% \braceorline decides whether the next nonwhitespace character is a
776042629Sobrien% {.  If so it reads up to the closing }, if not, it reads the whole
776142629Sobrien% line.  Whatever was read is then fed to the next control sequence
7762310490Scy% as an argument (by \parsebrace or \parsearg).
7763310490Scy% 
7764310490Scy\def\braceorline#1{\let\macnamexxx=#1\futurelet\nchar\braceorlinexxx}
776542629Sobrien\def\braceorlinexxx{%
776642629Sobrien  \ifx\nchar\bgroup\else
776782794Sobrien    \expandafter\parsearg
7768310490Scy  \fi \macnamexxx}
776942629Sobrien
777042629Sobrien
777182794Sobrien% @alias.
777282794Sobrien% We need some trickery to remove the optional spaces around the equal
7773310490Scy% sign.  Make them active and then expand them all to nothing.
7774310490Scy%
7775174294Sobrien\def\alias{\parseargusing\obeyspaces\aliasxxx}
777682794Sobrien\def\aliasxxx #1{\aliasyyy#1\relax}
7777174294Sobrien\def\aliasyyy #1=#2\relax{%
7778174294Sobrien  {%
7779174294Sobrien    \expandafter\let\obeyedspace=\empty
7780310490Scy    \addtomacrolist{#1}%
7781174294Sobrien    \xdef\next{\global\let\makecsname{#1}=\makecsname{#2}}%
7782174294Sobrien  }%
7783174294Sobrien  \next
7784174294Sobrien}
778582794Sobrien
778682794Sobrien
778742629Sobrien\message{cross references,}
778882794Sobrien
778942629Sobrien\newwrite\auxfile
779042629Sobrien\newif\ifhavexrefs    % True if xref values are known.
779138494Sobrien\newif\ifwarnedxrefs  % True if we warned once that they aren't known.
779238494Sobrien
779342629Sobrien% @inforef is relatively simple.
779438494Sobrien\def\inforef #1{\inforefzzz #1,,,,**}
7795310490Scy\def\inforefzzz #1,#2,#3,#4**{%
7796310490Scy  \putwordSee{} \putwordInfo{} \putwordfile{} \file{\ignorespaces #3{}},
779738494Sobrien  node \samp{\ignorespaces#1{}}}
779838494Sobrien
7799174294Sobrien% @node's only job in TeX is to define \lastnode, which is used in
7800174294Sobrien% cross-references.  The @node line might or might not have commas, and
7801174294Sobrien% might or might not have spaces before the first comma, like:
7802174294Sobrien% @node foo , bar , ...
7803174294Sobrien% We don't want such trailing spaces in the node name.
7804174294Sobrien%
7805174294Sobrien\parseargdef\node{\checkenv{}\donode #1 ,\finishnodeparse}
7806174294Sobrien%
7807174294Sobrien% also remove a trailing comma, in case of something like this:
7808174294Sobrien% @node Help-Cross,  ,  , Cross-refs
7809174294Sobrien\def\donode#1 ,#2\finishnodeparse{\dodonode #1,\finishnodeparse}
7810174294Sobrien\def\dodonode#1,#2\finishnodeparse{\gdef\lastnode{#1}}
7811174294Sobrien
781242629Sobrien\let\nwnode=\node
7813174294Sobrien\let\lastnode=\empty
781438494Sobrien
7815174294Sobrien% Write a cross-reference definition for the current node.  #1 is the
7816174294Sobrien% type (Ynumbered, Yappendix, Ynothing).
7817174294Sobrien%
7818174294Sobrien\def\donoderef#1{%
7819174294Sobrien  \ifx\lastnode\empty\else
7820174294Sobrien    \setref{\lastnode}{#1}%
7821174294Sobrien    \global\let\lastnode=\empty
782242629Sobrien  \fi
782342629Sobrien}
782438494Sobrien
782542629Sobrien% @anchor{NAME} -- define xref target at arbitrary point.
782682794Sobrien%
782782794Sobrien\newcount\savesfregister
7828174294Sobrien%
7829174294Sobrien\def\savesf{\relax \ifhmode \savesfregister=\spacefactor \fi}
7830174294Sobrien\def\restoresf{\relax \ifhmode \spacefactor=\savesfregister \fi}
7831174294Sobrien\def\anchor#1{\savesf \setref{#1}{Ynothing}\restoresf \ignorespaces}
783238494Sobrien
7833174294Sobrien% \setref{NAME}{SNT} defines a cross-reference point NAME (a node or an
7834174294Sobrien% anchor), which consists of three parts:
7835310490Scy% 1) NAME-title - the current sectioning name taken from \lastsection,
7836174294Sobrien%                 or the anchor name.
7837174294Sobrien% 2) NAME-snt   - section number and type, passed as the SNT arg, or
7838174294Sobrien%                 empty for anchors.
7839174294Sobrien% 3) NAME-pg    - the page number.
784082794Sobrien%
7841174294Sobrien% This is called from \donoderef, \anchor, and \dofloat.  In the case of
7842174294Sobrien% floats, there is an additional part, which is not written here:
7843174294Sobrien% 4) NAME-lof   - the text as it should appear in a @listoffloats.
7844174294Sobrien%
7845174294Sobrien\def\setref#1#2{%
784682794Sobrien  \pdfmkdest{#1}%
7847174294Sobrien  \iflinks
7848174294Sobrien    {%
7849174294Sobrien      \atdummies  % preserve commands, but don't expand them
7850174294Sobrien      \edef\writexrdef##1##2{%
7851174294Sobrien	\write\auxfile{@xrdef{#1-% #1 of \setref, expanded by the \edef
7852174294Sobrien	  ##1}{##2}}% these are parameters of \writexrdef
7853174294Sobrien      }%
7854310490Scy      \toks0 = \expandafter{\lastsection}%
7855174294Sobrien      \immediate \writexrdef{title}{\the\toks0 }%
7856174294Sobrien      \immediate \writexrdef{snt}{\csname #2\endcsname}% \Ynumbered etc.
7857310490Scy      \safewhatsit{\writexrdef{pg}{\folio}}% will be written later, at \shipout
7858174294Sobrien    }%
7859174294Sobrien  \fi
7860174294Sobrien}
786142629Sobrien
7862310490Scy% @xrefautosectiontitle on|off says whether @section(ing) names are used
7863310490Scy% automatically in xrefs, if the third arg is not explicitly specified.
7864310490Scy% This was provided as a "secret" @set xref-automatic-section-title
7865310490Scy% variable, now it's official.
7866310490Scy% 
7867310490Scy\parseargdef\xrefautomaticsectiontitle{%
7868310490Scy  \def\temp{#1}%
7869310490Scy  \ifx\temp\onword
7870310490Scy    \expandafter\let\csname SETxref-automatic-section-title\endcsname
7871310490Scy      = \empty
7872310490Scy  \else\ifx\temp\offword
7873310490Scy    \expandafter\let\csname SETxref-automatic-section-title\endcsname
7874310490Scy      = \relax
7875310490Scy  \else
7876310490Scy    \errhelp = \EMsimple
7877310490Scy    \errmessage{Unknown @xrefautomaticsectiontitle value `\temp',
7878310490Scy                must be on|off}%
7879310490Scy  \fi\fi
7880310490Scy}
7881310490Scy
7882310490Scy% 
788342629Sobrien% @xref, @pxref, and @ref generate cross-references.  For \xrefX, #1 is
788442629Sobrien% the node name, #2 the name of the Info cross-reference, #3 the printed
788542629Sobrien% node name, #4 the name of the Info file, #5 the name of the printed
788642629Sobrien% manual.  All but the node name can be omitted.
788738494Sobrien%
788838494Sobrien\def\pxref#1{\putwordsee{} \xrefX[#1,,,,,,,]}
788938494Sobrien\def\xref#1{\putwordSee{} \xrefX[#1,,,,,,,]}
789038494Sobrien\def\ref#1{\xrefX[#1,,,,,,,]}
7891310490Scy%
7892310490Scy\newbox\toprefbox
7893310490Scy\newbox\printedrefnamebox
7894310490Scy\newbox\infofilenamebox
7895310490Scy\newbox\printedmanualbox
7896310490Scy%
789738494Sobrien\def\xrefX[#1,#2,#3,#4,#5,#6]{\begingroup
789882794Sobrien  \unsepspaces
7899310490Scy  %
7900310490Scy  % Get args without leading/trailing spaces.
7901310490Scy  \def\printedrefname{\ignorespaces #3}%
7902310490Scy  \setbox\printedrefnamebox = \hbox{\printedrefname\unskip}%
7903310490Scy  %
7904310490Scy  \def\infofilename{\ignorespaces #4}%
7905310490Scy  \setbox\infofilenamebox = \hbox{\infofilename\unskip}%
7906310490Scy  %
790738494Sobrien  \def\printedmanual{\ignorespaces #5}%
7908310490Scy  \setbox\printedmanualbox  = \hbox{\printedmanual\unskip}%
7909310490Scy  %
7910310490Scy  % If the printed reference name (arg #3) was not explicitly given in
7911310490Scy  % the @xref, figure out what we want to use.
7912310490Scy  \ifdim \wd\printedrefnamebox = 0pt
791338494Sobrien    % No printed node name was explicitly given.
7914310490Scy    \expandafter\ifx\csname SETxref-automatic-section-title\endcsname \relax
7915310490Scy      % Not auto section-title: use node name inside the square brackets.
7916174294Sobrien      \def\printedrefname{\ignorespaces #1}%
791738494Sobrien    \else
7918310490Scy      % Auto section-title: use chapter/section title inside
7919310490Scy      % the square brackets if we have it.
7920310490Scy      \ifdim \wd\printedmanualbox > 0pt
7921310490Scy        % It is in another manual, so we don't have it; use node name.
7922174294Sobrien        \def\printedrefname{\ignorespaces #1}%
792338494Sobrien      \else
792438494Sobrien        \ifhavexrefs
7925310490Scy          % We (should) know the real title if we have the xref values.
7926174294Sobrien          \def\printedrefname{\refx{#1-title}{}}%
792738494Sobrien        \else
792838494Sobrien          % Otherwise just copy the Info node name.
7929174294Sobrien          \def\printedrefname{\ignorespaces #1}%
793038494Sobrien        \fi%
793138494Sobrien      \fi
793238494Sobrien    \fi
793338494Sobrien  \fi
793438494Sobrien  %
7935174294Sobrien  % Make link in pdf output.
793682794Sobrien  \ifpdf
7937310490Scy    {\indexnofonts
7938310490Scy     \turnoffactive
7939310490Scy     \makevalueexpandable
7940310490Scy     % This expands tokens, so do it after making catcode changes, so _
7941310490Scy     % etc. don't get their TeX definitions.  This ignores all spaces in
7942310490Scy     % #4, including (wrongly) those in the middle of the filename.
7943310490Scy     \getfilename{#4}%
7944310490Scy     %
7945310490Scy     % This (wrongly) does not take account of leading or trailing
7946310490Scy     % spaces in #1, which should be ignored.
7947310490Scy     \edef\pdfxrefdest{#1}%
7948310490Scy     \ifx\pdfxrefdest\empty
7949310490Scy       \def\pdfxrefdest{Top}% no empty targets
7950310490Scy     \else
7951310490Scy       \txiescapepdf\pdfxrefdest  % escape PDF special chars
7952310490Scy     \fi
7953310490Scy     %
7954310490Scy     \leavevmode
7955310490Scy     \startlink attr{/Border [0 0 0]}%
795682794Sobrien     \ifnum\filenamelength>0
7957310490Scy       goto file{\the\filename.pdf} name{\pdfxrefdest}%
795882794Sobrien     \else
7959310490Scy       goto name{\pdfmkpgn{\pdfxrefdest}}%
796082794Sobrien     \fi
796182794Sobrien    }%
7962310490Scy    \setcolor{\linkcolor}%
796382794Sobrien  \fi
796482794Sobrien  %
7965174294Sobrien  % Float references are printed completely differently: "Figure 1.2"
7966174294Sobrien  % instead of "[somenode], p.3".  We distinguish them by the
7967174294Sobrien  % LABEL-title being set to a magic string.
7968174294Sobrien  {%
7969174294Sobrien    % Have to otherify everything special to allow the \csname to
7970174294Sobrien    % include an _ in the xref name, etc.
7971174294Sobrien    \indexnofonts
7972174294Sobrien    \turnoffactive
7973174294Sobrien    \expandafter\global\expandafter\let\expandafter\Xthisreftitle
7974174294Sobrien      \csname XR#1-title\endcsname
7975174294Sobrien  }%
7976174294Sobrien  \iffloat\Xthisreftitle
7977174294Sobrien    % If the user specified the print name (third arg) to the ref,
7978174294Sobrien    % print it instead of our usual "Figure 1.2".
7979310490Scy    \ifdim\wd\printedrefnamebox = 0pt
7980310490Scy      \refx{#1-snt}{}%
7981174294Sobrien    \else
7982174294Sobrien      \printedrefname
7983174294Sobrien    \fi
7984174294Sobrien    %
7985310490Scy    % If the user also gave the printed manual name (fifth arg), append
7986174294Sobrien    % "in MANUALNAME".
7987310490Scy    \ifdim \wd\printedmanualbox > 0pt
7988174294Sobrien      \space \putwordin{} \cite{\printedmanual}%
7989174294Sobrien    \fi
799038494Sobrien  \else
7991174294Sobrien    % node/anchor (non-float) references.
7992310490Scy    % 
7993310490Scy    % If we use \unhbox to print the node names, TeX does not insert
7994310490Scy    % empty discretionaries after hyphens, which means that it will not
7995310490Scy    % find a line break at a hyphen in a node names.  Since some manuals
7996310490Scy    % are best written with fairly long node names, containing hyphens,
7997310490Scy    % this is a loss.  Therefore, we give the text of the node name
7998310490Scy    % again, so it is as if TeX is seeing it for the first time.
7999310490Scy    % 
8000310490Scy    \ifdim \wd\printedmanualbox > 0pt
8001310490Scy      % Cross-manual reference with a printed manual name.
8002310490Scy      % 
8003310490Scy      \crossmanualxref{\cite{\printedmanual\unskip}}%
8004174294Sobrien    %
8005310490Scy    \else\ifdim \wd\infofilenamebox > 0pt
8006310490Scy      % Cross-manual reference with only an info filename (arg 4), no
8007310490Scy      % printed manual name (arg 5).  This is essentially the same as
8008310490Scy      % the case above; we output the filename, since we have nothing else.
8009310490Scy      % 
8010310490Scy      \crossmanualxref{\code{\infofilename\unskip}}%
8011310490Scy    %
8012174294Sobrien    \else
8013310490Scy      % Reference within this manual.
8014310490Scy      %
8015174294Sobrien      % _ (for example) has to be the character _ for the purposes of the
8016174294Sobrien      % control sequence corresponding to the node, but it has to expand
8017174294Sobrien      % into the usual \leavevmode...\vrule stuff for purposes of
8018174294Sobrien      % printing. So we \turnoffactive for the \refx-snt, back on for the
8019174294Sobrien      % printing, back off for the \refx-pg.
8020310490Scy      {\turnoffactive
8021174294Sobrien       % Only output a following space if the -snt ref is nonempty; for
8022174294Sobrien       % @unnumbered and @anchor, it won't be.
8023174294Sobrien       \setbox2 = \hbox{\ignorespaces \refx{#1-snt}{}}%
8024174294Sobrien       \ifdim \wd2 > 0pt \refx{#1-snt}\space\fi
8025174294Sobrien      }%
8026310490Scy      % output the `[mynode]' via the macro below so it can be overridden.
8027174294Sobrien      \xrefprintnodename\printedrefname
8028174294Sobrien      %
8029174294Sobrien      % But we always want a comma and a space:
8030174294Sobrien      ,\space
8031174294Sobrien      %
8032174294Sobrien      % output the `page 3'.
8033310490Scy      \turnoffactive \putwordpage\tie\refx{#1-pg}{}%
8034310490Scy    \fi\fi
803538494Sobrien  \fi
803682794Sobrien  \endlink
803738494Sobrien\endgroup}
803838494Sobrien
8039310490Scy% Output a cross-manual xref to #1.  Used just above (twice).
8040310490Scy% 
8041310490Scy% Only include the text "Section ``foo'' in" if the foo is neither
8042310490Scy% missing or Top.  Thus, @xref{,,,foo,The Foo Manual} outputs simply
8043310490Scy% "see The Foo Manual", the idea being to refer to the whole manual.
8044310490Scy% 
8045310490Scy% But, this being TeX, we can't easily compare our node name against the
8046310490Scy% string "Top" while ignoring the possible spaces before and after in
8047310490Scy% the input.  By adding the arbitrary 7sp below, we make it much less
8048310490Scy% likely that a real node name would have the same width as "Top" (e.g.,
8049310490Scy% in a monospaced font).  Hopefully it will never happen in practice.
8050310490Scy% 
8051310490Scy% For the same basic reason, we retypeset the "Top" at every
8052310490Scy% reference, since the current font is indeterminate.
8053310490Scy% 
8054310490Scy\def\crossmanualxref#1{%
8055310490Scy  \setbox\toprefbox = \hbox{Top\kern7sp}%
8056310490Scy  \setbox2 = \hbox{\ignorespaces \printedrefname \unskip \kern7sp}%
8057310490Scy  \ifdim \wd2 > 7sp  % nonempty?
8058310490Scy    \ifdim \wd2 = \wd\toprefbox \else  % same as Top?
8059310490Scy      \putwordSection{} ``\printedrefname'' \putwordin{}\space
8060310490Scy    \fi
8061310490Scy  \fi
8062310490Scy  #1%
8063310490Scy}
8064310490Scy
8065174294Sobrien% This macro is called from \xrefX for the `[nodename]' part of xref
8066174294Sobrien% output.  It's a separate macro only so it can be changed more easily,
8067174294Sobrien% since square brackets don't work well in some documents.  Particularly
8068174294Sobrien% one that Bob is working on :).
8069174294Sobrien%
8070174294Sobrien\def\xrefprintnodename#1{[#1]}
807138494Sobrien
8072174294Sobrien% Things referred to by \setref.
8073174294Sobrien%
8074174294Sobrien\def\Ynothing{}
8075174294Sobrien\def\Yomitfromtoc{}
8076174294Sobrien\def\Ynumbered{%
8077174294Sobrien  \ifnum\secno=0
8078174294Sobrien    \putwordChapter@tie \the\chapno
8079174294Sobrien  \else \ifnum\subsecno=0
8080174294Sobrien    \putwordSection@tie \the\chapno.\the\secno
8081174294Sobrien  \else \ifnum\subsubsecno=0
8082174294Sobrien    \putwordSection@tie \the\chapno.\the\secno.\the\subsecno
8083174294Sobrien  \else
8084174294Sobrien    \putwordSection@tie \the\chapno.\the\secno.\the\subsecno.\the\subsubsecno
8085174294Sobrien  \fi\fi\fi
808642629Sobrien}
8087174294Sobrien\def\Yappendix{%
8088174294Sobrien  \ifnum\secno=0
8089174294Sobrien     \putwordAppendix@tie @char\the\appendixno{}%
8090174294Sobrien  \else \ifnum\subsecno=0
8091174294Sobrien     \putwordSection@tie @char\the\appendixno.\the\secno
8092174294Sobrien  \else \ifnum\subsubsecno=0
8093174294Sobrien    \putwordSection@tie @char\the\appendixno.\the\secno.\the\subsecno
8094174294Sobrien  \else
8095174294Sobrien    \putwordSection@tie
8096174294Sobrien      @char\the\appendixno.\the\secno.\the\subsecno.\the\subsubsecno
8097174294Sobrien  \fi\fi\fi
8098174294Sobrien}
809938494Sobrien
810038494Sobrien% Define \refx{NAME}{SUFFIX} to reference a cross-reference string named NAME.
810138494Sobrien% If its value is nonempty, SUFFIX is output afterward.
8102174294Sobrien%
810338494Sobrien\def\refx#1#2{%
8104174294Sobrien  {%
8105174294Sobrien    \indexnofonts
8106174294Sobrien    \otherbackslash
8107174294Sobrien    \expandafter\global\expandafter\let\expandafter\thisrefX
8108174294Sobrien      \csname XR#1\endcsname
8109174294Sobrien  }%
8110174294Sobrien  \ifx\thisrefX\relax
811138494Sobrien    % If not defined, say something at least.
811242629Sobrien    \angleleft un\-de\-fined\angleright
811342629Sobrien    \iflinks
811442629Sobrien      \ifhavexrefs
8115310490Scy        {\toks0 = {#1}% avoid expansion of possibly-complex value
8116310490Scy         \message{\linenumber Undefined cross reference `\the\toks0'.}}%
811742629Sobrien      \else
811842629Sobrien        \ifwarnedxrefs\else
811942629Sobrien          \global\warnedxrefstrue
812042629Sobrien          \message{Cross reference values unknown; you must run TeX again.}%
812142629Sobrien        \fi
812238494Sobrien      \fi
812338494Sobrien    \fi
812438494Sobrien  \else
812538494Sobrien    % It's defined, so just use it.
8126174294Sobrien    \thisrefX
812738494Sobrien  \fi
812838494Sobrien  #2% Output the suffix in any case.
812938494Sobrien}
813038494Sobrien
8131174294Sobrien% This is the macro invoked by entries in the aux file.  Usually it's
8132174294Sobrien% just a \def (we prepend XR to the control sequence name to avoid
8133174294Sobrien% collisions).  But if this is a float type, we have more work to do.
813482794Sobrien%
8135174294Sobrien\def\xrdef#1#2{%
8136310490Scy  {% The node name might contain 8-bit characters, which in our current
8137310490Scy   % implementation are changed to commands like @'e.  Don't let these
8138310490Scy   % mess up the control sequence name.
8139310490Scy    \indexnofonts
8140310490Scy    \turnoffactive
8141310490Scy    \xdef\safexrefname{#1}%
8142310490Scy  }%
8143174294Sobrien  %
8144310490Scy  \expandafter\gdef\csname XR\safexrefname\endcsname{#2}% remember this xref
8145310490Scy  %
8146174294Sobrien  % Was that xref control sequence that we just defined for a float?
8147310490Scy  \expandafter\iffloat\csname XR\safexrefname\endcsname
8148174294Sobrien    % it was a float, and we have the (safe) float type in \iffloattype.
8149174294Sobrien    \expandafter\let\expandafter\floatlist
8150174294Sobrien      \csname floatlist\iffloattype\endcsname
8151174294Sobrien    %
8152174294Sobrien    % Is this the first time we've seen this float type?
8153174294Sobrien    \expandafter\ifx\floatlist\relax
8154174294Sobrien      \toks0 = {\do}% yes, so just \do
8155174294Sobrien    \else
8156174294Sobrien      % had it before, so preserve previous elements in list.
8157174294Sobrien      \toks0 = \expandafter{\floatlist\do}%
8158174294Sobrien    \fi
8159174294Sobrien    %
8160174294Sobrien    % Remember this xref in the control sequence \floatlistFLOATTYPE,
8161174294Sobrien    % for later use in \listoffloats.
8162310490Scy    \expandafter\xdef\csname floatlist\iffloattype\endcsname{\the\toks0
8163310490Scy      {\safexrefname}}%
8164174294Sobrien  \fi
816542629Sobrien}
816638494Sobrien
816738494Sobrien% Read the last existing aux file, if any.  No error if none exists.
8168174294Sobrien%
8169174294Sobrien\def\tryauxfile{%
8170174294Sobrien  \openin 1 \jobname.aux
8171174294Sobrien  \ifeof 1 \else
8172310490Scy    \readdatafile{aux}%
8173174294Sobrien    \global\havexrefstrue
8174174294Sobrien  \fi
8175174294Sobrien  \closein 1
8176174294Sobrien}
8177174294Sobrien
8178310490Scy\def\setupdatafile{%
817938494Sobrien  \catcode`\^^@=\other
818038494Sobrien  \catcode`\^^A=\other
818138494Sobrien  \catcode`\^^B=\other
818238494Sobrien  \catcode`\^^C=\other
818338494Sobrien  \catcode`\^^D=\other
818438494Sobrien  \catcode`\^^E=\other
818538494Sobrien  \catcode`\^^F=\other
818638494Sobrien  \catcode`\^^G=\other
818738494Sobrien  \catcode`\^^H=\other
818838494Sobrien  \catcode`\^^K=\other
818938494Sobrien  \catcode`\^^L=\other
819038494Sobrien  \catcode`\^^N=\other
819138494Sobrien  \catcode`\^^P=\other
819238494Sobrien  \catcode`\^^Q=\other
819338494Sobrien  \catcode`\^^R=\other
819438494Sobrien  \catcode`\^^S=\other
819538494Sobrien  \catcode`\^^T=\other
819638494Sobrien  \catcode`\^^U=\other
819738494Sobrien  \catcode`\^^V=\other
819838494Sobrien  \catcode`\^^W=\other
819938494Sobrien  \catcode`\^^X=\other
820038494Sobrien  \catcode`\^^Z=\other
820138494Sobrien  \catcode`\^^[=\other
820238494Sobrien  \catcode`\^^\=\other
820338494Sobrien  \catcode`\^^]=\other
820438494Sobrien  \catcode`\^^^=\other
820538494Sobrien  \catcode`\^^_=\other
8206174294Sobrien  % It was suggested to set the catcode of ^ to 7, which would allow ^^e4 etc.
820738494Sobrien  % in xref tags, i.e., node names.  But since ^^e4 notation isn't
820838494Sobrien  % supported in the main text, it doesn't seem desirable.  Furthermore,
820938494Sobrien  % that is not enough: for node names that actually contain a ^
821038494Sobrien  % character, we would end up writing a line like this: 'xrdef {'hat
821138494Sobrien  % b-title}{'hat b} and \xrdef does a \csname...\endcsname on the first
821238494Sobrien  % argument, and \hat is not an expandable control sequence.  It could
821338494Sobrien  % all be worked out, but why?  Either we support ^^ or we don't.
821438494Sobrien  %
821538494Sobrien  % The other change necessary for this was to define \auxhat:
821638494Sobrien  % \def\auxhat{\def^{'hat }}% extra space so ok if followed by letter
821738494Sobrien  % and then to call \auxhat in \setq.
821838494Sobrien  %
8219174294Sobrien  \catcode`\^=\other
8220174294Sobrien  %
8221174294Sobrien  % Special characters.  Should be turned off anyway, but...
822238494Sobrien  \catcode`\~=\other
822338494Sobrien  \catcode`\[=\other
822438494Sobrien  \catcode`\]=\other
822538494Sobrien  \catcode`\"=\other
822638494Sobrien  \catcode`\_=\other
822738494Sobrien  \catcode`\|=\other
822838494Sobrien  \catcode`\<=\other
822938494Sobrien  \catcode`\>=\other
823038494Sobrien  \catcode`\$=\other
823138494Sobrien  \catcode`\#=\other
823238494Sobrien  \catcode`\&=\other
8233174294Sobrien  \catcode`\%=\other
823442629Sobrien  \catcode`+=\other % avoid \+ for paranoia even though we've turned it off
8235174294Sobrien  %
8236174294Sobrien  % This is to support \ in node names and titles, since the \
8237174294Sobrien  % characters end up in a \csname.  It's easier than
8238174294Sobrien  % leaving it active and making its active definition an actual \
8239174294Sobrien  % character.  What I don't understand is why it works in the *value*
8240174294Sobrien  % of the xrdef.  Seems like it should be a catcode12 \, and that
8241174294Sobrien  % should not typeset properly.  But it works, so I'm moving on for
8242174294Sobrien  % now.  --karl, 15jan04.
8243174294Sobrien  \catcode`\\=\other
8244174294Sobrien  %
8245174294Sobrien  % Make the characters 128-255 be printing characters.
824638494Sobrien  {%
8247310490Scy    \count1=128
824838494Sobrien    \def\loop{%
8249310490Scy      \catcode\count1=\other
8250310490Scy      \advance\count1 by 1
8251310490Scy      \ifnum \count1<256 \loop \fi
825238494Sobrien    }%
825338494Sobrien  }%
8254174294Sobrien  %
8255174294Sobrien  % @ is our escape character in .aux files, and we need braces.
825638494Sobrien  \catcode`\{=1
825738494Sobrien  \catcode`\}=2
8258174294Sobrien  \catcode`\@=0
8259310490Scy}
8260310490Scy
8261310490Scy\def\readdatafile#1{%
8262310490Scy\begingroup
8263310490Scy  \setupdatafile
8264310490Scy  \input\jobname.#1
826538494Sobrien\endgroup}
826638494Sobrien
826738494Sobrien
8268174294Sobrien\message{insertions,}
8269174294Sobrien% including footnotes.
827038494Sobrien
827138494Sobrien\newcount \footnoteno
827238494Sobrien
827338494Sobrien% The trailing space in the following definition for supereject is
827438494Sobrien% vital for proper filling; pages come out unaligned when you do a
827538494Sobrien% pagealignmacro call if that space before the closing brace is
827638494Sobrien% removed. (Generally, numeric constants should always be followed by a
827738494Sobrien% space to prevent strange expansion errors.)
827838494Sobrien\def\supereject{\par\penalty -20000\footnoteno =0 }
827938494Sobrien
8280310490Scy% @footnotestyle is meaningful for Info output only.
828138494Sobrien\let\footnotestyle=\comment
828238494Sobrien
828338494Sobrien{\catcode `\@=11
828438494Sobrien%
828538494Sobrien% Auto-number footnotes.  Otherwise like plain.
828638494Sobrien\gdef\footnote{%
8287174294Sobrien  \let\indent=\ptexindent
8288174294Sobrien  \let\noindent=\ptexnoindent
828938494Sobrien  \global\advance\footnoteno by \@ne
829038494Sobrien  \edef\thisfootno{$^{\the\footnoteno}$}%
829138494Sobrien  %
829238494Sobrien  % In case the footnote comes at the end of a sentence, preserve the
829338494Sobrien  % extra spacing after we do the footnote number.
829438494Sobrien  \let\@sf\empty
8295174294Sobrien  \ifhmode\edef\@sf{\spacefactor\the\spacefactor}\ptexslash\fi
829638494Sobrien  %
829738494Sobrien  % Remove inadvertent blank space before typesetting the footnote number.
829838494Sobrien  \unskip
829938494Sobrien  \thisfootno\@sf
8300174294Sobrien  \dofootnote
830138494Sobrien}%
830238494Sobrien
830338494Sobrien% Don't bother with the trickery in plain.tex to not require the
830438494Sobrien% footnote text as a parameter.  Our footnotes don't need to be so general.
830538494Sobrien%
8306174294Sobrien% Oh yes, they do; otherwise, @ifset (and anything else that uses
8307174294Sobrien% \parseargline) fails inside footnotes because the tokens are fixed when
830838494Sobrien% the footnote is read.  --karl, 16nov96.
830938494Sobrien%
8310174294Sobrien\gdef\dofootnote{%
8311174294Sobrien  \insert\footins\bgroup
831238494Sobrien  % We want to typeset this text as a normal paragraph, even if the
831338494Sobrien  % footnote reference occurs in (for example) a display environment.
831438494Sobrien  % So reset some parameters.
8315174294Sobrien  \hsize=\pagewidth
831638494Sobrien  \interlinepenalty\interfootnotelinepenalty
831738494Sobrien  \splittopskip\ht\strutbox % top baseline for broken footnotes
831838494Sobrien  \splitmaxdepth\dp\strutbox
831938494Sobrien  \floatingpenalty\@MM
832038494Sobrien  \leftskip\z@skip
832138494Sobrien  \rightskip\z@skip
832238494Sobrien  \spaceskip\z@skip
832338494Sobrien  \xspaceskip\z@skip
832438494Sobrien  \parindent\defaultparindent
832538494Sobrien  %
832682794Sobrien  \smallfonts \rm
832782794Sobrien  %
8328119679Smbr  % Because we use hanging indentation in footnotes, a @noindent appears
8329119679Smbr  % to exdent this text, so make it be a no-op.  makeinfo does not use
8330119679Smbr  % hanging indentation so @noindent can still be needed within footnote
8331119679Smbr  % text after an @example or the like (not that this is good style).
8332119679Smbr  \let\noindent = \relax
8333119679Smbr  %
8334119679Smbr  % Hang the footnote text off the number.  Use \everypar in case the
8335119679Smbr  % footnote extends for more than one paragraph.
8336119679Smbr  \everypar = {\hang}%
833738494Sobrien  \textindent{\thisfootno}%
833838494Sobrien  %
833938494Sobrien  % Don't crash into the line above the footnote text.  Since this
834038494Sobrien  % expands into a box, it must come within the paragraph, lest it
834138494Sobrien  % provide a place where TeX can split the footnote.
834238494Sobrien  \footstrut
8343310490Scy  %
8344310490Scy  % Invoke rest of plain TeX footnote routine.
834538494Sobrien  \futurelet\next\fo@t
834638494Sobrien}
834738494Sobrien}%end \catcode `\@=11
834838494Sobrien
8349174294Sobrien% In case a @footnote appears in a vbox, save the footnote text and create
8350174294Sobrien% the real \insert just after the vbox finished.  Otherwise, the insertion
8351174294Sobrien% would be lost.
8352310490Scy% Similarly, if a @footnote appears inside an alignment, save the footnote
8353174294Sobrien% text to a box and make the \insert when a row of the table is finished.
8354174294Sobrien% And the same can be done for other insert classes.  --kasal, 16nov03.
8355174294Sobrien
8356174294Sobrien% Replace the \insert primitive by a cheating macro.
8357174294Sobrien% Deeper inside, just make sure that the saved insertions are not spilled
8358174294Sobrien% out prematurely.
835938494Sobrien%
8360174294Sobrien\def\startsavinginserts{%
8361174294Sobrien  \ifx \insert\ptexinsert
8362174294Sobrien    \let\insert\saveinsert
8363174294Sobrien  \else
8364174294Sobrien    \let\checkinserts\relax
8365174294Sobrien  \fi
836638494Sobrien}
836738494Sobrien
8368174294Sobrien% This \insert replacement works for both \insert\footins{foo} and
8369174294Sobrien% \insert\footins\bgroup foo\egroup, but it doesn't work for \insert27{foo}.
837038494Sobrien%
8371174294Sobrien\def\saveinsert#1{%
8372174294Sobrien  \edef\next{\noexpand\savetobox \makeSAVEname#1}%
8373174294Sobrien  \afterassignment\next
8374174294Sobrien  % swallow the left brace
8375174294Sobrien  \let\temp =
8376174294Sobrien}
8377174294Sobrien\def\makeSAVEname#1{\makecsname{SAVE\expandafter\gobble\string#1}}
8378174294Sobrien\def\savetobox#1{\global\setbox#1 = \vbox\bgroup \unvbox#1}
837938494Sobrien
8380174294Sobrien\def\checksaveins#1{\ifvoid#1\else \placesaveins#1\fi}
8381174294Sobrien
8382174294Sobrien\def\placesaveins#1{%
8383174294Sobrien  \ptexinsert \csname\expandafter\gobblesave\string#1\endcsname
8384174294Sobrien    {\box#1}%
8385174294Sobrien}
8386174294Sobrien
8387174294Sobrien% eat @SAVE -- beware, all of them have catcode \other:
8388174294Sobrien{
8389174294Sobrien  \def\dospecials{\do S\do A\do V\do E} \uncatcodespecials  %  ;-)
8390174294Sobrien  \gdef\gobblesave @SAVE{}
8391174294Sobrien}
8392174294Sobrien
8393174294Sobrien% initialization:
8394174294Sobrien\def\newsaveins #1{%
8395174294Sobrien  \edef\next{\noexpand\newsaveinsX \makeSAVEname#1}%
8396174294Sobrien  \next
8397174294Sobrien}
8398174294Sobrien\def\newsaveinsX #1{%
8399174294Sobrien  \csname newbox\endcsname #1%
8400174294Sobrien  \expandafter\def\expandafter\checkinserts\expandafter{\checkinserts
8401174294Sobrien    \checksaveins #1}%
8402174294Sobrien}
8403174294Sobrien
8404174294Sobrien% initialize:
8405174294Sobrien\let\checkinserts\empty
8406174294Sobrien\newsaveins\footins
8407174294Sobrien\newsaveins\margin
8408174294Sobrien
8409174294Sobrien
841038494Sobrien% @image.  We use the macros from epsf.tex to support this.
841138494Sobrien% If epsf.tex is not installed and @image is used, we complain.
841282794Sobrien%
841338494Sobrien% Check for and read epsf.tex up front.  If we read it only at @image
841438494Sobrien% time, we might be inside a group, and then its definitions would get
841538494Sobrien% undone and the next image would fail.
841642629Sobrien\openin 1 = epsf.tex
841738494Sobrien\ifeof 1 \else
8418174294Sobrien  % Do not bother showing banner with epsf.tex v2.7k (available in
8419174294Sobrien  % doc/epsf.tex and on ctan).
842042629Sobrien  \def\epsfannounce{\toks0 = }%
842138494Sobrien  \input epsf.tex
842238494Sobrien\fi
8423174294Sobrien\closein 1
842438494Sobrien%
842582794Sobrien% We will only complain once about lack of epsf.tex.
842638494Sobrien\newif\ifwarnednoepsf
842738494Sobrien\newhelp\noepsfhelp{epsf.tex must be installed for images to
842838494Sobrien  work.  It is also included in the Texinfo distribution, or you can get
842982794Sobrien  it from ftp://tug.org/tex/epsf.tex.}
843038494Sobrien%
843138494Sobrien\def\image#1{%
8432310490Scy  \ifx\epsfbox\thisisundefined
843338494Sobrien    \ifwarnednoepsf \else
843438494Sobrien      \errhelp = \noepsfhelp
843538494Sobrien      \errmessage{epsf.tex not found, images will be ignored}%
843638494Sobrien      \global\warnednoepsftrue
843738494Sobrien    \fi
843838494Sobrien  \else
8439119679Smbr    \imagexxx #1,,,,,\finish
844038494Sobrien  \fi
844138494Sobrien}
844238494Sobrien%
844338494Sobrien% Arguments to @image:
844438494Sobrien% #1 is (mandatory) image filename; we tack on .eps extension.
844538494Sobrien% #2 is (optional) width, #3 is (optional) height.
844682794Sobrien% #4 is (ignored optional) html alt text.
844782794Sobrien% #5 is (ignored optional) extension.
8448310490Scy% #6 is just the usual extra ignored arg for parsing stuff.
8449119679Smbr\newif\ifimagevmode
8450119679Smbr\def\imagexxx#1,#2,#3,#4,#5,#6\finish{\begingroup
8451119679Smbr  \catcode`\^^M = 5     % in case we're inside an example
8452119679Smbr  \normalturnoffactive  % allow _ et al. in names
8453119679Smbr  % If the image is by itself, center it.
8454119679Smbr  \ifvmode
8455119679Smbr    \imagevmodetrue
8456310490Scy  \else \ifx\centersub\centerV
8457310490Scy    % for @center @image, we need a vbox so we can have our vertical space
8458310490Scy    \imagevmodetrue
8459310490Scy    \vbox\bgroup % vbox has better behavior than vtop herev
8460310490Scy  \fi\fi
8461310490Scy  %
8462310490Scy  \ifimagevmode
8463310490Scy    \nobreak\medskip
8464119679Smbr    % Usually we'll have text after the image which will insert
8465119679Smbr    % \parskip glue, so insert it here too to equalize the space
8466174294Sobrien    % above and below.
8467119679Smbr    \nobreak\vskip\parskip
8468119679Smbr    \nobreak
8469119679Smbr  \fi
8470119679Smbr  %
8471310490Scy  % Leave vertical mode so that indentation from an enclosing
8472310490Scy  %  environment such as @quotation is respected.
8473310490Scy  % However, if we're at the top level, we don't want the
8474310490Scy  %  normal paragraph indentation.
8475310490Scy  % On the other hand, if we are in the case of @center @image, we don't
8476310490Scy  %  want to start a paragraph, which will create a hsize-width box and
8477310490Scy  %  eradicate the centering.
8478310490Scy  \ifx\centersub\centerV\else \noindent \fi
8479310490Scy  %
8480119679Smbr  % Output the image.
848182794Sobrien  \ifpdf
8482119679Smbr    \dopdfimage{#1}{#2}{#3}%
848342629Sobrien  \else
848482794Sobrien    % \epsfbox itself resets \epsf?size at each figure.
848582794Sobrien    \setbox0 = \hbox{\ignorespaces #2}\ifdim\wd0 > 0pt \epsfxsize=#2\relax \fi
848682794Sobrien    \setbox0 = \hbox{\ignorespaces #3}\ifdim\wd0 > 0pt \epsfysize=#3\relax \fi
8487119679Smbr    \epsfbox{#1.eps}%
848842629Sobrien  \fi
8489119679Smbr  %
8490310490Scy  \ifimagevmode
8491310490Scy    \medskip  % space after a standalone image
8492310490Scy  \fi  
8493310490Scy  \ifx\centersub\centerV \egroup \fi
8494119679Smbr\endgroup}
849538494Sobrien
849638494Sobrien
8497174294Sobrien% @float FLOATTYPE,LABEL,LOC ... @end float for displayed figures, tables,
8498174294Sobrien% etc.  We don't actually implement floating yet, we always include the
8499174294Sobrien% float "here".  But it seemed the best name for the future.
8500174294Sobrien%
8501174294Sobrien\envparseargdef\float{\eatcommaspace\eatcommaspace\dofloat#1, , ,\finish}
8502174294Sobrien
8503174294Sobrien% There may be a space before second and/or third parameter; delete it.
8504174294Sobrien\def\eatcommaspace#1, {#1,}
8505174294Sobrien
8506174294Sobrien% #1 is the optional FLOATTYPE, the text label for this float, typically
8507174294Sobrien% "Figure", "Table", "Example", etc.  Can't contain commas.  If omitted,
8508174294Sobrien% this float will not be numbered and cannot be referred to.
8509174294Sobrien%
8510174294Sobrien% #2 is the optional xref label.  Also must be present for the float to
8511174294Sobrien% be referable.
8512174294Sobrien%
8513174294Sobrien% #3 is the optional positioning argument; for now, it is ignored.  It
8514174294Sobrien% will somehow specify the positions allowed to float to (here, top, bottom).
8515174294Sobrien%
8516174294Sobrien% We keep a separate counter for each FLOATTYPE, which we reset at each
8517174294Sobrien% chapter-level command.
8518174294Sobrien\let\resetallfloatnos=\empty
8519174294Sobrien%
8520174294Sobrien\def\dofloat#1,#2,#3,#4\finish{%
8521174294Sobrien  \let\thiscaption=\empty
8522174294Sobrien  \let\thisshortcaption=\empty
8523174294Sobrien  %
8524174294Sobrien  % don't lose footnotes inside @float.
8525174294Sobrien  %
8526174294Sobrien  % BEWARE: when the floats start float, we have to issue warning whenever an
8527174294Sobrien  % insert appears inside a float which could possibly float. --kasal, 26may04
8528174294Sobrien  %
8529174294Sobrien  \startsavinginserts
8530174294Sobrien  %
8531174294Sobrien  % We can't be used inside a paragraph.
8532174294Sobrien  \par
8533174294Sobrien  %
8534174294Sobrien  \vtop\bgroup
8535174294Sobrien    \def\floattype{#1}%
8536174294Sobrien    \def\floatlabel{#2}%
8537174294Sobrien    \def\floatloc{#3}% we do nothing with this yet.
8538174294Sobrien    %
8539174294Sobrien    \ifx\floattype\empty
8540174294Sobrien      \let\safefloattype=\empty
8541174294Sobrien    \else
8542174294Sobrien      {%
8543174294Sobrien        % the floattype might have accents or other special characters,
8544174294Sobrien        % but we need to use it in a control sequence name.
8545174294Sobrien        \indexnofonts
8546174294Sobrien        \turnoffactive
8547174294Sobrien        \xdef\safefloattype{\floattype}%
8548174294Sobrien      }%
8549174294Sobrien    \fi
8550174294Sobrien    %
8551174294Sobrien    % If label is given but no type, we handle that as the empty type.
8552174294Sobrien    \ifx\floatlabel\empty \else
8553174294Sobrien      % We want each FLOATTYPE to be numbered separately (Figure 1,
8554174294Sobrien      % Table 1, Figure 2, ...).  (And if no label, no number.)
8555174294Sobrien      %
8556174294Sobrien      \expandafter\getfloatno\csname\safefloattype floatno\endcsname
8557174294Sobrien      \global\advance\floatno by 1
8558174294Sobrien      %
8559174294Sobrien      {%
8560310490Scy        % This magic value for \lastsection is output by \setref as the
8561174294Sobrien        % XREFLABEL-title value.  \xrefX uses it to distinguish float
8562174294Sobrien        % labels (which have a completely different output format) from
8563174294Sobrien        % node and anchor labels.  And \xrdef uses it to construct the
8564174294Sobrien        % lists of floats.
8565174294Sobrien        %
8566310490Scy        \edef\lastsection{\floatmagic=\safefloattype}%
8567174294Sobrien        \setref{\floatlabel}{Yfloat}%
8568174294Sobrien      }%
8569174294Sobrien    \fi
8570174294Sobrien    %
8571174294Sobrien    % start with \parskip glue, I guess.
8572174294Sobrien    \vskip\parskip
8573174294Sobrien    %
8574174294Sobrien    % Don't suppress indentation if a float happens to start a section.
8575174294Sobrien    \restorefirstparagraphindent
8576174294Sobrien}
8577174294Sobrien
8578174294Sobrien% we have these possibilities:
8579174294Sobrien% @float Foo,lbl & @caption{Cap}: Foo 1.1: Cap
8580174294Sobrien% @float Foo,lbl & no caption:    Foo 1.1
8581174294Sobrien% @float Foo & @caption{Cap}:     Foo: Cap
8582174294Sobrien% @float Foo & no caption:        Foo
8583174294Sobrien% @float ,lbl & Caption{Cap}:     1.1: Cap
8584174294Sobrien% @float ,lbl & no caption:       1.1
8585174294Sobrien% @float & @caption{Cap}:         Cap
8586174294Sobrien% @float & no caption:
8587174294Sobrien%
8588174294Sobrien\def\Efloat{%
8589174294Sobrien    \let\floatident = \empty
8590174294Sobrien    %
8591174294Sobrien    % In all cases, if we have a float type, it comes first.
8592174294Sobrien    \ifx\floattype\empty \else \def\floatident{\floattype}\fi
8593174294Sobrien    %
8594174294Sobrien    % If we have an xref label, the number comes next.
8595174294Sobrien    \ifx\floatlabel\empty \else
8596174294Sobrien      \ifx\floattype\empty \else % if also had float type, need tie first.
8597174294Sobrien        \appendtomacro\floatident{\tie}%
8598174294Sobrien      \fi
8599174294Sobrien      % the number.
8600174294Sobrien      \appendtomacro\floatident{\chaplevelprefix\the\floatno}%
8601174294Sobrien    \fi
8602174294Sobrien    %
8603174294Sobrien    % Start the printed caption with what we've constructed in
8604174294Sobrien    % \floatident, but keep it separate; we need \floatident again.
8605174294Sobrien    \let\captionline = \floatident
8606174294Sobrien    %
8607174294Sobrien    \ifx\thiscaption\empty \else
8608174294Sobrien      \ifx\floatident\empty \else
8609174294Sobrien	\appendtomacro\captionline{: }% had ident, so need a colon between
8610174294Sobrien      \fi
8611174294Sobrien      %
8612174294Sobrien      % caption text.
8613174294Sobrien      \appendtomacro\captionline{\scanexp\thiscaption}%
8614174294Sobrien    \fi
8615174294Sobrien    %
8616174294Sobrien    % If we have anything to print, print it, with space before.
8617174294Sobrien    % Eventually this needs to become an \insert.
8618174294Sobrien    \ifx\captionline\empty \else
8619174294Sobrien      \vskip.5\parskip
8620174294Sobrien      \captionline
8621174294Sobrien      %
8622174294Sobrien      % Space below caption.
8623174294Sobrien      \vskip\parskip
8624174294Sobrien    \fi
8625174294Sobrien    %
8626174294Sobrien    % If have an xref label, write the list of floats info.  Do this
8627174294Sobrien    % after the caption, to avoid chance of it being a breakpoint.
8628174294Sobrien    \ifx\floatlabel\empty \else
8629174294Sobrien      % Write the text that goes in the lof to the aux file as
8630174294Sobrien      % \floatlabel-lof.  Besides \floatident, we include the short
8631174294Sobrien      % caption if specified, else the full caption if specified, else nothing.
8632174294Sobrien      {%
8633310490Scy        \atdummies
8634310490Scy        %
8635174294Sobrien        % since we read the caption text in the macro world, where ^^M
8636174294Sobrien        % is turned into a normal character, we have to scan it back, so
8637174294Sobrien        % we don't write the literal three characters "^^M" into the aux file.
8638174294Sobrien	\scanexp{%
8639174294Sobrien	  \xdef\noexpand\gtemp{%
8640174294Sobrien	    \ifx\thisshortcaption\empty
8641174294Sobrien	      \thiscaption
8642174294Sobrien	    \else
8643174294Sobrien	      \thisshortcaption
8644174294Sobrien	    \fi
8645174294Sobrien	  }%
8646174294Sobrien	}%
8647174294Sobrien        \immediate\write\auxfile{@xrdef{\floatlabel-lof}{\floatident
8648174294Sobrien	  \ifx\gtemp\empty \else : \gtemp \fi}}%
8649174294Sobrien      }%
8650174294Sobrien    \fi
8651174294Sobrien  \egroup  % end of \vtop
8652174294Sobrien  %
8653174294Sobrien  % place the captured inserts
8654174294Sobrien  %
8655310490Scy  % BEWARE: when the floats start floating, we have to issue warning
8656310490Scy  % whenever an insert appears inside a float which could possibly
8657310490Scy  % float. --kasal, 26may04
8658174294Sobrien  %
8659174294Sobrien  \checkinserts
8660174294Sobrien}
8661174294Sobrien
8662174294Sobrien% Append the tokens #2 to the definition of macro #1, not expanding either.
8663174294Sobrien%
8664174294Sobrien\def\appendtomacro#1#2{%
8665174294Sobrien  \expandafter\def\expandafter#1\expandafter{#1#2}%
8666174294Sobrien}
8667174294Sobrien
8668174294Sobrien% @caption, @shortcaption
8669174294Sobrien%
8670174294Sobrien\def\caption{\docaption\thiscaption}
8671174294Sobrien\def\shortcaption{\docaption\thisshortcaption}
8672174294Sobrien\def\docaption{\checkenv\float \bgroup\scanargctxt\defcaption}
8673174294Sobrien\def\defcaption#1#2{\egroup \def#1{#2}}
8674174294Sobrien
8675174294Sobrien% The parameter is the control sequence identifying the counter we are
8676174294Sobrien% going to use.  Create it if it doesn't exist and assign it to \floatno.
8677174294Sobrien\def\getfloatno#1{%
8678174294Sobrien  \ifx#1\relax
8679174294Sobrien      % Haven't seen this figure type before.
8680174294Sobrien      \csname newcount\endcsname #1%
8681174294Sobrien      %
8682174294Sobrien      % Remember to reset this floatno at the next chap.
8683174294Sobrien      \expandafter\gdef\expandafter\resetallfloatnos
8684174294Sobrien        \expandafter{\resetallfloatnos #1=0 }%
8685174294Sobrien  \fi
8686174294Sobrien  \let\floatno#1%
8687174294Sobrien}
8688174294Sobrien
8689174294Sobrien% \setref calls this to get the XREFLABEL-snt value.  We want an @xref
8690174294Sobrien% to the FLOATLABEL to expand to "Figure 3.1".  We call \setref when we
8691174294Sobrien% first read the @float command.
8692174294Sobrien%
8693174294Sobrien\def\Yfloat{\floattype@tie \chaplevelprefix\the\floatno}%
8694174294Sobrien
8695174294Sobrien% Magic string used for the XREFLABEL-title value, so \xrefX can
8696174294Sobrien% distinguish floats from other xref types.
8697174294Sobrien\def\floatmagic{!!float!!}
8698174294Sobrien
8699174294Sobrien% #1 is the control sequence we are passed; we expand into a conditional
8700174294Sobrien% which is true if #1 represents a float ref.  That is, the magic
8701310490Scy% \lastsection value which we \setref above.
8702174294Sobrien%
8703174294Sobrien\def\iffloat#1{\expandafter\doiffloat#1==\finish}
8704174294Sobrien%
8705174294Sobrien% #1 is (maybe) the \floatmagic string.  If so, #2 will be the
8706174294Sobrien% (safe) float type for this float.  We set \iffloattype to #2.
8707174294Sobrien%
8708174294Sobrien\def\doiffloat#1=#2=#3\finish{%
8709174294Sobrien  \def\temp{#1}%
8710174294Sobrien  \def\iffloattype{#2}%
8711174294Sobrien  \ifx\temp\floatmagic
8712174294Sobrien}
8713174294Sobrien
8714174294Sobrien% @listoffloats FLOATTYPE - print a list of floats like a table of contents.
8715174294Sobrien%
8716174294Sobrien\parseargdef\listoffloats{%
8717174294Sobrien  \def\floattype{#1}% floattype
8718174294Sobrien  {%
8719174294Sobrien    % the floattype might have accents or other special characters,
8720174294Sobrien    % but we need to use it in a control sequence name.
8721174294Sobrien    \indexnofonts
8722174294Sobrien    \turnoffactive
8723174294Sobrien    \xdef\safefloattype{\floattype}%
8724174294Sobrien  }%
8725174294Sobrien  %
8726174294Sobrien  % \xrdef saves the floats as a \do-list in \floatlistSAFEFLOATTYPE.
8727174294Sobrien  \expandafter\ifx\csname floatlist\safefloattype\endcsname \relax
8728174294Sobrien    \ifhavexrefs
8729174294Sobrien      % if the user said @listoffloats foo but never @float foo.
8730174294Sobrien      \message{\linenumber No `\safefloattype' floats to list.}%
8731174294Sobrien    \fi
8732174294Sobrien  \else
8733174294Sobrien    \begingroup
8734174294Sobrien      \leftskip=\tocindent  % indent these entries like a toc
8735174294Sobrien      \let\do=\listoffloatsdo
8736174294Sobrien      \csname floatlist\safefloattype\endcsname
8737174294Sobrien    \endgroup
8738174294Sobrien  \fi
8739174294Sobrien}
8740174294Sobrien
8741174294Sobrien% This is called on each entry in a list of floats.  We're passed the
8742174294Sobrien% xref label, in the form LABEL-title, which is how we save it in the
8743174294Sobrien% aux file.  We strip off the -title and look up \XRLABEL-lof, which
8744174294Sobrien% has the text we're supposed to typeset here.
8745174294Sobrien%
8746174294Sobrien% Figures without xref labels will not be included in the list (since
8747174294Sobrien% they won't appear in the aux file).
8748174294Sobrien%
8749174294Sobrien\def\listoffloatsdo#1{\listoffloatsdoentry#1\finish}
8750174294Sobrien\def\listoffloatsdoentry#1-title\finish{{%
8751174294Sobrien  % Can't fully expand XR#1-lof because it can contain anything.  Just
8752174294Sobrien  % pass the control sequence.  On the other hand, XR#1-pg is just the
8753174294Sobrien  % page number, and we want to fully expand that so we can get a link
8754174294Sobrien  % in pdf output.
8755174294Sobrien  \toksA = \expandafter{\csname XR#1-lof\endcsname}%
8756174294Sobrien  %
8757174294Sobrien  % use the same \entry macro we use to generate the TOC and index.
8758174294Sobrien  \edef\writeentry{\noexpand\entry{\the\toksA}{\csname XR#1-pg\endcsname}}%
8759174294Sobrien  \writeentry
8760174294Sobrien}}
8761174294Sobrien
8762310490Scy
876382794Sobrien\message{localization,}
876438494Sobrien
8765310490Scy% For single-language documents, @documentlanguage is usually given very
8766310490Scy% early, just after @documentencoding.  Single argument is the language
8767310490Scy% (de) or locale (de_DE) abbreviation.
876882794Sobrien%
8769310490Scy{
8770310490Scy  \catcode`\_ = \active
8771310490Scy  \globaldefs=1
8772310490Scy\parseargdef\documentlanguage{\begingroup
8773310490Scy  \let_=\normalunderscore  % normal _ character for filenames
877482794Sobrien  \tex % read txi-??.tex file in plain TeX.
8775310490Scy    % Read the file by the name they passed if it exists.
8776174294Sobrien    \openin 1 txi-#1.tex
8777174294Sobrien    \ifeof 1
8778310490Scy      \documentlanguagetrywithoutunderscore{#1_\finish}%
8779174294Sobrien    \else
8780310490Scy      \globaldefs = 1  % everything in the txi-LL files needs to persist
8781174294Sobrien      \input txi-#1.tex
8782174294Sobrien    \fi
8783174294Sobrien    \closein 1
8784310490Scy  \endgroup % end raw TeX
8785310490Scy\endgroup}
8786310490Scy%
8787310490Scy% If they passed de_DE, and txi-de_DE.tex doesn't exist,
8788310490Scy% try txi-de.tex.
8789310490Scy%
8790310490Scy\gdef\documentlanguagetrywithoutunderscore#1_#2\finish{%
8791310490Scy  \openin 1 txi-#1.tex
8792310490Scy  \ifeof 1
8793310490Scy    \errhelp = \nolanghelp
8794310490Scy    \errmessage{Cannot read language file txi-#1.tex}%
8795310490Scy  \else
8796310490Scy    \globaldefs = 1  % everything in the txi-LL files needs to persist
8797310490Scy    \input txi-#1.tex
8798310490Scy  \fi
8799310490Scy  \closein 1
880082794Sobrien}
8801310490Scy}% end of special _ catcode
8802310490Scy%
880382794Sobrien\newhelp\nolanghelp{The given language definition file cannot be found or
8804310490Scyis empty.  Maybe you need to install it?  Putting it in the current
8805310490Scydirectory should work if nowhere else does.}
880682794Sobrien
8807310490Scy% This macro is called from txi-??.tex files; the first argument is the
8808310490Scy% \language name to set (without the "\lang@" prefix), the second and
8809310490Scy% third args are \{left,right}hyphenmin.
8810310490Scy%
8811310490Scy% The language names to pass are determined when the format is built.
8812310490Scy% See the etex.log file created at that time, e.g.,
8813310490Scy% /usr/local/texlive/2008/texmf-var/web2c/pdftex/etex.log.
8814310490Scy%
8815310490Scy% With TeX Live 2008, etex now includes hyphenation patterns for all
8816310490Scy% available languages.  This means we can support hyphenation in
8817310490Scy% Texinfo, at least to some extent.  (This still doesn't solve the
8818310490Scy% accented characters problem.)
8819310490Scy%
8820310490Scy\catcode`@=11
8821310490Scy\def\txisetlanguage#1#2#3{%
8822310490Scy  % do not set the language if the name is undefined in the current TeX.
8823310490Scy  \expandafter\ifx\csname lang@#1\endcsname \relax
8824310490Scy    \message{no patterns for #1}%
8825310490Scy  \else
8826310490Scy    \global\language = \csname lang@#1\endcsname
8827310490Scy  \fi
8828310490Scy  % but there is no harm in adjusting the hyphenmin values regardless.
8829310490Scy  \global\lefthyphenmin = #2\relax
8830310490Scy  \global\righthyphenmin = #3\relax
8831310490Scy}
883282794Sobrien
8833310490Scy% Helpers for encodings.
8834310490Scy% Set the catcode of characters 128 through 255 to the specified number.
8835310490Scy%
8836310490Scy\def\setnonasciicharscatcode#1{%
8837310490Scy   \count255=128
8838310490Scy   \loop\ifnum\count255<256
8839310490Scy      \global\catcode\count255=#1\relax
8840310490Scy      \advance\count255 by 1
8841310490Scy   \repeat
8842310490Scy}
884382794Sobrien
8844310490Scy\def\setnonasciicharscatcodenonglobal#1{%
8845310490Scy   \count255=128
8846310490Scy   \loop\ifnum\count255<256
8847310490Scy      \catcode\count255=#1\relax
8848310490Scy      \advance\count255 by 1
8849310490Scy   \repeat
8850310490Scy}
885182794Sobrien
8852310490Scy% @documentencoding sets the definition of non-ASCII characters
8853310490Scy% according to the specified encoding.
885482794Sobrien%
8855310490Scy\parseargdef\documentencoding{%
8856310490Scy  % Encoding being declared for the document.
8857310490Scy  \def\declaredencoding{\csname #1.enc\endcsname}%
8858310490Scy  %
8859310490Scy  % Supported encodings: names converted to tokens in order to be able
8860310490Scy  % to compare them with \ifx.
8861310490Scy  \def\ascii{\csname US-ASCII.enc\endcsname}%
8862310490Scy  \def\latnine{\csname ISO-8859-15.enc\endcsname}%
8863310490Scy  \def\latone{\csname ISO-8859-1.enc\endcsname}%
8864310490Scy  \def\lattwo{\csname ISO-8859-2.enc\endcsname}%
8865310490Scy  \def\utfeight{\csname UTF-8.enc\endcsname}%
8866310490Scy  %
8867310490Scy  \ifx \declaredencoding \ascii
8868310490Scy     \asciichardefs
8869310490Scy  %
8870310490Scy  \else \ifx \declaredencoding \lattwo
8871310490Scy     \setnonasciicharscatcode\active
8872310490Scy     \lattwochardefs
8873310490Scy  %
8874310490Scy  \else \ifx \declaredencoding \latone
8875310490Scy     \setnonasciicharscatcode\active
8876310490Scy     \latonechardefs
8877310490Scy  %
8878310490Scy  \else \ifx \declaredencoding \latnine
8879310490Scy     \setnonasciicharscatcode\active
8880310490Scy     \latninechardefs
8881310490Scy  %
8882310490Scy  \else \ifx \declaredencoding \utfeight
8883310490Scy     \setnonasciicharscatcode\active
8884310490Scy     \utfeightchardefs
8885310490Scy  %
8886310490Scy  \else
8887310490Scy    \message{Unknown document encoding #1, ignoring.}%
8888310490Scy  %
8889310490Scy  \fi % utfeight
8890310490Scy  \fi % latnine
8891310490Scy  \fi % latone
8892310490Scy  \fi % lattwo
8893310490Scy  \fi % ascii
8894310490Scy}
8895310490Scy
8896310490Scy% A message to be logged when using a character that isn't available
8897310490Scy% the default font encoding (OT1).
8898310490Scy%
8899310490Scy\def\missingcharmsg#1{\message{Character missing in OT1 encoding: #1.}}
8900310490Scy
8901310490Scy% Take account of \c (plain) vs. \, (Texinfo) difference.
8902310490Scy\def\cedilla#1{\ifx\c\ptexc\c{#1}\else\,{#1}\fi}
8903310490Scy
8904310490Scy% First, make active non-ASCII characters in order for them to be
8905310490Scy% correctly categorized when TeX reads the replacement text of
8906310490Scy% macros containing the character definitions.
8907310490Scy\setnonasciicharscatcode\active
8908310490Scy%
8909310490Scy% Latin1 (ISO-8859-1) character definitions.
8910310490Scy\def\latonechardefs{%
8911310490Scy  \gdef^^a0{\tie}
8912310490Scy  \gdef^^a1{\exclamdown}
8913310490Scy  \gdef^^a2{\missingcharmsg{CENT SIGN}}
8914310490Scy  \gdef^^a3{{\pounds}}
8915310490Scy  \gdef^^a4{\missingcharmsg{CURRENCY SIGN}}
8916310490Scy  \gdef^^a5{\missingcharmsg{YEN SIGN}}
8917310490Scy  \gdef^^a6{\missingcharmsg{BROKEN BAR}}
8918310490Scy  \gdef^^a7{\S}
8919310490Scy  \gdef^^a8{\"{}}
8920310490Scy  \gdef^^a9{\copyright}
8921310490Scy  \gdef^^aa{\ordf}
8922310490Scy  \gdef^^ab{\guillemetleft}
8923310490Scy  \gdef^^ac{$\lnot$}
8924310490Scy  \gdef^^ad{\-}
8925310490Scy  \gdef^^ae{\registeredsymbol}
8926310490Scy  \gdef^^af{\={}}
8927310490Scy  %
8928310490Scy  \gdef^^b0{\textdegree}
8929310490Scy  \gdef^^b1{$\pm$}
8930310490Scy  \gdef^^b2{$^2$}
8931310490Scy  \gdef^^b3{$^3$}
8932310490Scy  \gdef^^b4{\'{}}
8933310490Scy  \gdef^^b5{$\mu$}
8934310490Scy  \gdef^^b6{\P}
8935310490Scy  %
8936310490Scy  \gdef^^b7{$^.$}
8937310490Scy  \gdef^^b8{\cedilla\ }
8938310490Scy  \gdef^^b9{$^1$}
8939310490Scy  \gdef^^ba{\ordm}
8940310490Scy  %
8941310490Scy  \gdef^^bb{\guillemetright}
8942310490Scy  \gdef^^bc{$1\over4$}
8943310490Scy  \gdef^^bd{$1\over2$}
8944310490Scy  \gdef^^be{$3\over4$}
8945310490Scy  \gdef^^bf{\questiondown}
8946310490Scy  %
8947310490Scy  \gdef^^c0{\`A}
8948310490Scy  \gdef^^c1{\'A}
8949310490Scy  \gdef^^c2{\^A}
8950310490Scy  \gdef^^c3{\~A}
8951310490Scy  \gdef^^c4{\"A}
8952310490Scy  \gdef^^c5{\ringaccent A}
8953310490Scy  \gdef^^c6{\AE}
8954310490Scy  \gdef^^c7{\cedilla C}
8955310490Scy  \gdef^^c8{\`E}
8956310490Scy  \gdef^^c9{\'E}
8957310490Scy  \gdef^^ca{\^E}
8958310490Scy  \gdef^^cb{\"E}
8959310490Scy  \gdef^^cc{\`I}
8960310490Scy  \gdef^^cd{\'I}
8961310490Scy  \gdef^^ce{\^I}
8962310490Scy  \gdef^^cf{\"I}
8963310490Scy  %
8964310490Scy  \gdef^^d0{\DH}
8965310490Scy  \gdef^^d1{\~N}
8966310490Scy  \gdef^^d2{\`O}
8967310490Scy  \gdef^^d3{\'O}
8968310490Scy  \gdef^^d4{\^O}
8969310490Scy  \gdef^^d5{\~O}
8970310490Scy  \gdef^^d6{\"O}
8971310490Scy  \gdef^^d7{$\times$}
8972310490Scy  \gdef^^d8{\O}
8973310490Scy  \gdef^^d9{\`U}
8974310490Scy  \gdef^^da{\'U}
8975310490Scy  \gdef^^db{\^U}
8976310490Scy  \gdef^^dc{\"U}
8977310490Scy  \gdef^^dd{\'Y}
8978310490Scy  \gdef^^de{\TH}
8979310490Scy  \gdef^^df{\ss}
8980310490Scy  %
8981310490Scy  \gdef^^e0{\`a}
8982310490Scy  \gdef^^e1{\'a}
8983310490Scy  \gdef^^e2{\^a}
8984310490Scy  \gdef^^e3{\~a}
8985310490Scy  \gdef^^e4{\"a}
8986310490Scy  \gdef^^e5{\ringaccent a}
8987310490Scy  \gdef^^e6{\ae}
8988310490Scy  \gdef^^e7{\cedilla c}
8989310490Scy  \gdef^^e8{\`e}
8990310490Scy  \gdef^^e9{\'e}
8991310490Scy  \gdef^^ea{\^e}
8992310490Scy  \gdef^^eb{\"e}
8993310490Scy  \gdef^^ec{\`{\dotless i}}
8994310490Scy  \gdef^^ed{\'{\dotless i}}
8995310490Scy  \gdef^^ee{\^{\dotless i}}
8996310490Scy  \gdef^^ef{\"{\dotless i}}
8997310490Scy  %
8998310490Scy  \gdef^^f0{\dh}
8999310490Scy  \gdef^^f1{\~n}
9000310490Scy  \gdef^^f2{\`o}
9001310490Scy  \gdef^^f3{\'o}
9002310490Scy  \gdef^^f4{\^o}
9003310490Scy  \gdef^^f5{\~o}
9004310490Scy  \gdef^^f6{\"o}
9005310490Scy  \gdef^^f7{$\div$}
9006310490Scy  \gdef^^f8{\o}
9007310490Scy  \gdef^^f9{\`u}
9008310490Scy  \gdef^^fa{\'u}
9009310490Scy  \gdef^^fb{\^u}
9010310490Scy  \gdef^^fc{\"u}
9011310490Scy  \gdef^^fd{\'y}
9012310490Scy  \gdef^^fe{\th}
9013310490Scy  \gdef^^ff{\"y}
9014310490Scy}
9015310490Scy
9016310490Scy% Latin9 (ISO-8859-15) encoding character definitions.
9017310490Scy\def\latninechardefs{%
9018310490Scy  % Encoding is almost identical to Latin1.
9019310490Scy  \latonechardefs
9020310490Scy  %
9021310490Scy  \gdef^^a4{\euro}
9022310490Scy  \gdef^^a6{\v S}
9023310490Scy  \gdef^^a8{\v s}
9024310490Scy  \gdef^^b4{\v Z}
9025310490Scy  \gdef^^b8{\v z}
9026310490Scy  \gdef^^bc{\OE}
9027310490Scy  \gdef^^bd{\oe}
9028310490Scy  \gdef^^be{\"Y}
9029310490Scy}
9030310490Scy
9031310490Scy% Latin2 (ISO-8859-2) character definitions.
9032310490Scy\def\lattwochardefs{%
9033310490Scy  \gdef^^a0{\tie}
9034310490Scy  \gdef^^a1{\ogonek{A}}
9035310490Scy  \gdef^^a2{\u{}}
9036310490Scy  \gdef^^a3{\L}
9037310490Scy  \gdef^^a4{\missingcharmsg{CURRENCY SIGN}}
9038310490Scy  \gdef^^a5{\v L}
9039310490Scy  \gdef^^a6{\'S}
9040310490Scy  \gdef^^a7{\S}
9041310490Scy  \gdef^^a8{\"{}}
9042310490Scy  \gdef^^a9{\v S}
9043310490Scy  \gdef^^aa{\cedilla S}
9044310490Scy  \gdef^^ab{\v T}
9045310490Scy  \gdef^^ac{\'Z}
9046310490Scy  \gdef^^ad{\-}
9047310490Scy  \gdef^^ae{\v Z}
9048310490Scy  \gdef^^af{\dotaccent Z}
9049310490Scy  %
9050310490Scy  \gdef^^b0{\textdegree}
9051310490Scy  \gdef^^b1{\ogonek{a}}
9052310490Scy  \gdef^^b2{\ogonek{ }}
9053310490Scy  \gdef^^b3{\l}
9054310490Scy  \gdef^^b4{\'{}}
9055310490Scy  \gdef^^b5{\v l}
9056310490Scy  \gdef^^b6{\'s}
9057310490Scy  \gdef^^b7{\v{}}
9058310490Scy  \gdef^^b8{\cedilla\ }
9059310490Scy  \gdef^^b9{\v s}
9060310490Scy  \gdef^^ba{\cedilla s}
9061310490Scy  \gdef^^bb{\v t}
9062310490Scy  \gdef^^bc{\'z}
9063310490Scy  \gdef^^bd{\H{}}
9064310490Scy  \gdef^^be{\v z}
9065310490Scy  \gdef^^bf{\dotaccent z}
9066310490Scy  %
9067310490Scy  \gdef^^c0{\'R}
9068310490Scy  \gdef^^c1{\'A}
9069310490Scy  \gdef^^c2{\^A}
9070310490Scy  \gdef^^c3{\u A}
9071310490Scy  \gdef^^c4{\"A}
9072310490Scy  \gdef^^c5{\'L}
9073310490Scy  \gdef^^c6{\'C}
9074310490Scy  \gdef^^c7{\cedilla C}
9075310490Scy  \gdef^^c8{\v C}
9076310490Scy  \gdef^^c9{\'E}
9077310490Scy  \gdef^^ca{\ogonek{E}}
9078310490Scy  \gdef^^cb{\"E}
9079310490Scy  \gdef^^cc{\v E}
9080310490Scy  \gdef^^cd{\'I}
9081310490Scy  \gdef^^ce{\^I}
9082310490Scy  \gdef^^cf{\v D}
9083310490Scy  %
9084310490Scy  \gdef^^d0{\DH}
9085310490Scy  \gdef^^d1{\'N}
9086310490Scy  \gdef^^d2{\v N}
9087310490Scy  \gdef^^d3{\'O}
9088310490Scy  \gdef^^d4{\^O}
9089310490Scy  \gdef^^d5{\H O}
9090310490Scy  \gdef^^d6{\"O}
9091310490Scy  \gdef^^d7{$\times$}
9092310490Scy  \gdef^^d8{\v R}
9093310490Scy  \gdef^^d9{\ringaccent U}
9094310490Scy  \gdef^^da{\'U}
9095310490Scy  \gdef^^db{\H U}
9096310490Scy  \gdef^^dc{\"U}
9097310490Scy  \gdef^^dd{\'Y}
9098310490Scy  \gdef^^de{\cedilla T}
9099310490Scy  \gdef^^df{\ss}
9100310490Scy  %
9101310490Scy  \gdef^^e0{\'r}
9102310490Scy  \gdef^^e1{\'a}
9103310490Scy  \gdef^^e2{\^a}
9104310490Scy  \gdef^^e3{\u a}
9105310490Scy  \gdef^^e4{\"a}
9106310490Scy  \gdef^^e5{\'l}
9107310490Scy  \gdef^^e6{\'c}
9108310490Scy  \gdef^^e7{\cedilla c}
9109310490Scy  \gdef^^e8{\v c}
9110310490Scy  \gdef^^e9{\'e}
9111310490Scy  \gdef^^ea{\ogonek{e}}
9112310490Scy  \gdef^^eb{\"e}
9113310490Scy  \gdef^^ec{\v e}
9114310490Scy  \gdef^^ed{\'{\dotless{i}}}
9115310490Scy  \gdef^^ee{\^{\dotless{i}}}
9116310490Scy  \gdef^^ef{\v d}
9117310490Scy  %
9118310490Scy  \gdef^^f0{\dh}
9119310490Scy  \gdef^^f1{\'n}
9120310490Scy  \gdef^^f2{\v n}
9121310490Scy  \gdef^^f3{\'o}
9122310490Scy  \gdef^^f4{\^o}
9123310490Scy  \gdef^^f5{\H o}
9124310490Scy  \gdef^^f6{\"o}
9125310490Scy  \gdef^^f7{$\div$}
9126310490Scy  \gdef^^f8{\v r}
9127310490Scy  \gdef^^f9{\ringaccent u}
9128310490Scy  \gdef^^fa{\'u}
9129310490Scy  \gdef^^fb{\H u}
9130310490Scy  \gdef^^fc{\"u}
9131310490Scy  \gdef^^fd{\'y}
9132310490Scy  \gdef^^fe{\cedilla t}
9133310490Scy  \gdef^^ff{\dotaccent{}}
9134310490Scy}
9135310490Scy
9136310490Scy% UTF-8 character definitions.
9137310490Scy%
9138310490Scy% This code to support UTF-8 is based on LaTeX's utf8.def, with some
9139310490Scy% changes for Texinfo conventions.  It is included here under the GPL by
9140310490Scy% permission from Frank Mittelbach and the LaTeX team.
9141310490Scy%
9142310490Scy\newcount\countUTFx
9143310490Scy\newcount\countUTFy
9144310490Scy\newcount\countUTFz
9145310490Scy
9146310490Scy\gdef\UTFviiiTwoOctets#1#2{\expandafter
9147310490Scy   \UTFviiiDefined\csname u8:#1\string #2\endcsname}
9148310490Scy%
9149310490Scy\gdef\UTFviiiThreeOctets#1#2#3{\expandafter
9150310490Scy   \UTFviiiDefined\csname u8:#1\string #2\string #3\endcsname}
9151310490Scy%
9152310490Scy\gdef\UTFviiiFourOctets#1#2#3#4{\expandafter
9153310490Scy   \UTFviiiDefined\csname u8:#1\string #2\string #3\string #4\endcsname}
9154310490Scy
9155310490Scy\gdef\UTFviiiDefined#1{%
9156310490Scy  \ifx #1\relax
9157310490Scy    \message{\linenumber Unicode char \string #1 not defined for Texinfo}%
9158310490Scy  \else
9159310490Scy    \expandafter #1%
9160310490Scy  \fi
9161310490Scy}
9162310490Scy
9163310490Scy\begingroup
9164310490Scy  \catcode`\~13
9165310490Scy  \catcode`\"12
9166310490Scy
9167310490Scy  \def\UTFviiiLoop{%
9168310490Scy    \global\catcode\countUTFx\active
9169310490Scy    \uccode`\~\countUTFx
9170310490Scy    \uppercase\expandafter{\UTFviiiTmp}%
9171310490Scy    \advance\countUTFx by 1
9172310490Scy    \ifnum\countUTFx < \countUTFy
9173310490Scy      \expandafter\UTFviiiLoop
9174310490Scy    \fi}
9175310490Scy
9176310490Scy  \countUTFx = "C2
9177310490Scy  \countUTFy = "E0
9178310490Scy  \def\UTFviiiTmp{%
9179310490Scy    \xdef~{\noexpand\UTFviiiTwoOctets\string~}}
9180310490Scy  \UTFviiiLoop
9181310490Scy
9182310490Scy  \countUTFx = "E0
9183310490Scy  \countUTFy = "F0
9184310490Scy  \def\UTFviiiTmp{%
9185310490Scy    \xdef~{\noexpand\UTFviiiThreeOctets\string~}}
9186310490Scy  \UTFviiiLoop
9187310490Scy
9188310490Scy  \countUTFx = "F0
9189310490Scy  \countUTFy = "F4
9190310490Scy  \def\UTFviiiTmp{%
9191310490Scy    \xdef~{\noexpand\UTFviiiFourOctets\string~}}
9192310490Scy  \UTFviiiLoop
9193310490Scy\endgroup
9194310490Scy
9195310490Scy\begingroup
9196310490Scy  \catcode`\"=12
9197310490Scy  \catcode`\<=12
9198310490Scy  \catcode`\.=12
9199310490Scy  \catcode`\,=12
9200310490Scy  \catcode`\;=12
9201310490Scy  \catcode`\!=12
9202310490Scy  \catcode`\~=13
9203310490Scy
9204310490Scy  \gdef\DeclareUnicodeCharacter#1#2{%
9205310490Scy    \countUTFz = "#1\relax
9206310490Scy    %\wlog{\space\space defining Unicode char U+#1 (decimal \the\countUTFz)}%
9207310490Scy    \begingroup
9208310490Scy      \parseXMLCharref
9209310490Scy      \def\UTFviiiTwoOctets##1##2{%
9210310490Scy        \csname u8:##1\string ##2\endcsname}%
9211310490Scy      \def\UTFviiiThreeOctets##1##2##3{%
9212310490Scy        \csname u8:##1\string ##2\string ##3\endcsname}%
9213310490Scy      \def\UTFviiiFourOctets##1##2##3##4{%
9214310490Scy        \csname u8:##1\string ##2\string ##3\string ##4\endcsname}%
9215310490Scy      \expandafter\expandafter\expandafter\expandafter
9216310490Scy       \expandafter\expandafter\expandafter
9217310490Scy       \gdef\UTFviiiTmp{#2}%
9218310490Scy    \endgroup}
9219310490Scy
9220310490Scy  \gdef\parseXMLCharref{%
9221310490Scy    \ifnum\countUTFz < "A0\relax
9222310490Scy      \errhelp = \EMsimple
9223310490Scy      \errmessage{Cannot define Unicode char value < 00A0}%
9224310490Scy    \else\ifnum\countUTFz < "800\relax
9225310490Scy      \parseUTFviiiA,%
9226310490Scy      \parseUTFviiiB C\UTFviiiTwoOctets.,%
9227310490Scy    \else\ifnum\countUTFz < "10000\relax
9228310490Scy      \parseUTFviiiA;%
9229310490Scy      \parseUTFviiiA,%
9230310490Scy      \parseUTFviiiB E\UTFviiiThreeOctets.{,;}%
9231310490Scy    \else
9232310490Scy      \parseUTFviiiA;%
9233310490Scy      \parseUTFviiiA,%
9234310490Scy      \parseUTFviiiA!%
9235310490Scy      \parseUTFviiiB F\UTFviiiFourOctets.{!,;}%
9236310490Scy    \fi\fi\fi
9237310490Scy  }
9238310490Scy
9239310490Scy  \gdef\parseUTFviiiA#1{%
9240310490Scy    \countUTFx = \countUTFz
9241310490Scy    \divide\countUTFz by 64
9242310490Scy    \countUTFy = \countUTFz
9243310490Scy    \multiply\countUTFz by 64
9244310490Scy    \advance\countUTFx by -\countUTFz
9245310490Scy    \advance\countUTFx by 128
9246310490Scy    \uccode `#1\countUTFx
9247310490Scy    \countUTFz = \countUTFy}
9248310490Scy
9249310490Scy  \gdef\parseUTFviiiB#1#2#3#4{%
9250310490Scy    \advance\countUTFz by "#10\relax
9251310490Scy    \uccode `#3\countUTFz
9252310490Scy    \uppercase{\gdef\UTFviiiTmp{#2#3#4}}}
9253310490Scy\endgroup
9254310490Scy
9255310490Scy\def\utfeightchardefs{%
9256310490Scy  \DeclareUnicodeCharacter{00A0}{\tie}
9257310490Scy  \DeclareUnicodeCharacter{00A1}{\exclamdown}
9258310490Scy  \DeclareUnicodeCharacter{00A3}{\pounds}
9259310490Scy  \DeclareUnicodeCharacter{00A8}{\"{ }}
9260310490Scy  \DeclareUnicodeCharacter{00A9}{\copyright}
9261310490Scy  \DeclareUnicodeCharacter{00AA}{\ordf}
9262310490Scy  \DeclareUnicodeCharacter{00AB}{\guillemetleft}
9263310490Scy  \DeclareUnicodeCharacter{00AD}{\-}
9264310490Scy  \DeclareUnicodeCharacter{00AE}{\registeredsymbol}
9265310490Scy  \DeclareUnicodeCharacter{00AF}{\={ }}
9266310490Scy
9267310490Scy  \DeclareUnicodeCharacter{00B0}{\ringaccent{ }}
9268310490Scy  \DeclareUnicodeCharacter{00B4}{\'{ }}
9269310490Scy  \DeclareUnicodeCharacter{00B8}{\cedilla{ }}
9270310490Scy  \DeclareUnicodeCharacter{00BA}{\ordm}
9271310490Scy  \DeclareUnicodeCharacter{00BB}{\guillemetright}
9272310490Scy  \DeclareUnicodeCharacter{00BF}{\questiondown}
9273310490Scy
9274310490Scy  \DeclareUnicodeCharacter{00C0}{\`A}
9275310490Scy  \DeclareUnicodeCharacter{00C1}{\'A}
9276310490Scy  \DeclareUnicodeCharacter{00C2}{\^A}
9277310490Scy  \DeclareUnicodeCharacter{00C3}{\~A}
9278310490Scy  \DeclareUnicodeCharacter{00C4}{\"A}
9279310490Scy  \DeclareUnicodeCharacter{00C5}{\AA}
9280310490Scy  \DeclareUnicodeCharacter{00C6}{\AE}
9281310490Scy  \DeclareUnicodeCharacter{00C7}{\cedilla{C}}
9282310490Scy  \DeclareUnicodeCharacter{00C8}{\`E}
9283310490Scy  \DeclareUnicodeCharacter{00C9}{\'E}
9284310490Scy  \DeclareUnicodeCharacter{00CA}{\^E}
9285310490Scy  \DeclareUnicodeCharacter{00CB}{\"E}
9286310490Scy  \DeclareUnicodeCharacter{00CC}{\`I}
9287310490Scy  \DeclareUnicodeCharacter{00CD}{\'I}
9288310490Scy  \DeclareUnicodeCharacter{00CE}{\^I}
9289310490Scy  \DeclareUnicodeCharacter{00CF}{\"I}
9290310490Scy
9291310490Scy  \DeclareUnicodeCharacter{00D0}{\DH}
9292310490Scy  \DeclareUnicodeCharacter{00D1}{\~N}
9293310490Scy  \DeclareUnicodeCharacter{00D2}{\`O}
9294310490Scy  \DeclareUnicodeCharacter{00D3}{\'O}
9295310490Scy  \DeclareUnicodeCharacter{00D4}{\^O}
9296310490Scy  \DeclareUnicodeCharacter{00D5}{\~O}
9297310490Scy  \DeclareUnicodeCharacter{00D6}{\"O}
9298310490Scy  \DeclareUnicodeCharacter{00D8}{\O}
9299310490Scy  \DeclareUnicodeCharacter{00D9}{\`U}
9300310490Scy  \DeclareUnicodeCharacter{00DA}{\'U}
9301310490Scy  \DeclareUnicodeCharacter{00DB}{\^U}
9302310490Scy  \DeclareUnicodeCharacter{00DC}{\"U}
9303310490Scy  \DeclareUnicodeCharacter{00DD}{\'Y}
9304310490Scy  \DeclareUnicodeCharacter{00DE}{\TH}
9305310490Scy  \DeclareUnicodeCharacter{00DF}{\ss}
9306310490Scy
9307310490Scy  \DeclareUnicodeCharacter{00E0}{\`a}
9308310490Scy  \DeclareUnicodeCharacter{00E1}{\'a}
9309310490Scy  \DeclareUnicodeCharacter{00E2}{\^a}
9310310490Scy  \DeclareUnicodeCharacter{00E3}{\~a}
9311310490Scy  \DeclareUnicodeCharacter{00E4}{\"a}
9312310490Scy  \DeclareUnicodeCharacter{00E5}{\aa}
9313310490Scy  \DeclareUnicodeCharacter{00E6}{\ae}
9314310490Scy  \DeclareUnicodeCharacter{00E7}{\cedilla{c}}
9315310490Scy  \DeclareUnicodeCharacter{00E8}{\`e}
9316310490Scy  \DeclareUnicodeCharacter{00E9}{\'e}
9317310490Scy  \DeclareUnicodeCharacter{00EA}{\^e}
9318310490Scy  \DeclareUnicodeCharacter{00EB}{\"e}
9319310490Scy  \DeclareUnicodeCharacter{00EC}{\`{\dotless{i}}}
9320310490Scy  \DeclareUnicodeCharacter{00ED}{\'{\dotless{i}}}
9321310490Scy  \DeclareUnicodeCharacter{00EE}{\^{\dotless{i}}}
9322310490Scy  \DeclareUnicodeCharacter{00EF}{\"{\dotless{i}}}
9323310490Scy
9324310490Scy  \DeclareUnicodeCharacter{00F0}{\dh}
9325310490Scy  \DeclareUnicodeCharacter{00F1}{\~n}
9326310490Scy  \DeclareUnicodeCharacter{00F2}{\`o}
9327310490Scy  \DeclareUnicodeCharacter{00F3}{\'o}
9328310490Scy  \DeclareUnicodeCharacter{00F4}{\^o}
9329310490Scy  \DeclareUnicodeCharacter{00F5}{\~o}
9330310490Scy  \DeclareUnicodeCharacter{00F6}{\"o}
9331310490Scy  \DeclareUnicodeCharacter{00F8}{\o}
9332310490Scy  \DeclareUnicodeCharacter{00F9}{\`u}
9333310490Scy  \DeclareUnicodeCharacter{00FA}{\'u}
9334310490Scy  \DeclareUnicodeCharacter{00FB}{\^u}
9335310490Scy  \DeclareUnicodeCharacter{00FC}{\"u}
9336310490Scy  \DeclareUnicodeCharacter{00FD}{\'y}
9337310490Scy  \DeclareUnicodeCharacter{00FE}{\th}
9338310490Scy  \DeclareUnicodeCharacter{00FF}{\"y}
9339310490Scy
9340310490Scy  \DeclareUnicodeCharacter{0100}{\=A}
9341310490Scy  \DeclareUnicodeCharacter{0101}{\=a}
9342310490Scy  \DeclareUnicodeCharacter{0102}{\u{A}}
9343310490Scy  \DeclareUnicodeCharacter{0103}{\u{a}}
9344310490Scy  \DeclareUnicodeCharacter{0104}{\ogonek{A}}
9345310490Scy  \DeclareUnicodeCharacter{0105}{\ogonek{a}}
9346310490Scy  \DeclareUnicodeCharacter{0106}{\'C}
9347310490Scy  \DeclareUnicodeCharacter{0107}{\'c}
9348310490Scy  \DeclareUnicodeCharacter{0108}{\^C}
9349310490Scy  \DeclareUnicodeCharacter{0109}{\^c}
9350310490Scy  \DeclareUnicodeCharacter{0118}{\ogonek{E}}
9351310490Scy  \DeclareUnicodeCharacter{0119}{\ogonek{e}}
9352310490Scy  \DeclareUnicodeCharacter{010A}{\dotaccent{C}}
9353310490Scy  \DeclareUnicodeCharacter{010B}{\dotaccent{c}}
9354310490Scy  \DeclareUnicodeCharacter{010C}{\v{C}}
9355310490Scy  \DeclareUnicodeCharacter{010D}{\v{c}}
9356310490Scy  \DeclareUnicodeCharacter{010E}{\v{D}}
9357310490Scy
9358310490Scy  \DeclareUnicodeCharacter{0112}{\=E}
9359310490Scy  \DeclareUnicodeCharacter{0113}{\=e}
9360310490Scy  \DeclareUnicodeCharacter{0114}{\u{E}}
9361310490Scy  \DeclareUnicodeCharacter{0115}{\u{e}}
9362310490Scy  \DeclareUnicodeCharacter{0116}{\dotaccent{E}}
9363310490Scy  \DeclareUnicodeCharacter{0117}{\dotaccent{e}}
9364310490Scy  \DeclareUnicodeCharacter{011A}{\v{E}}
9365310490Scy  \DeclareUnicodeCharacter{011B}{\v{e}}
9366310490Scy  \DeclareUnicodeCharacter{011C}{\^G}
9367310490Scy  \DeclareUnicodeCharacter{011D}{\^g}
9368310490Scy  \DeclareUnicodeCharacter{011E}{\u{G}}
9369310490Scy  \DeclareUnicodeCharacter{011F}{\u{g}}
9370310490Scy
9371310490Scy  \DeclareUnicodeCharacter{0120}{\dotaccent{G}}
9372310490Scy  \DeclareUnicodeCharacter{0121}{\dotaccent{g}}
9373310490Scy  \DeclareUnicodeCharacter{0124}{\^H}
9374310490Scy  \DeclareUnicodeCharacter{0125}{\^h}
9375310490Scy  \DeclareUnicodeCharacter{0128}{\~I}
9376310490Scy  \DeclareUnicodeCharacter{0129}{\~{\dotless{i}}}
9377310490Scy  \DeclareUnicodeCharacter{012A}{\=I}
9378310490Scy  \DeclareUnicodeCharacter{012B}{\={\dotless{i}}}
9379310490Scy  \DeclareUnicodeCharacter{012C}{\u{I}}
9380310490Scy  \DeclareUnicodeCharacter{012D}{\u{\dotless{i}}}
9381310490Scy
9382310490Scy  \DeclareUnicodeCharacter{0130}{\dotaccent{I}}
9383310490Scy  \DeclareUnicodeCharacter{0131}{\dotless{i}}
9384310490Scy  \DeclareUnicodeCharacter{0132}{IJ}
9385310490Scy  \DeclareUnicodeCharacter{0133}{ij}
9386310490Scy  \DeclareUnicodeCharacter{0134}{\^J}
9387310490Scy  \DeclareUnicodeCharacter{0135}{\^{\dotless{j}}}
9388310490Scy  \DeclareUnicodeCharacter{0139}{\'L}
9389310490Scy  \DeclareUnicodeCharacter{013A}{\'l}
9390310490Scy
9391310490Scy  \DeclareUnicodeCharacter{0141}{\L}
9392310490Scy  \DeclareUnicodeCharacter{0142}{\l}
9393310490Scy  \DeclareUnicodeCharacter{0143}{\'N}
9394310490Scy  \DeclareUnicodeCharacter{0144}{\'n}
9395310490Scy  \DeclareUnicodeCharacter{0147}{\v{N}}
9396310490Scy  \DeclareUnicodeCharacter{0148}{\v{n}}
9397310490Scy  \DeclareUnicodeCharacter{014C}{\=O}
9398310490Scy  \DeclareUnicodeCharacter{014D}{\=o}
9399310490Scy  \DeclareUnicodeCharacter{014E}{\u{O}}
9400310490Scy  \DeclareUnicodeCharacter{014F}{\u{o}}
9401310490Scy
9402310490Scy  \DeclareUnicodeCharacter{0150}{\H{O}}
9403310490Scy  \DeclareUnicodeCharacter{0151}{\H{o}}
9404310490Scy  \DeclareUnicodeCharacter{0152}{\OE}
9405310490Scy  \DeclareUnicodeCharacter{0153}{\oe}
9406310490Scy  \DeclareUnicodeCharacter{0154}{\'R}
9407310490Scy  \DeclareUnicodeCharacter{0155}{\'r}
9408310490Scy  \DeclareUnicodeCharacter{0158}{\v{R}}
9409310490Scy  \DeclareUnicodeCharacter{0159}{\v{r}}
9410310490Scy  \DeclareUnicodeCharacter{015A}{\'S}
9411310490Scy  \DeclareUnicodeCharacter{015B}{\'s}
9412310490Scy  \DeclareUnicodeCharacter{015C}{\^S}
9413310490Scy  \DeclareUnicodeCharacter{015D}{\^s}
9414310490Scy  \DeclareUnicodeCharacter{015E}{\cedilla{S}}
9415310490Scy  \DeclareUnicodeCharacter{015F}{\cedilla{s}}
9416310490Scy
9417310490Scy  \DeclareUnicodeCharacter{0160}{\v{S}}
9418310490Scy  \DeclareUnicodeCharacter{0161}{\v{s}}
9419310490Scy  \DeclareUnicodeCharacter{0162}{\cedilla{t}}
9420310490Scy  \DeclareUnicodeCharacter{0163}{\cedilla{T}}
9421310490Scy  \DeclareUnicodeCharacter{0164}{\v{T}}
9422310490Scy
9423310490Scy  \DeclareUnicodeCharacter{0168}{\~U}
9424310490Scy  \DeclareUnicodeCharacter{0169}{\~u}
9425310490Scy  \DeclareUnicodeCharacter{016A}{\=U}
9426310490Scy  \DeclareUnicodeCharacter{016B}{\=u}
9427310490Scy  \DeclareUnicodeCharacter{016C}{\u{U}}
9428310490Scy  \DeclareUnicodeCharacter{016D}{\u{u}}
9429310490Scy  \DeclareUnicodeCharacter{016E}{\ringaccent{U}}
9430310490Scy  \DeclareUnicodeCharacter{016F}{\ringaccent{u}}
9431310490Scy
9432310490Scy  \DeclareUnicodeCharacter{0170}{\H{U}}
9433310490Scy  \DeclareUnicodeCharacter{0171}{\H{u}}
9434310490Scy  \DeclareUnicodeCharacter{0174}{\^W}
9435310490Scy  \DeclareUnicodeCharacter{0175}{\^w}
9436310490Scy  \DeclareUnicodeCharacter{0176}{\^Y}
9437310490Scy  \DeclareUnicodeCharacter{0177}{\^y}
9438310490Scy  \DeclareUnicodeCharacter{0178}{\"Y}
9439310490Scy  \DeclareUnicodeCharacter{0179}{\'Z}
9440310490Scy  \DeclareUnicodeCharacter{017A}{\'z}
9441310490Scy  \DeclareUnicodeCharacter{017B}{\dotaccent{Z}}
9442310490Scy  \DeclareUnicodeCharacter{017C}{\dotaccent{z}}
9443310490Scy  \DeclareUnicodeCharacter{017D}{\v{Z}}
9444310490Scy  \DeclareUnicodeCharacter{017E}{\v{z}}
9445310490Scy
9446310490Scy  \DeclareUnicodeCharacter{01C4}{D\v{Z}}
9447310490Scy  \DeclareUnicodeCharacter{01C5}{D\v{z}}
9448310490Scy  \DeclareUnicodeCharacter{01C6}{d\v{z}}
9449310490Scy  \DeclareUnicodeCharacter{01C7}{LJ}
9450310490Scy  \DeclareUnicodeCharacter{01C8}{Lj}
9451310490Scy  \DeclareUnicodeCharacter{01C9}{lj}
9452310490Scy  \DeclareUnicodeCharacter{01CA}{NJ}
9453310490Scy  \DeclareUnicodeCharacter{01CB}{Nj}
9454310490Scy  \DeclareUnicodeCharacter{01CC}{nj}
9455310490Scy  \DeclareUnicodeCharacter{01CD}{\v{A}}
9456310490Scy  \DeclareUnicodeCharacter{01CE}{\v{a}}
9457310490Scy  \DeclareUnicodeCharacter{01CF}{\v{I}}
9458310490Scy
9459310490Scy  \DeclareUnicodeCharacter{01D0}{\v{\dotless{i}}}
9460310490Scy  \DeclareUnicodeCharacter{01D1}{\v{O}}
9461310490Scy  \DeclareUnicodeCharacter{01D2}{\v{o}}
9462310490Scy  \DeclareUnicodeCharacter{01D3}{\v{U}}
9463310490Scy  \DeclareUnicodeCharacter{01D4}{\v{u}}
9464310490Scy
9465310490Scy  \DeclareUnicodeCharacter{01E2}{\={\AE}}
9466310490Scy  \DeclareUnicodeCharacter{01E3}{\={\ae}}
9467310490Scy  \DeclareUnicodeCharacter{01E6}{\v{G}}
9468310490Scy  \DeclareUnicodeCharacter{01E7}{\v{g}}
9469310490Scy  \DeclareUnicodeCharacter{01E8}{\v{K}}
9470310490Scy  \DeclareUnicodeCharacter{01E9}{\v{k}}
9471310490Scy
9472310490Scy  \DeclareUnicodeCharacter{01F0}{\v{\dotless{j}}}
9473310490Scy  \DeclareUnicodeCharacter{01F1}{DZ}
9474310490Scy  \DeclareUnicodeCharacter{01F2}{Dz}
9475310490Scy  \DeclareUnicodeCharacter{01F3}{dz}
9476310490Scy  \DeclareUnicodeCharacter{01F4}{\'G}
9477310490Scy  \DeclareUnicodeCharacter{01F5}{\'g}
9478310490Scy  \DeclareUnicodeCharacter{01F8}{\`N}
9479310490Scy  \DeclareUnicodeCharacter{01F9}{\`n}
9480310490Scy  \DeclareUnicodeCharacter{01FC}{\'{\AE}}
9481310490Scy  \DeclareUnicodeCharacter{01FD}{\'{\ae}}
9482310490Scy  \DeclareUnicodeCharacter{01FE}{\'{\O}}
9483310490Scy  \DeclareUnicodeCharacter{01FF}{\'{\o}}
9484310490Scy
9485310490Scy  \DeclareUnicodeCharacter{021E}{\v{H}}
9486310490Scy  \DeclareUnicodeCharacter{021F}{\v{h}}
9487310490Scy
9488310490Scy  \DeclareUnicodeCharacter{0226}{\dotaccent{A}}
9489310490Scy  \DeclareUnicodeCharacter{0227}{\dotaccent{a}}
9490310490Scy  \DeclareUnicodeCharacter{0228}{\cedilla{E}}
9491310490Scy  \DeclareUnicodeCharacter{0229}{\cedilla{e}}
9492310490Scy  \DeclareUnicodeCharacter{022E}{\dotaccent{O}}
9493310490Scy  \DeclareUnicodeCharacter{022F}{\dotaccent{o}}
9494310490Scy
9495310490Scy  \DeclareUnicodeCharacter{0232}{\=Y}
9496310490Scy  \DeclareUnicodeCharacter{0233}{\=y}
9497310490Scy  \DeclareUnicodeCharacter{0237}{\dotless{j}}
9498310490Scy
9499310490Scy  \DeclareUnicodeCharacter{02DB}{\ogonek{ }}
9500310490Scy
9501310490Scy  \DeclareUnicodeCharacter{1E02}{\dotaccent{B}}
9502310490Scy  \DeclareUnicodeCharacter{1E03}{\dotaccent{b}}
9503310490Scy  \DeclareUnicodeCharacter{1E04}{\udotaccent{B}}
9504310490Scy  \DeclareUnicodeCharacter{1E05}{\udotaccent{b}}
9505310490Scy  \DeclareUnicodeCharacter{1E06}{\ubaraccent{B}}
9506310490Scy  \DeclareUnicodeCharacter{1E07}{\ubaraccent{b}}
9507310490Scy  \DeclareUnicodeCharacter{1E0A}{\dotaccent{D}}
9508310490Scy  \DeclareUnicodeCharacter{1E0B}{\dotaccent{d}}
9509310490Scy  \DeclareUnicodeCharacter{1E0C}{\udotaccent{D}}
9510310490Scy  \DeclareUnicodeCharacter{1E0D}{\udotaccent{d}}
9511310490Scy  \DeclareUnicodeCharacter{1E0E}{\ubaraccent{D}}
9512310490Scy  \DeclareUnicodeCharacter{1E0F}{\ubaraccent{d}}
9513310490Scy
9514310490Scy  \DeclareUnicodeCharacter{1E1E}{\dotaccent{F}}
9515310490Scy  \DeclareUnicodeCharacter{1E1F}{\dotaccent{f}}
9516310490Scy
9517310490Scy  \DeclareUnicodeCharacter{1E20}{\=G}
9518310490Scy  \DeclareUnicodeCharacter{1E21}{\=g}
9519310490Scy  \DeclareUnicodeCharacter{1E22}{\dotaccent{H}}
9520310490Scy  \DeclareUnicodeCharacter{1E23}{\dotaccent{h}}
9521310490Scy  \DeclareUnicodeCharacter{1E24}{\udotaccent{H}}
9522310490Scy  \DeclareUnicodeCharacter{1E25}{\udotaccent{h}}
9523310490Scy  \DeclareUnicodeCharacter{1E26}{\"H}
9524310490Scy  \DeclareUnicodeCharacter{1E27}{\"h}
9525310490Scy
9526310490Scy  \DeclareUnicodeCharacter{1E30}{\'K}
9527310490Scy  \DeclareUnicodeCharacter{1E31}{\'k}
9528310490Scy  \DeclareUnicodeCharacter{1E32}{\udotaccent{K}}
9529310490Scy  \DeclareUnicodeCharacter{1E33}{\udotaccent{k}}
9530310490Scy  \DeclareUnicodeCharacter{1E34}{\ubaraccent{K}}
9531310490Scy  \DeclareUnicodeCharacter{1E35}{\ubaraccent{k}}
9532310490Scy  \DeclareUnicodeCharacter{1E36}{\udotaccent{L}}
9533310490Scy  \DeclareUnicodeCharacter{1E37}{\udotaccent{l}}
9534310490Scy  \DeclareUnicodeCharacter{1E3A}{\ubaraccent{L}}
9535310490Scy  \DeclareUnicodeCharacter{1E3B}{\ubaraccent{l}}
9536310490Scy  \DeclareUnicodeCharacter{1E3E}{\'M}
9537310490Scy  \DeclareUnicodeCharacter{1E3F}{\'m}
9538310490Scy
9539310490Scy  \DeclareUnicodeCharacter{1E40}{\dotaccent{M}}
9540310490Scy  \DeclareUnicodeCharacter{1E41}{\dotaccent{m}}
9541310490Scy  \DeclareUnicodeCharacter{1E42}{\udotaccent{M}}
9542310490Scy  \DeclareUnicodeCharacter{1E43}{\udotaccent{m}}
9543310490Scy  \DeclareUnicodeCharacter{1E44}{\dotaccent{N}}
9544310490Scy  \DeclareUnicodeCharacter{1E45}{\dotaccent{n}}
9545310490Scy  \DeclareUnicodeCharacter{1E46}{\udotaccent{N}}
9546310490Scy  \DeclareUnicodeCharacter{1E47}{\udotaccent{n}}
9547310490Scy  \DeclareUnicodeCharacter{1E48}{\ubaraccent{N}}
9548310490Scy  \DeclareUnicodeCharacter{1E49}{\ubaraccent{n}}
9549310490Scy
9550310490Scy  \DeclareUnicodeCharacter{1E54}{\'P}
9551310490Scy  \DeclareUnicodeCharacter{1E55}{\'p}
9552310490Scy  \DeclareUnicodeCharacter{1E56}{\dotaccent{P}}
9553310490Scy  \DeclareUnicodeCharacter{1E57}{\dotaccent{p}}
9554310490Scy  \DeclareUnicodeCharacter{1E58}{\dotaccent{R}}
9555310490Scy  \DeclareUnicodeCharacter{1E59}{\dotaccent{r}}
9556310490Scy  \DeclareUnicodeCharacter{1E5A}{\udotaccent{R}}
9557310490Scy  \DeclareUnicodeCharacter{1E5B}{\udotaccent{r}}
9558310490Scy  \DeclareUnicodeCharacter{1E5E}{\ubaraccent{R}}
9559310490Scy  \DeclareUnicodeCharacter{1E5F}{\ubaraccent{r}}
9560310490Scy
9561310490Scy  \DeclareUnicodeCharacter{1E60}{\dotaccent{S}}
9562310490Scy  \DeclareUnicodeCharacter{1E61}{\dotaccent{s}}
9563310490Scy  \DeclareUnicodeCharacter{1E62}{\udotaccent{S}}
9564310490Scy  \DeclareUnicodeCharacter{1E63}{\udotaccent{s}}
9565310490Scy  \DeclareUnicodeCharacter{1E6A}{\dotaccent{T}}
9566310490Scy  \DeclareUnicodeCharacter{1E6B}{\dotaccent{t}}
9567310490Scy  \DeclareUnicodeCharacter{1E6C}{\udotaccent{T}}
9568310490Scy  \DeclareUnicodeCharacter{1E6D}{\udotaccent{t}}
9569310490Scy  \DeclareUnicodeCharacter{1E6E}{\ubaraccent{T}}
9570310490Scy  \DeclareUnicodeCharacter{1E6F}{\ubaraccent{t}}
9571310490Scy
9572310490Scy  \DeclareUnicodeCharacter{1E7C}{\~V}
9573310490Scy  \DeclareUnicodeCharacter{1E7D}{\~v}
9574310490Scy  \DeclareUnicodeCharacter{1E7E}{\udotaccent{V}}
9575310490Scy  \DeclareUnicodeCharacter{1E7F}{\udotaccent{v}}
9576310490Scy
9577310490Scy  \DeclareUnicodeCharacter{1E80}{\`W}
9578310490Scy  \DeclareUnicodeCharacter{1E81}{\`w}
9579310490Scy  \DeclareUnicodeCharacter{1E82}{\'W}
9580310490Scy  \DeclareUnicodeCharacter{1E83}{\'w}
9581310490Scy  \DeclareUnicodeCharacter{1E84}{\"W}
9582310490Scy  \DeclareUnicodeCharacter{1E85}{\"w}
9583310490Scy  \DeclareUnicodeCharacter{1E86}{\dotaccent{W}}
9584310490Scy  \DeclareUnicodeCharacter{1E87}{\dotaccent{w}}
9585310490Scy  \DeclareUnicodeCharacter{1E88}{\udotaccent{W}}
9586310490Scy  \DeclareUnicodeCharacter{1E89}{\udotaccent{w}}
9587310490Scy  \DeclareUnicodeCharacter{1E8A}{\dotaccent{X}}
9588310490Scy  \DeclareUnicodeCharacter{1E8B}{\dotaccent{x}}
9589310490Scy  \DeclareUnicodeCharacter{1E8C}{\"X}
9590310490Scy  \DeclareUnicodeCharacter{1E8D}{\"x}
9591310490Scy  \DeclareUnicodeCharacter{1E8E}{\dotaccent{Y}}
9592310490Scy  \DeclareUnicodeCharacter{1E8F}{\dotaccent{y}}
9593310490Scy
9594310490Scy  \DeclareUnicodeCharacter{1E90}{\^Z}
9595310490Scy  \DeclareUnicodeCharacter{1E91}{\^z}
9596310490Scy  \DeclareUnicodeCharacter{1E92}{\udotaccent{Z}}
9597310490Scy  \DeclareUnicodeCharacter{1E93}{\udotaccent{z}}
9598310490Scy  \DeclareUnicodeCharacter{1E94}{\ubaraccent{Z}}
9599310490Scy  \DeclareUnicodeCharacter{1E95}{\ubaraccent{z}}
9600310490Scy  \DeclareUnicodeCharacter{1E96}{\ubaraccent{h}}
9601310490Scy  \DeclareUnicodeCharacter{1E97}{\"t}
9602310490Scy  \DeclareUnicodeCharacter{1E98}{\ringaccent{w}}
9603310490Scy  \DeclareUnicodeCharacter{1E99}{\ringaccent{y}}
9604310490Scy
9605310490Scy  \DeclareUnicodeCharacter{1EA0}{\udotaccent{A}}
9606310490Scy  \DeclareUnicodeCharacter{1EA1}{\udotaccent{a}}
9607310490Scy
9608310490Scy  \DeclareUnicodeCharacter{1EB8}{\udotaccent{E}}
9609310490Scy  \DeclareUnicodeCharacter{1EB9}{\udotaccent{e}}
9610310490Scy  \DeclareUnicodeCharacter{1EBC}{\~E}
9611310490Scy  \DeclareUnicodeCharacter{1EBD}{\~e}
9612310490Scy
9613310490Scy  \DeclareUnicodeCharacter{1ECA}{\udotaccent{I}}
9614310490Scy  \DeclareUnicodeCharacter{1ECB}{\udotaccent{i}}
9615310490Scy  \DeclareUnicodeCharacter{1ECC}{\udotaccent{O}}
9616310490Scy  \DeclareUnicodeCharacter{1ECD}{\udotaccent{o}}
9617310490Scy
9618310490Scy  \DeclareUnicodeCharacter{1EE4}{\udotaccent{U}}
9619310490Scy  \DeclareUnicodeCharacter{1EE5}{\udotaccent{u}}
9620310490Scy
9621310490Scy  \DeclareUnicodeCharacter{1EF2}{\`Y}
9622310490Scy  \DeclareUnicodeCharacter{1EF3}{\`y}
9623310490Scy  \DeclareUnicodeCharacter{1EF4}{\udotaccent{Y}}
9624310490Scy
9625310490Scy  \DeclareUnicodeCharacter{1EF8}{\~Y}
9626310490Scy  \DeclareUnicodeCharacter{1EF9}{\~y}
9627310490Scy
9628310490Scy  \DeclareUnicodeCharacter{2013}{--}
9629310490Scy  \DeclareUnicodeCharacter{2014}{---}
9630310490Scy  \DeclareUnicodeCharacter{2018}{\quoteleft}
9631310490Scy  \DeclareUnicodeCharacter{2019}{\quoteright}
9632310490Scy  \DeclareUnicodeCharacter{201A}{\quotesinglbase}
9633310490Scy  \DeclareUnicodeCharacter{201C}{\quotedblleft}
9634310490Scy  \DeclareUnicodeCharacter{201D}{\quotedblright}
9635310490Scy  \DeclareUnicodeCharacter{201E}{\quotedblbase}
9636310490Scy  \DeclareUnicodeCharacter{2022}{\bullet}
9637310490Scy  \DeclareUnicodeCharacter{2026}{\dots}
9638310490Scy  \DeclareUnicodeCharacter{2039}{\guilsinglleft}
9639310490Scy  \DeclareUnicodeCharacter{203A}{\guilsinglright}
9640310490Scy  \DeclareUnicodeCharacter{20AC}{\euro}
9641310490Scy
9642310490Scy  \DeclareUnicodeCharacter{2192}{\expansion}
9643310490Scy  \DeclareUnicodeCharacter{21D2}{\result}
9644310490Scy
9645310490Scy  \DeclareUnicodeCharacter{2212}{\minus}
9646310490Scy  \DeclareUnicodeCharacter{2217}{\point}
9647310490Scy  \DeclareUnicodeCharacter{2261}{\equiv}
9648310490Scy}% end of \utfeightchardefs
9649310490Scy
9650310490Scy
9651310490Scy% US-ASCII character definitions.
9652310490Scy\def\asciichardefs{% nothing need be done
9653310490Scy   \relax
9654310490Scy}
9655310490Scy
9656310490Scy% Make non-ASCII characters printable again for compatibility with
9657310490Scy% existing Texinfo documents that may use them, even without declaring a
9658310490Scy% document encoding.
9659310490Scy%
9660310490Scy\setnonasciicharscatcode \other
9661310490Scy
9662310490Scy
9663310490Scy\message{formatting,}
9664310490Scy
966538494Sobrien\newdimen\defaultparindent \defaultparindent = 15pt
966638494Sobrien
966738494Sobrien\chapheadingskip = 15pt plus 4pt minus 2pt
966838494Sobrien\secheadingskip = 12pt plus 3pt minus 2pt
966938494Sobrien\subsecheadingskip = 9pt plus 2pt minus 2pt
967038494Sobrien
967138494Sobrien% Prevent underfull vbox error messages.
967242629Sobrien\vbadness = 10000
967338494Sobrien
9674310490Scy% Don't be very finicky about underfull hboxes, either.
9675310490Scy\hbadness = 6666
967642629Sobrien
9677310490Scy% Following George Bush, get rid of widows and orphans.
967838494Sobrien\widowpenalty=10000
967938494Sobrien\clubpenalty=10000
968038494Sobrien
968138494Sobrien% Use TeX 3.0's \emergencystretch to help line breaking, but if we're
968238494Sobrien% using an old version of TeX, don't do anything.  We want the amount of
968338494Sobrien% stretch added to depend on the line length, hence the dependence on
968482794Sobrien% \hsize.  We call this whenever the paper size is set.
968538494Sobrien%
968642629Sobrien\def\setemergencystretch{%
968742629Sobrien  \ifx\emergencystretch\thisisundefined
968842629Sobrien    % Allow us to assign to \emergencystretch anyway.
968942629Sobrien    \def\emergencystretch{\dimen0}%
969042629Sobrien  \else
969182794Sobrien    \emergencystretch = .15\hsize
969242629Sobrien  \fi
969342629Sobrien}
969438494Sobrien
9695310490Scy% Parameters in order: 1) textheight; 2) textwidth;
9696310490Scy% 3) voffset; 4) hoffset; 5) binding offset; 6) topskip;
9697310490Scy% 7) physical page height; 8) physical page width.
969842629Sobrien%
9699174294Sobrien% We also call \setleading{\textleading}, so the caller should define
9700174294Sobrien% \textleading.  The caller should also set \parskip.
9701174294Sobrien%
9702174294Sobrien\def\internalpagesizes#1#2#3#4#5#6#7#8{%
970342629Sobrien  \voffset = #3\relax
970442629Sobrien  \topskip = #6\relax
970542629Sobrien  \splittopskip = \topskip
970638494Sobrien  %
970742629Sobrien  \vsize = #1\relax
970842629Sobrien  \advance\vsize by \topskip
970942629Sobrien  \outervsize = \vsize
971042629Sobrien  \advance\outervsize by 2\topandbottommargin
971142629Sobrien  \pageheight = \vsize
971238494Sobrien  %
971342629Sobrien  \hsize = #2\relax
971442629Sobrien  \outerhsize = \hsize
971542629Sobrien  \advance\outerhsize by 0.5in
971642629Sobrien  \pagewidth = \hsize
971738494Sobrien  %
971842629Sobrien  \normaloffset = #4\relax
971942629Sobrien  \bindingoffset = #5\relax
972042629Sobrien  %
9721174294Sobrien  \ifpdf
9722174294Sobrien    \pdfpageheight #7\relax
9723174294Sobrien    \pdfpagewidth #8\relax
9724310490Scy    % if we don't reset these, they will remain at "1 true in" of
9725310490Scy    % whatever layout pdftex was dumped with.
9726310490Scy    \pdfhorigin = 1 true in
9727310490Scy    \pdfvorigin = 1 true in
9728174294Sobrien  \fi
9729174294Sobrien  %
973082794Sobrien  \setleading{\textleading}
973182794Sobrien  %
973242629Sobrien  \parindent = \defaultparindent
973342629Sobrien  \setemergencystretch
973438494Sobrien}
973538494Sobrien
973642629Sobrien% @letterpaper (the default).
973742629Sobrien\def\letterpaper{{\globaldefs = 1
973842629Sobrien  \parskip = 3pt plus 2pt minus 1pt
973982794Sobrien  \textleading = 13.2pt
974042629Sobrien  %
974142629Sobrien  % If page is nothing but text, make it come out even.
9742310490Scy  \internalpagesizes{607.2pt}{6in}% that's 46 lines
9743174294Sobrien                    {\voffset}{.25in}%
9744174294Sobrien                    {\bindingoffset}{36pt}%
9745174294Sobrien                    {11in}{8.5in}%
974642629Sobrien}}
974742629Sobrien
9748310490Scy% Use @smallbook to reset parameters for 7x9.25 trim size.
974942629Sobrien\def\smallbook{{\globaldefs = 1
975042629Sobrien  \parskip = 2pt plus 1pt
975182794Sobrien  \textleading = 12pt
975242629Sobrien  %
9753174294Sobrien  \internalpagesizes{7.5in}{5in}%
9754310490Scy                    {-.2in}{0in}%
9755174294Sobrien                    {\bindingoffset}{16pt}%
9756174294Sobrien                    {9.25in}{7in}%
975742629Sobrien  %
975842629Sobrien  \lispnarrowing = 0.3in
975942629Sobrien  \tolerance = 700
976042629Sobrien  \hfuzz = 1pt
976142629Sobrien  \contentsrightmargin = 0pt
976242629Sobrien  \defbodyindent = .5cm
976342629Sobrien}}
976442629Sobrien
9765310490Scy% Use @smallerbook to reset parameters for 6x9 trim size.
9766310490Scy% (Just testing, parameters still in flux.)
9767310490Scy\def\smallerbook{{\globaldefs = 1
9768310490Scy  \parskip = 1.5pt plus 1pt
9769310490Scy  \textleading = 12pt
9770310490Scy  %
9771310490Scy  \internalpagesizes{7.4in}{4.8in}%
9772310490Scy                    {-.2in}{-.4in}%
9773310490Scy                    {0pt}{14pt}%
9774310490Scy                    {9in}{6in}%
9775310490Scy  %
9776310490Scy  \lispnarrowing = 0.25in
9777310490Scy  \tolerance = 700
9778310490Scy  \hfuzz = 1pt
9779310490Scy  \contentsrightmargin = 0pt
9780310490Scy  \defbodyindent = .4cm
9781310490Scy}}
9782310490Scy
978338494Sobrien% Use @afourpaper to print on European A4 paper.
978442629Sobrien\def\afourpaper{{\globaldefs = 1
978542629Sobrien  \parskip = 3pt plus 2pt minus 1pt
9786174294Sobrien  \textleading = 13.2pt
978742629Sobrien  %
9788174294Sobrien  % Double-side printing via postscript on Laserjet 4050
9789174294Sobrien  % prints double-sided nicely when \bindingoffset=10mm and \hoffset=-6mm.
9790174294Sobrien  % To change the settings for a different printer or situation, adjust
9791174294Sobrien  % \normaloffset until the front-side and back-side texts align.  Then
9792174294Sobrien  % do the same for \bindingoffset.  You can set these for testing in
9793174294Sobrien  % your texinfo source file like this:
9794174294Sobrien  % @tex
9795174294Sobrien  % \global\normaloffset = -6mm
9796174294Sobrien  % \global\bindingoffset = 10mm
9797174294Sobrien  % @end tex
9798310490Scy  \internalpagesizes{673.2pt}{160mm}% that's 51 lines
9799174294Sobrien                    {\voffset}{\hoffset}%
9800174294Sobrien                    {\bindingoffset}{44pt}%
9801174294Sobrien                    {297mm}{210mm}%
980242629Sobrien  %
980342629Sobrien  \tolerance = 700
980442629Sobrien  \hfuzz = 1pt
9805174294Sobrien  \contentsrightmargin = 0pt
9806174294Sobrien  \defbodyindent = 5mm
980742629Sobrien}}
980838494Sobrien
980982794Sobrien% Use @afivepaper to print on European A5 paper.
981082794Sobrien% From romildo@urano.iceb.ufop.br, 2 July 2000.
981182794Sobrien% He also recommends making @example and @lisp be small.
981282794Sobrien\def\afivepaper{{\globaldefs = 1
981382794Sobrien  \parskip = 2pt plus 1pt minus 0.1pt
981482794Sobrien  \textleading = 12.5pt
981582794Sobrien  %
9816174294Sobrien  \internalpagesizes{160mm}{120mm}%
9817174294Sobrien                    {\voffset}{\hoffset}%
9818174294Sobrien                    {\bindingoffset}{8pt}%
9819174294Sobrien                    {210mm}{148mm}%
982082794Sobrien  %
982182794Sobrien  \lispnarrowing = 0.2in
982282794Sobrien  \tolerance = 800
982382794Sobrien  \hfuzz = 1.2pt
9824174294Sobrien  \contentsrightmargin = 0pt
982582794Sobrien  \defbodyindent = 2mm
982682794Sobrien  \tableindent = 12mm
982782794Sobrien}}
982882794Sobrien
9829174294Sobrien% A specific text layout, 24x15cm overall, intended for A4 paper.
983042629Sobrien\def\afourlatex{{\globaldefs = 1
983142629Sobrien  \afourpaper
9832174294Sobrien  \internalpagesizes{237mm}{150mm}%
9833174294Sobrien                    {\voffset}{4.6mm}%
9834174294Sobrien                    {\bindingoffset}{7mm}%
9835174294Sobrien                    {297mm}{210mm}%
9836119679Smbr  %
9837174294Sobrien  % Must explicitly reset to 0 because we call \afourpaper.
9838119679Smbr  \globaldefs = 0
983942629Sobrien}}
984038494Sobrien
9841174294Sobrien% Use @afourwide to print on A4 paper in landscape format.
9842174294Sobrien\def\afourwide{{\globaldefs = 1
984342629Sobrien  \afourpaper
9844174294Sobrien  \internalpagesizes{241mm}{165mm}%
9845174294Sobrien                    {\voffset}{-2.95mm}%
9846174294Sobrien                    {\bindingoffset}{7mm}%
9847174294Sobrien                    {297mm}{210mm}%
9848174294Sobrien  \globaldefs = 0
9849174294Sobrien}}
985038494Sobrien
985142629Sobrien% @pagesizes TEXTHEIGHT[,TEXTWIDTH]
985242629Sobrien% Perhaps we should allow setting the margins, \topskip, \parskip,
985342629Sobrien% and/or leading, also. Or perhaps we should compute them somehow.
985482794Sobrien%
9855174294Sobrien\parseargdef\pagesizes{\pagesizesyyy #1,,\finish}
985642629Sobrien\def\pagesizesyyy#1,#2,#3\finish{{%
985742629Sobrien  \setbox0 = \hbox{\ignorespaces #2}\ifdim\wd0 > 0pt \hsize=#2\relax \fi
985842629Sobrien  \globaldefs = 1
985942629Sobrien  %
986042629Sobrien  \parskip = 3pt plus 2pt minus 1pt
986182794Sobrien  \setleading{\textleading}%
986242629Sobrien  %
9863310490Scy  \dimen0 = #1\relax
9864174294Sobrien  \advance\dimen0 by \voffset
9865174294Sobrien  %
9866174294Sobrien  \dimen2 = \hsize
9867174294Sobrien  \advance\dimen2 by \normaloffset
9868174294Sobrien  %
9869174294Sobrien  \internalpagesizes{#1}{\hsize}%
9870174294Sobrien                    {\voffset}{\normaloffset}%
9871174294Sobrien                    {\bindingoffset}{44pt}%
9872174294Sobrien                    {\dimen0}{\dimen2}%
987342629Sobrien}}
987438494Sobrien
987542629Sobrien% Set default to letter.
987682794Sobrien%
987742629Sobrien\letterpaper
987838494Sobrien
987982794Sobrien
988042629Sobrien\message{and turning on texinfo input format.}
988138494Sobrien
9882310490Scy\def^^L{\par} % remove \outer, so ^L can appear in an @comment
9883310490Scy
9884310490Scy% DEL is a comment character, in case @c does not suffice.
9885310490Scy\catcode`\^^? = 14
9886310490Scy
988738494Sobrien% Define macros to output various characters with catcode for normal text.
9888310490Scy\catcode`\"=\other \def\normaldoublequote{"}
9889310490Scy\catcode`\$=\other \def\normaldollar{$}%$ font-lock fix
9890310490Scy\catcode`\+=\other \def\normalplus{+}
9891310490Scy\catcode`\<=\other \def\normalless{<}
9892310490Scy\catcode`\>=\other \def\normalgreater{>}
9893310490Scy\catcode`\^=\other \def\normalcaret{^}
9894310490Scy\catcode`\_=\other \def\normalunderscore{_}
9895310490Scy\catcode`\|=\other \def\normalverticalbar{|}
9896310490Scy\catcode`\~=\other \def\normaltilde{~}
989738494Sobrien
9898174294Sobrien% This macro is used to make a character print one way in \tt
9899174294Sobrien% (where it can probably be output as-is), and another way in other fonts,
990038494Sobrien% where something hairier probably needs to be done.
990138494Sobrien%
990238494Sobrien% #1 is what to print if we are indeed using \tt; #2 is what to print
990338494Sobrien% otherwise.  Since all the Computer Modern typewriter fonts have zero
990438494Sobrien% interword stretch (and shrink), and it is reasonable to expect all
990538494Sobrien% typewriter fonts to have this, we can check that font parameter.
990638494Sobrien%
990782794Sobrien\def\ifusingtt#1#2{\ifdim \fontdimen3\font=0pt #1\else #2\fi}
990838494Sobrien
990982794Sobrien% Same as above, but check for italic font.  Actually this also catches
991082794Sobrien% non-italic slanted fonts since it is impossible to distinguish them from
991182794Sobrien% italic fonts.  But since this is only used by $ and it uses \sl anyway
991282794Sobrien% this is not a problem.
991382794Sobrien\def\ifusingit#1#2{\ifdim \fontdimen1\font>0pt #1\else #2\fi}
991482794Sobrien
991538494Sobrien% Turn off all special characters except @
991638494Sobrien% (and those which the user can use as if they were ordinary).
991738494Sobrien% Most of these we simply print from the \tt font, but for some, we can
991838494Sobrien% use math or other variants that look better in normal text.
991938494Sobrien
992038494Sobrien\catcode`\"=\active
992142629Sobrien\def\activedoublequote{{\tt\char34}}
992238494Sobrien\let"=\activedoublequote
992338494Sobrien\catcode`\~=\active
992442629Sobrien\def~{{\tt\char126}}
992538494Sobrien\chardef\hat=`\^
992638494Sobrien\catcode`\^=\active
992738494Sobrien\def^{{\tt \hat}}
992838494Sobrien
992938494Sobrien\catcode`\_=\active
993038494Sobrien\def_{\ifusingtt\normalunderscore\_}
9931310490Scy\let\realunder=_
993238494Sobrien% Subroutine for the previous macro.
9933174294Sobrien\def\_{\leavevmode \kern.07em \vbox{\hrule width.3em height.1ex}\kern .07em }
993438494Sobrien
993538494Sobrien\catcode`\|=\active
993642629Sobrien\def|{{\tt\char124}}
993738494Sobrien\chardef \less=`\<
993838494Sobrien\catcode`\<=\active
993938494Sobrien\def<{{\tt \less}}
994038494Sobrien\chardef \gtr=`\>
994138494Sobrien\catcode`\>=\active
994238494Sobrien\def>{{\tt \gtr}}
994338494Sobrien\catcode`\+=\active
994438494Sobrien\def+{{\tt \char 43}}
994582794Sobrien\catcode`\$=\active
9946119679Smbr\def${\ifusingit{{\sl\$}}\normaldollar}%$ font-lock fix
994738494Sobrien
994838494Sobrien% If a .fmt file is being used, characters that might appear in a file
994938494Sobrien% name cannot be active until we have parsed the command line.
995038494Sobrien% So turn them off again, and have \everyjob (or @setfilename) turn them on.
995138494Sobrien% \otherifyactive is called near the end of this file.
995238494Sobrien\def\otherifyactive{\catcode`+=\other \catcode`\_=\other}
995338494Sobrien
9954310490Scy% Used sometimes to turn off (effectively) the active characters even after
9955310490Scy% parsing them.
9956310490Scy\def\turnoffactive{%
9957310490Scy  \normalturnoffactive
9958310490Scy  \otherbackslash
9959310490Scy}
9960310490Scy
996138494Sobrien\catcode`\@=0
996238494Sobrien
9963174294Sobrien% \backslashcurfont outputs one backslash character in current font,
9964174294Sobrien% as in \char`\\.
9965174294Sobrien\global\chardef\backslashcurfont=`\\
9966174294Sobrien\global\let\rawbackslashxx=\backslashcurfont  % let existing .??s files work
996738494Sobrien
9968310490Scy% \realbackslash is an actual character `\' with catcode other, and
9969310490Scy% \doublebackslash is two of them (for the pdf outlines).
9970310490Scy{\catcode`\\=\other @gdef@realbackslash{\} @gdef@doublebackslash{\\}}
997138494Sobrien
9972310490Scy% In texinfo, backslash is an active character; it prints the backslash
9973310490Scy% in fixed width font.
9974310490Scy\catcode`\\=\active  % @ for escape char from now on.
9975174294Sobrien
9976310490Scy% The story here is that in math mode, the \char of \backslashcurfont
9977310490Scy% ends up printing the roman \ from the math symbol font (because \char
9978310490Scy% in math mode uses the \mathcode, and plain.tex sets
9979310490Scy% \mathcode`\\="026E).  It seems better for @backslashchar{} to always
9980310490Scy% print a typewriter backslash, hence we use an explicit \mathchar,
9981310490Scy% which is the decimal equivalent of "715c (class 7, e.g., use \fam;
9982310490Scy% ignored family value; char position "5C).  We can't use " for the
9983310490Scy% usual hex value because it has already been made active.
9984310490Scy@def@normalbackslash{{@tt @ifmmode @mathchar29020 @else @backslashcurfont @fi}}
9985310490Scy@let@backslashchar = @normalbackslash % @backslashchar{} is for user documents.
998638494Sobrien
9987310490Scy% On startup, @fixbackslash assigns:
9988310490Scy%  @let \ = @normalbackslash
9989310490Scy% \rawbackslash defines an active \ to do \backslashcurfont.
9990310490Scy% \otherbackslash defines an active \ to be a literal `\' character with
9991310490Scy% catcode other.  We switch back and forth between these.
9992310490Scy@gdef@rawbackslash{@let\=@backslashcurfont}
9993310490Scy@gdef@otherbackslash{@let\=@realbackslash}
999438494Sobrien
9995174294Sobrien% Same as @turnoffactive except outputs \ as {\tt\char`\\} instead of
9996310490Scy% the literal character `\'.  Also revert - to its normal character, in
9997310490Scy% case the active - from code has slipped in.
9998174294Sobrien%
9999310490Scy{@catcode`- = @active
10000310490Scy @gdef@normalturnoffactive{%
10001310490Scy   @let-=@normaldash
10002310490Scy   @let"=@normaldoublequote
10003310490Scy   @let$=@normaldollar %$ font-lock fix
10004310490Scy   @let+=@normalplus
10005310490Scy   @let<=@normalless
10006310490Scy   @let>=@normalgreater
10007310490Scy   @let\=@normalbackslash
10008310490Scy   @let^=@normalcaret
10009310490Scy   @let_=@normalunderscore
10010310490Scy   @let|=@normalverticalbar
10011310490Scy   @let~=@normaltilde
10012310490Scy   @markupsetuplqdefault
10013310490Scy   @markupsetuprqdefault
10014310490Scy   @unsepspaces
10015310490Scy }
10016310490Scy}
1001738494Sobrien
1001838494Sobrien% Make _ and + \other characters, temporarily.
1001938494Sobrien% This is canceled by @fixbackslash.
1002038494Sobrien@otherifyactive
1002138494Sobrien
1002238494Sobrien% If a .fmt file is being used, we don't want the `\input texinfo' to show up.
1002338494Sobrien% That is what \eatinput is for; after that, the `\' should revert to printing
1002438494Sobrien% a backslash.
1002538494Sobrien%
1002638494Sobrien@gdef@eatinput input texinfo{@fixbackslash}
1002738494Sobrien@global@let\ = @eatinput
1002838494Sobrien
1002938494Sobrien% On the other hand, perhaps the file did not have a `\input texinfo'. Then
10030310490Scy% the first `\' in the file would cause an error. This macro tries to fix
1003138494Sobrien% that, assuming it is called before the first `\' could plausibly occur.
10032310490Scy% Also turn back on active characters that might appear in the input
1003338494Sobrien% file name, in case not using a pre-dumped format.
1003438494Sobrien%
1003582794Sobrien@gdef@fixbackslash{%
1003682794Sobrien  @ifx\@eatinput @let\ = @normalbackslash @fi
1003782794Sobrien  @catcode`+=@active
1003882794Sobrien  @catcode`@_=@active
1003982794Sobrien}
1004038494Sobrien
1004182794Sobrien% Say @foo, not \foo, in error messages.
1004282794Sobrien@escapechar = `@@
1004338494Sobrien
10044310490Scy% These (along with & and #) are made active for url-breaking, so need
10045310490Scy% active definitions as the normal characters.
10046310490Scy@def@normaldot{.}
10047310490Scy@def@normalquest{?}
10048310490Scy@def@normalslash{/}
10049310490Scy
10050174294Sobrien% These look ok in all fonts, so just make them not special.
10051310490Scy% @hashchar{} gets its own user-level command, because of #line.
10052310490Scy@catcode`@& = @other @def@normalamp{&}
10053310490Scy@catcode`@# = @other @def@normalhash{#}
10054310490Scy@catcode`@% = @other @def@normalpercent{%}
1005582794Sobrien
10056310490Scy@let @hashchar = @normalhash
1005738494Sobrien
10058310490Scy@c Finally, make ` and ' active, so that txicodequoteundirected and
10059310490Scy@c txicodequotebacktick work right in, e.g., @w{@code{`foo'}}.  If we
10060310490Scy@c don't make ` and ' active, @code will not get them as active chars.
10061310490Scy@c Do this last of all since we use ` in the previous @catcode assignments.
10062310490Scy@catcode`@'=@active
10063310490Scy@catcode`@`=@active
10064310490Scy@markupsetuplqdefault
10065310490Scy@markupsetuprqdefault
10066310490Scy
1006738494Sobrien@c Local variables:
1006842629Sobrien@c eval: (add-hook 'write-file-hooks 'time-stamp)
1006938494Sobrien@c page-delimiter: "^\\\\message"
1007042629Sobrien@c time-stamp-start: "def\\\\texinfoversion{"
1007182794Sobrien@c time-stamp-format: "%:y-%02m-%02d.%02H"
1007242629Sobrien@c time-stamp-end: "}"
1007338494Sobrien@c End:
10074174294Sobrien
10075174294Sobrien@c vim:sw=2:
10076174294Sobrien
10077174294Sobrien@ignore
10078174294Sobrien   arch-tag: e1b36e32-c96e-4135-a41a-0b2efa2ea115
10079174294Sobrien@end ignore
10080