4 Copyright (c) 2014 - 2015 Steffen (Daode) Nurpmeso <sdaoden@users.sf.net>.
6 Copyright (C) 2005, 2006 Free Software Foundation, Inc.
7 written by Joachim Walsdorff <Joachim.Walsdorff@urz.uni-heidelberg.de>.
9 This is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free
11 Software Foundation; either version 2, or (at your option) any later
14 This is distributed in the hope that it will be useful, but WITHOUT
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
19 You should have received a copy of the GNU General Public License
20 along with groff; see the file COPYING. If not, write to the Free
21 Software Foundation, 51 Franklin St - Fifth Floor, Boston, MA
32 .\" ** Some macros and default settings needed by hdtbl **
35 .\" Utility macro: .t*getarg <key> ...
37 .\" Get macro argument. This macro searches <key> in the
38 .\" remaining arguments and assigns its value to a string
39 .\" register named <key>. The following syntax forms are
42 .\" <key>=<val> Assign <val> to string <key>.
43 .\" <val> must not contain spaces.
44 .\" <key>='<val>' Assign <val> to string <key>.
45 .\" <val> can contain spaces.
46 .\" <key>= Assign `=' to string <key>.
47 .\" <key> Assign `key' to string <key>.
49 .\" After return, the string `args' contains the remaining
52 .\" Example: With the definition of string `foo' as
54 .\" .ds foo aaa=xxx bbb ccc='yyy zzz' ddd= eee
56 .\" a call to `t*getarg' with
58 .\" .t*getarg ccc \*[foo]
60 .\" sets string `ccc' to value `yyy zzz'. The string `args'
61 .\" now contains `aaa=xxx bbb ddd= eee'. An additional call
64 .\" .t*getarg ddd \*[args]
66 .\" sets string `ddd' to value `=', and `args' contains
67 .\" `aaa=xxx bbb eee'.
84 . if (\\n[*] > \\n[**]) \{\
85 . as args " "\\*[**]"\" value too short, repeat
88 . substring * 0 (\\n[*] - 1)
89 . \" The surrounding \? escapes emulate string comparison.
90 . ie !"\?\\*[$1]\?"\?\\*[*]\?" \{\
91 . as args " "\\*[**]"\" key not found, repeat
95 . ie "\?\\*[**]\?"\?\\*[$1]\?" \
96 . ds \\*[$1] \\*[$1]\" return key as string
98 . ie "\?\\*[**]\?"\?\\*[$1]=\?" \
99 . ds \\*[$1] =\" return `='
101 . substring ** (\\n[*] + 1) -1
105 . \" check whether value starts with quote
106 . if "\?\\*[*]\?"\?'\?" \{\
111 . \" search final quote
112 . ie "\?\\*[*]\?"\?'\?" \
115 . as \\*[$1] \\*[**] \" not found, append argument
118 . ds ** \\$1\" get next argument
123 . if "\?\\*[*]\?"\?'\?" \{\
125 . break \" break if no final quote
128 . as \\*[$1] \\*[**] \" otherwise append and repeat
132 . as \\*[$1] \\*[**]\"
143 .\" Utility macro: .t*index <string1> <string2>
145 .\" Check whether <string2> is a substring of <string> and
146 .\" return its position in number register `t*index', starting
147 .\" with 1. If not found, return 0. If <string2> is empty,
148 .\" set `t*index' to -999.
159 . while (\\n+[*] < \\n[**]) \{\
161 . substring * \\n[*] (\\n[*] + \\n[$2] - 1)
162 . \" The surrounding \? escapes emulate string comparison.
163 . if "\?\\*[*]\?"\?\\$2\?" \
167 . ie (\\n[*] == \\n[**]) \
170 . nr t*index (\\n[*] + 1)
174 .\" ** non-accumulating space .t*SP [v]
175 .\" ** nl vor erster Seite -1, oben auf Seite 0 resp. tH
176 .\" ** .k nach .sp oder .br 0,
177 .\" ** sonst Laenge der angefangenen Zeile
178 .\" ** Der Merker M# fuer vorangegangenes .t*SP wird in .HM am
179 .\" ** Seitenanfang zurueckgesetzt.
180 .\" ** ganz richtig ist .sp + .br = .br + .sp = .sp
183 . br \" start very first page
184 . nr * \\n[.p] \" save current page length
187 . pl +1 \" without arg increase page length by 1v
189 . pl +\\$1 \" otherwise use \\$1
191 . nr ** (\\n[.p] - \\n[*]) \" ** now holds arg for .t*SP in base units
192 . pl \\n[*]u \" restore page length
194 . \" we do nothing at start of new page or column
195 . if ((\\n[nl] - \\n[tH]) & (\\n[nl] - \\n[<<]) : \\n[.k]) \{\
196 . ie ((\\n[.d] - \\n[M#]) : \\n[.k]) \{\
197 . sp \\n[**]u \" execute .sp
198 . nr S# \\n[**] \" store ** in S#
201 . if (\\n[**] - \\n[S#]) \{\
202 . sp (\\n[**]u - \\n[S#]u)\" emit difference to previous .t*SP
203 . nr S# \\n[**] \" store ** in S#
206 . nr M# \\n[.d] \" store vertical position .d in M#
211 .\" ** Perform all arguments once
212 .\" ** t*P1 is nestable
214 . \" `while' command is about five times faster than recursion!
222 .\" ** Hilfsmakro zum Einstellen von Schriftgroesse und
223 .\" ** Zeilenabstand, bezogen auf Anfangswerte \n[t*s] und \n[t*v]
224 .\" ** sowie fuer Hyphenation:
225 .\" ** .t*pv t*s t*v hy# hart; macht .br
226 .\" ** Bei 4. Argument setzen der Register s und v und hy.
227 .\" ** Fuer angefangene Zeile die vorgefundenen Einstellungen
232 . ps (\\n[t*s]u * \\$1z / 1z)
235 . vs (\\n[t*v]u * \\$2p / 1p)
237 . vs (\\n[t*v]u * \\$1p / 1p)
252 .\" ** Hilfsmakros pop/pops/popr (pop stackelement):
253 .\" ** pop or popr: pop register
254 .\" ** pops: pop string
255 .\" ** .pop[s|r] reg|string stackname
256 .\" ** reg|string: name of reg/string to get the
257 .\" ** popped element
258 .\" ** stack: name of stack
261 . ds \\$2 \\$4\" pop first stackelement
265 . ds $3 \\$3\" remember stackname
266 . shift 4 \" shift four args
268 . ds \\*[$3] "\\$@\" fill stack with remaining elements
272 . *pop \\$0 \\$1 \\$2 \\*[\\$2]
279 .\" ** process diversion
282 . nf \" diversion is already formatted - output it unchanged
283 . \\$1 \" output the diversion ...
284 . rm \\$1 \" ... and remove it
286 . fi \" reactivate formatting
289 .\" ** Error check possibility for EOF
291 . if !"\\*[t*kept]"" \{\
292 . tm1 "hdtbl: Not all tables have been printed.
293 . tm1 " Add `.bp' at the end of your document.
295 . if !"\\*[t*held]"" \{\
296 . tm1 "hdtbl: There are held tables which haven't been printed.
297 . tm1 " Add `.t*free' at the end of your document.
300 . tm hdtbl: Missing `.ETB' macro; last .TBL in \\*[t*FN] at line \\*[t*LN].