1 % \iffalse meta-comment
5 % The LaTeX3 Project and any individual authors listed elsewhere
8 % This file is part of the Standard LaTeX `Tools Bundle'.
9 % -------------------------------------------------------
11 % It may be distributed and/or modified under the
12 % conditions of the LaTeX Project Public License, either version 1.3c
13 % of this license or (at your option) any later version.
14 % The latest version of this license is in
15 % http://www.latex-project.org/lppl.txt
16 % and version 1.3c or later is part of all distributions of LaTeX
17 % version 2005/12/01 or later.
19 % The list of all files belonging to the LaTeX `Tools Bundle' is
20 % given in the file `manifest.txt'.
24 %% File: hhline.dtx Copyright (C) 1991-1994 David Carlisle
26 %<package>\NeedsTeXFormat{LaTeX2e}
27 %<package>\ProvidesPackage{hhline}
28 %<package> [2014/10/28 v2.03 Table rule package (DPC)]
31 \documentclass{ltxdoc}
33 \GetFileInfo{hhline.sty}
35 \title{The \textsf{hhline} package\thanks{This file
36 has version number \fileversion, last
38 \author{David Carlisle}
40 \MaintainedByLaTeXTeam{tools}
49 % \changes{v1.00}{1991/06/04}{Initial Version}
50 % \changes{v2.00}{1991/11/06}
51 % {Add tilde which allows \cmd\cline-like constructions.}
52 % \changes{v2.01}{1992/06/26}
53 % {Re-issue for the new doc and docstrip.}
54 % \changes{v2.02}{1994/03/14}
55 % {Update for LaTeX2e.}
56 % \changes{v2.03}{1994/05/23}
57 % {New style warning.}
64 % "\hhline" produces a line like "\hline", or a double line like
65 % "\hline\hline", except for its interaction with vertical lines.
71 % \section{Introduction}
72 % The argument to "\hhline" is similar to the preamble of an {\tt
73 % array} or {\tt tabular}. It consists of a list of tokens with the
77 % "=" & A double hline the width of a column.\\
78 % "-" & A single hline the width of a column.\\[10pt]
79 % "~" & A column with no hline.\\[10pt]
81 % "|" & A vline which `cuts' through a double (or single) hline.\\
82 % ":" & A vline which is broken by a double hline.\\[10pt]
84 % "#" & A double hline segment between two vlines.\\
85 % "t" & The top half of a double hline segment.\\
86 % "b" & The bottom half of a double hline segment.\\
88 % "*" & "*{3}{==#}" expands to "==#==#==#",
89 % as in the {\tt*}-form for the preamble.
92 % If a double vline is specified ("||" or "::") then the hlines
93 % produced by "\hhline" are broken. To obtain the effect of an hline
94 % `cutting through' the double vline, use a "#" or omit the vline
95 % specifiers, depending on whether or not you wish the double vline to
98 % The tokens {\tt t} and {\tt b} must be used between two vertical
99 % rules. "|tb|" produces the same lines as "#", but is much less
100 % efficient. The main use for these are to make constructions like
101 % "|t:" (top left corner) and ":b|" (bottom right corner).
103 % If "\hhline" is used to make a single hline, then the argument
104 % should only contain the tokens "-", "~" and "|" (and
105 % {\tt*}-expressions).
107 % An example using most of these features is:
109 % \vcenter{\hsize=2in\begin{verbatim}
110 % \begin{tabular}{||cc||c|c||}
111 % \hhline{|t:==:t:==:t|}
113 % \hhline{|:==:|~|~||}
117 % \hhline{||--||--||}
119 % \hhline{|b:==:b:==:b|}
124 % \begin{tabular}{||cc||c|c||}
125 % \hhline{|t:==:t:==:t|}
127 % \hhline{|:==:|~|~||}
131 % \hhline{||--||--||}
133 % \hhline{|b:==:b:==:b|}
137 % The lines produced by \LaTeX's "\hline" consist of a single (\TeX\
138 % primitive) "\hrule". The lines produced by "\hhline" are made
139 % up of lots of small line segments. \TeX\ will place these very
140 % accurately in the {\tt .dvi} file, but the program that you use to
141 % print the {\tt .dvi} file may not line up these segments exactly. (A
142 % similar problem can occur with diagonal lines in the {\tt picture}
145 % If this effect causes a problem, you could try a different driver
146 % program, or if this is not possible, increasing "\arrayrulewidth"
147 % may help to reduce the effect.
151 % \section{The Macros}
157 % \begin{macro}{\HH@box}
158 % Makes a box containing a double hline segment. The most common case,
159 % both rules of length "\doublerulesep" will be stored in "\box1", this
160 % is not initialised until "\hhline" is called as the user may change
161 % the parameters "\doublerulesep" and "\arrayrulewidth". The two
162 % arguments to "\HH@box" are the widths (ie lengths) of the top and
165 \def\HH@box#1#2{\vbox{%
166 \hrule \@height \arrayrulewidth \@width #1
167 \vskip \doublerulesep
168 \hrule \@height \arrayrulewidth \@width #2}}
172 % \begin{macro}{\HH@add}
173 % Build up the preamble in the register "\toks@".
175 \def\HH@add#1{\toks@\expandafter{\the\toks@#1}}
179 % \begin{macro}{\HH@xexpast}
180 % \begin{macro}{\HH@xexnoop}
181 % We `borrow' the version of "\@xexpast" from Mittelbach's array.sty,
182 % as this allows "#" to appear in the argument list.
184 \def\HH@xexpast#1*#2#3#4\@@{%
186 \toks@={#1}\@temptokena={#3}%
187 \let\the@toksz\relax \let\the@toks\relax
188 \def\@tempa{\the@toksz}%
189 \ifnum\@tempcnta >0 \@whilenum\@tempcnta >0\do
190 {\edef\@tempa{\@tempa\the@toks}\advance \@tempcnta \m@ne}%
191 \let \@tempb \HH@xexpast \else
192 \let \@tempb \HH@xexnoop \fi
193 \def\the@toksz{\the\toks@}\def\the@toks{\the\@temptokena}%
194 \edef\@tempa{\@tempa}%
195 \expandafter \@tempb \@tempa #4\@@}
197 \def\HH@xexnoop#1\@@{}
202 % \begin{macro}{\hhline}
203 % Use a simplified version of "\@mkpream" to break apart the argument
204 % to "\hhline". Actually it is oversimplified, It assumes that the
205 % vertical rules are at the end of the column. If you were to specify
206 % "c|@{xx}|" in the array argument, then "\hhline" would not be
207 % able to access the first vertical rule. (It ought to have an "@"
208 % option, and add "\leaders" up to the width of a box containing the
209 % "@"-expression. We use a loop made with "\futurelet" rather
210 % than "\@tfor" so that we can use "#" to denote the crossing of
211 % a double hline with a double vline.\\
212 % "\if@firstamp" is true in the first column and false otherwise.\\
213 % "\if@tempswa" is true if the previous entry was a vline
216 \def\hhline#1{\omit\@firstamptrue\@tempswafalse
218 % Put two rules of width "\doublerulesep" in "\box1"
220 \global\setbox\@ne\HH@box\doublerulesep\doublerulesep
222 % If Mittelbach's {\tt array.sty} is loaded, we do not need the negative
223 % "\hskip"'s around vertical rules.
225 \xdef\@tempc{\ifx\extrarowheight\HH@undef\hskip-.5\arrayrulewidth\fi}%
227 % Now expand the {\tt*}-forms and add dummy tokens ( "\relax" and
228 % "`" ) to either end of the token list. Call "\HH@let" to start
229 % processing the token list.
231 \HH@xexpast\relax#1*0x\@@\toks@{}\expandafter\HH@let\@tempa`}
235 % \begin{macro}{\HH@let}
236 % Discard the last token, look at the next one.
238 \def\HH@let#1{\futurelet\@tempb\HH@loop}
242 % \begin{macro}{\HH@loop}
243 % The main loop. Note we use "\ifx" rather than "\if" in
244 % version~2 as the new token "~" is active.
248 % If next token is "`", stop the loop and put the lines into this row
251 \ifx\@tempb`\def\next##1{\the\toks@\cr}\else\let\next\HH@let
253 % "|", add a vertical rule (across either a double or
256 \ifx\@tempb|\if@tempswa\HH@add{\hskip\doublerulesep}\fi\@tempswatrue
257 \HH@add{\@tempc\vline\@tempc}\else
259 % ":", add a broken vertical rule (across a double hline).
261 \ifx\@tempb:\if@tempswa\HH@add{\hskip\doublerulesep}\fi\@tempswatrue
262 \HH@add{\@tempc\HH@box\arrayrulewidth\arrayrulewidth\@tempc}\else
264 % "#", add a double hline segment between two vlines.
266 \ifx\@tempb##\if@tempswa\HH@add{\hskip\doublerulesep}\fi\@tempswatrue
267 \HH@add{\@tempc\vline\@tempc\copy\@ne\@tempc\vline\@tempc}\else
269 % "~", A column with no hline (this gives an effect similar to
272 \ifx\@tempb~\@tempswafalse
273 \if@firstamp\@firstampfalse\else\HH@add{&\omit}\fi
276 % "-", add a single hline across the column.
278 \ifx\@tempb-\@tempswafalse
279 \if@firstamp\@firstampfalse\else\HH@add{&\omit}\fi
280 \HH@add{\leaders\hrule\@height\arrayrulewidth\hfil}\else
282 % "=", add a double hline across the column.
284 \ifx\@tempb=\@tempswafalse
285 \if@firstamp\@firstampfalse\else\HH@add{&\omit}\fi
287 % Put in as many copies of "\box1" as possible with
288 % "\leaders", this may leave gaps at the ends, so put an extra box
289 % at each end, overlapping the "\leaders".
292 {\rlap{\copy\@ne}\leaders\copy\@ne\hfil\llap{\copy\@ne}}\else
294 % "t", add the top half of a double hline segment, in a "\rlap"
295 % so that it may be used with {\tt b}.
297 \ifx\@tempb t\HH@add{\rlap{\HH@box\doublerulesep\z@}}\else
299 % "b", add the bottom half of a double hline segment in a "\rlap"
300 % so that it may be used with {\tt t}.
302 \ifx\@tempb b\HH@add{\rlap{\HH@box\z@\doublerulesep}}\else
304 % Otherwise ignore the token, with a warning.
306 \PackageWarning{hhline}%
307 {\meaning\@tempb\space ignored in \noexpand\hhline argument%
309 \fi\fi\fi\fi\fi\fi\fi\fi\fi
311 % Go around the loop again.