doc-src/rail.sty
changeset 42632 ebec0c1a5984
parent 42631 028f94955436
child 42633 f86467c5a72c
equal deleted inserted replaced
42631:028f94955436 42632:ebec0c1a5984
     1 % rail.sty - style file to support railroad diagrams
       
     2 %
       
     3 % 09-Jul-90 L. Rooijakkers
       
     4 % 08-Oct-90 L. Rooijakkers	fixed centering bug when \rail@tmpc<0.
       
     5 % 07-Feb-91 L. Rooijakkers	added \railoptions command, indexing
       
     6 % 08-Feb-91 L. Rooijakkers	minor fixes
       
     7 % 28-Jun-94 K. Barthelmann	turned into LaTeX2e package
       
     8 % 08-Dec-96 K. Barthelmann	replaced \@writefile
       
     9 % 13-Dec-96 K. Barthelmann	cleanup
       
    10 % 22-Feb-98 K. Barthelmann	fixed catcodes of special characters
       
    11 % 18-Apr-98 K. Barthelmann	fixed \par handling
       
    12 % 19-May-98 J. Olsson		Added new macros to support arrow heads.
       
    13 % 26-Jul-98 K. Barthelmann	changed \par to output newlines
       
    14 %
       
    15 % This style file needs to be used in conjunction with the 'rail'
       
    16 % program. Running LaTeX as 'latex file' produces file.rai, which should be
       
    17 % processed by Rail with 'rail file'. This produces file.rao, which will
       
    18 % be picked up by LaTeX on the next 'latex file' run.
       
    19 %
       
    20 % LaTeX will warn if there is no file.rao or it's out of date.
       
    21 %
       
    22 % The macros in this file thus consist of two parts: those that read and
       
    23 % write the .rai and .rao files, and those that do the actual formatting
       
    24 % of the railroad diagrams.
       
    25 
       
    26 \NeedsTeXFormat{LaTeX2e}
       
    27 \ProvidesPackage{rail}[1998/05/19]
       
    28 
       
    29 % railroad diagram formatting parameters (user level)
       
    30 % all of these are copied into their internal versions by \railinit
       
    31 %
       
    32 % \railunit : \unitlength within railroad diagrams
       
    33 % \railextra : extra length at outside of diagram
       
    34 % \railboxheight : height of ovals and frames
       
    35 % \railboxskip : vertical space between lines
       
    36 % \railboxleft : space to the left of a box
       
    37 % \railboxright : space to the right of a box
       
    38 % \railovalspace : extra space around contents of oval
       
    39 % \railframespace : extra space around contents of frame
       
    40 % \railtextleft : space to the left of text
       
    41 % \railtextright : space to the right of text
       
    42 % \railtextup : space to lift text up
       
    43 % \railjoinsize : circle size of join/split arcs
       
    44 % \railjoinadjust : space to adjust join
       
    45 %
       
    46 % \railnamesep : separator between name and rule body
       
    47 
       
    48 \newlength\railunit
       
    49 \newlength\railextra
       
    50 \newlength\railboxheight
       
    51 \newlength\railboxskip
       
    52 \newlength\railboxleft
       
    53 \newlength\railboxright
       
    54 \newlength\railovalspace
       
    55 \newlength\railframespace
       
    56 \newlength\railtextleft
       
    57 \newlength\railtextright
       
    58 \newlength\railtextup
       
    59 \newlength\railjoinsize
       
    60 \newlength\railjoinadjust
       
    61 \newlength\railnamesep
       
    62 
       
    63 % initialize the parameters
       
    64 
       
    65 \setlength\railunit{1sp}
       
    66 \setlength\railextra{4ex}
       
    67 \setlength\railboxleft{1ex}
       
    68 \setlength\railboxright{1ex}
       
    69 \setlength\railovalspace{2ex}
       
    70 \setlength\railframespace{2ex}
       
    71 \setlength\railtextleft{1ex}
       
    72 \setlength\railtextright{1ex}
       
    73 \setlength\railjoinadjust{0pt}
       
    74 \setlength\railnamesep{1ex}
       
    75 
       
    76 \DeclareOption{10pt}{
       
    77   \setlength\railboxheight{16pt}
       
    78   \setlength\railboxskip{24pt}
       
    79   \setlength\railtextup{5pt}
       
    80   \setlength\railjoinsize{16pt}
       
    81 }
       
    82 \DeclareOption{11pt}{
       
    83   \setlength\railboxheight{16pt}
       
    84   \setlength\railboxskip{24pt}
       
    85   \setlength\railtextup{5pt}
       
    86   \setlength\railjoinsize{16pt}
       
    87 }
       
    88 \DeclareOption{12pt}{
       
    89   \setlength\railboxheight{20pt}
       
    90   \setlength\railboxskip{28pt}
       
    91   \setlength\railtextup{6pt}
       
    92   \setlength\railjoinsize{20pt}
       
    93 }
       
    94 
       
    95 \ExecuteOptions{10pt}
       
    96 \ProcessOptions
       
    97 
       
    98 % internal versions of the formatting parameters
       
    99 %
       
   100 % \rail@extra   : \railextra
       
   101 % \rail@boxht   : \railboxheight
       
   102 % \rail@boxsp   : \railboxskip
       
   103 % \rail@boxlf   : \railboxleft
       
   104 % \rail@boxrt   : \railboxright
       
   105 % \rail@boxhht  : \railboxheight / 2
       
   106 % \rail@ovalsp  : \railovalspace
       
   107 % \rail@framesp : \railframespace
       
   108 % \rail@textlf  : \railtextleft
       
   109 % \rail@textrt  : \railtextright
       
   110 % \rail@textup  : \railtextup
       
   111 % \rail@joinsz  : \railjoinsize
       
   112 % \rail@joinhsz : \railjoinsize / 2
       
   113 % \rail@joinadj : \railjoinadjust
       
   114 %
       
   115 % \railinit : internalize all of the parameters.
       
   116 
       
   117 \newcount\rail@extra
       
   118 \newcount\rail@boxht
       
   119 \newcount\rail@boxsp
       
   120 \newcount\rail@boxlf
       
   121 \newcount\rail@boxrt
       
   122 \newcount\rail@boxhht
       
   123 \newcount\rail@ovalsp
       
   124 \newcount\rail@framesp
       
   125 \newcount\rail@textlf
       
   126 \newcount\rail@textrt
       
   127 \newcount\rail@textup
       
   128 \newcount\rail@joinsz
       
   129 \newcount\rail@joinhsz
       
   130 \newcount\rail@joinadj
       
   131 
       
   132 \newcommand\railinit{
       
   133 \rail@extra=\railextra
       
   134 \divide\rail@extra by \railunit
       
   135 \rail@boxht=\railboxheight
       
   136 \divide\rail@boxht by \railunit
       
   137 \rail@boxsp=\railboxskip
       
   138 \divide\rail@boxsp by \railunit
       
   139 \rail@boxlf=\railboxleft
       
   140 \divide\rail@boxlf by \railunit
       
   141 \rail@boxrt=\railboxright
       
   142 \divide\rail@boxrt by \railunit
       
   143 \rail@boxhht=\railboxheight
       
   144 \divide\rail@boxhht by \railunit
       
   145 \divide\rail@boxhht by 2
       
   146 \rail@ovalsp=\railovalspace
       
   147 \divide\rail@ovalsp by \railunit
       
   148 \rail@framesp=\railframespace
       
   149 \divide\rail@framesp by \railunit
       
   150 \rail@textlf=\railtextleft
       
   151 \divide\rail@textlf by \railunit
       
   152 \rail@textrt=\railtextright
       
   153 \divide\rail@textrt by \railunit
       
   154 \rail@textup=\railtextup
       
   155 \divide\rail@textup by \railunit
       
   156 \rail@joinsz=\railjoinsize
       
   157 \divide\rail@joinsz by \railunit
       
   158 \rail@joinhsz=\railjoinsize
       
   159 \divide\rail@joinhsz by \railunit
       
   160 \divide\rail@joinhsz by 2
       
   161 \rail@joinadj=\railjoinadjust
       
   162 \divide\rail@joinadj by \railunit
       
   163 }
       
   164 
       
   165 \AtBeginDocument{\railinit}
       
   166 
       
   167 % \rail@param : declarations for list environment
       
   168 %
       
   169 % \railparam{TEXT} : sets \rail@param to TEXT
       
   170 %
       
   171 % \rail@reserved : characters reserved for grammar
       
   172 
       
   173 \newcommand\railparam[1]{
       
   174 \def\rail@param{
       
   175   \setlength\leftmargin{0pt}\setlength\rightmargin{0pt}
       
   176   \setlength\labelwidth{0pt}\setlength\labelsep{0pt}
       
   177   \setlength\itemindent{0pt}\setlength\listparindent{0pt}
       
   178   #1
       
   179 }
       
   180 }
       
   181 \railparam{}
       
   182 
       
   183 \newtoks\rail@reserved
       
   184 \rail@reserved={:;|*+?[]()'"}
       
   185 
       
   186 % \rail@termfont : format setup for terminals
       
   187 %
       
   188 % \rail@nontfont : format setup for nonterminals
       
   189 %
       
   190 % \rail@annofont : format setup for annotations
       
   191 %
       
   192 % \rail@rulefont : format setup for rule names
       
   193 %
       
   194 % \rail@indexfont : format setup for index entry
       
   195 %
       
   196 % \railtermfont{TEXT} : set terminal format setup to TEXT
       
   197 %
       
   198 % \railnontermfont{TEXT} : set nonterminal format setup to TEXT
       
   199 %
       
   200 % \railannotatefont{TEXT} : set annotation format setup to TEXT
       
   201 %
       
   202 % \railnamefont{TEXT} : set rule name format setup to TEXT
       
   203 %
       
   204 % \railindexfont{TEXT} : set index entry format setup to TEXT
       
   205 
       
   206 \def\rail@termfont{\ttfamily\upshape}
       
   207 \def\rail@nontfont{\rmfamily\upshape}
       
   208 \def\rail@annofont{\rmfamily\itshape}
       
   209 \def\rail@namefont{\rmfamily\itshape}
       
   210 \def\rail@indexfont{\rmfamily\itshape}
       
   211 
       
   212 \newcommand\railtermfont[1]{
       
   213 \def\rail@termfont{#1}
       
   214 }
       
   215 
       
   216 \newcommand\railnontermfont[1]{
       
   217 \def\rail@nontfont{#1}
       
   218 }
       
   219 
       
   220 \newcommand\railannotatefont[1]{
       
   221 \def\rail@annofont{#1}
       
   222 }
       
   223 
       
   224 \newcommand\railnamefont[1]{
       
   225 \def\rail@namefont{#1}
       
   226 }
       
   227 
       
   228 \newcommand\railindexfont[1]{
       
   229 \def\rail@indexfont{#1}
       
   230 }
       
   231 
       
   232 % railroad read/write macros
       
   233 %
       
   234 % \begin{rail} TEXT \end{rail} : TEXT is written out to the .rai file,
       
   235 %                                as \rail@i{NR}{TEXT}. Then the matching
       
   236 %                                \rail@o{NR}{FMT} from the .rao file is
       
   237 %                                executed (if defined).
       
   238 %
       
   239 % \railoptions{OPTIONS} : OPTIONS are written out to the .rai file,
       
   240 %                         as \rail@p{OPTIONS}.
       
   241 %
       
   242 % \railterm{IDENT,IDENT,...} : format IDENT as terminals. writes out
       
   243 %                              \rail@t{IDENT} to the .rai file
       
   244 %
       
   245 % \railalias{IDENT}{TEXT} : format IDENT as TEXT. defines \rail@t@IDENT as
       
   246 %                           TEXT.
       
   247 %
       
   248 % \railtoken{IDENT}{TEXT} : abbreviates \railalias{IDENT}{TEXT}\railterm{IDENT}
       
   249 %                           (for backward compatibility)
       
   250 %
       
   251 % \rail@setcodes : guards special characters
       
   252 %
       
   253 % \rail@makeother{CHARACTER} : sets \catcode of CHARACTER to "other"
       
   254 %                              used inside a loop for \rail@setcodes
       
   255 %
       
   256 % \rail@nr : railroad diagram counter
       
   257 %
       
   258 % \ifrail@match : current \rail@i{NR}{TEXT} matches
       
   259 %
       
   260 % \rail@first : actions to be done first. read in .rao file,
       
   261 %               open .rai file if \@filesw true, undefine \rail@first.
       
   262 %               executed from \begin{rail}, \railoptions and \railterm.
       
   263 %
       
   264 % \rail@i{NR}{TEXT} : defines \rail@i@NR as TEXT. written to the .rai
       
   265 %                     file by \rail, read from the .rao file by
       
   266 %                     \rail@first
       
   267 %
       
   268 % \rail@t{IDENT} : tells Rail that IDENT is to be custom formatted,
       
   269 %                  written to the .rai file by \railterm.
       
   270 %
       
   271 % \rail@o{NR}{TEXT} : defines \rail@o@NR as TEXT, read from the .rao
       
   272 %                     file by \rail@first.
       
   273 %
       
   274 % \rail@p{OPTIONS} : pass options to rail, written to the .rai file by
       
   275 %                    \railoptions
       
   276 %
       
   277 % \rail@write{TEXT} : write TEXT to the .rai file
       
   278 %
       
   279 % \rail@warn : warn user for mismatching diagrams
       
   280 %
       
   281 % \rail@endwarn : either \relax or \rail@warn
       
   282 %
       
   283 % \ifrail@all : checked at the end of the document
       
   284 
       
   285 \def\rail@makeother#1{
       
   286   \expandafter\catcode\expandafter`\csname\string #1\endcsname=12
       
   287 }
       
   288 
       
   289 \def\rail@setcodes{
       
   290 \let\par=\relax
       
   291 \let\\=\relax
       
   292 \expandafter\@tfor\expandafter\rail@symbol\expandafter:\expandafter=%
       
   293   \the\rail@reserved
       
   294 \do{\expandafter\rail@makeother\rail@symbol}
       
   295 }
       
   296 
       
   297 \newcount\rail@nr
       
   298 
       
   299 \newif\ifrail@all
       
   300 \rail@alltrue
       
   301 
       
   302 \newif\ifrail@match
       
   303 
       
   304 \def\rail@first{
       
   305 \begingroup
       
   306 \makeatletter
       
   307 \rail@setcodes
       
   308 \InputIfFileExists{\jobname.rao}{}{\PackageInfo{rail}{No file \jobname.rao}}
       
   309 \makeatother
       
   310 \endgroup
       
   311 \if@filesw
       
   312 \newwrite\tf@rai
       
   313 \immediate\openout\tf@rai=\jobname.rai
       
   314 \fi
       
   315 \global\let\rail@first=\relax
       
   316 }
       
   317 
       
   318 \long\def\rail@body#1\end{
       
   319 {
       
   320 \newlinechar=`^^J
       
   321 \def\par{\string\par^^J}
       
   322 \rail@write{\string\rail@i{\number\rail@nr}{#1}}
       
   323 }
       
   324 \xdef\rail@i@{#1}
       
   325 \end
       
   326 }
       
   327 
       
   328 \newenvironment{rail}{
       
   329 \global\advance\rail@nr by 1
       
   330 \rail@first
       
   331 \begingroup
       
   332 \rail@setcodes
       
   333 \rail@body
       
   334 }{
       
   335 \endgroup
       
   336 \rail@matchtrue
       
   337 \@ifundefined{rail@o@\number\rail@nr}{\rail@matchfalse}{}
       
   338 \expandafter\ifx\csname rail@i@\number\rail@nr\endcsname\rail@i@
       
   339 \else
       
   340 \rail@matchfalse
       
   341 \fi
       
   342 \ifrail@match
       
   343 \csname rail@o@\number\rail@nr\endcsname
       
   344 \else
       
   345 \PackageWarning{rail}{Railroad diagram {\number\rail@nr} doesn't match}
       
   346 \global\let\rail@endwarn=\rail@warn
       
   347 \begin{list}{}{\rail@param}
       
   348 \rail@begin{1}{}
       
   349 \rail@setbox{\bfseries ???}
       
   350 \rail@oval
       
   351 \rail@end
       
   352 \end{list}
       
   353 \fi
       
   354 }
       
   355 
       
   356 \newcommand\railoptions[1]{
       
   357 \rail@first
       
   358 \rail@write{\string\rail@p{#1}}
       
   359 }
       
   360 
       
   361 \newcommand\railterm[1]{
       
   362 \rail@first
       
   363 \@for\rail@@:=#1\do{
       
   364 \rail@write{\string\rail@t{\rail@@}}
       
   365 }
       
   366 }
       
   367 
       
   368 \newcommand\railalias[2]{
       
   369 \expandafter\def\csname rail@t@#1\endcsname{#2}
       
   370 }
       
   371 
       
   372 \newcommand\railtoken[2]{\railalias{#1}{#2}\railterm{#1}}
       
   373 
       
   374 \long\def\rail@i#1#2{
       
   375 \expandafter\gdef\csname rail@i@#1\endcsname{#2}
       
   376 }
       
   377 
       
   378 \def\rail@o#1#2{
       
   379 \expandafter\gdef\csname rail@o@#1\endcsname{
       
   380 \begin{list}{}{\rail@param}
       
   381 #2
       
   382 \end{list}
       
   383 }
       
   384 }
       
   385 
       
   386 \def\rail@t#1{}
       
   387 
       
   388 \def\rail@p#1{}
       
   389 
       
   390 \long\def\rail@write#1{\@ifundefined{tf@rai}{}{\immediate\write\tf@rai{#1}}}
       
   391 
       
   392 \def\rail@warn{
       
   393 \PackageWarningNoLine{rail}{Railroad diagram(s) may have changed.
       
   394                             Use 'rail' and rerun}
       
   395 }
       
   396 
       
   397 \let\rail@endwarn=\relax
       
   398 
       
   399 \AtEndDocument{\rail@endwarn}
       
   400 
       
   401 % index entry macro
       
   402 %
       
   403 % \rail@index{IDENT} : add index entry for IDENT
       
   404 
       
   405 \def\rail@index#1{
       
   406 \index{\rail@indexfont#1}
       
   407 }
       
   408 
       
   409 % railroad formatting primitives
       
   410 %
       
   411 % \rail@x : current x
       
   412 % \rail@y : current y
       
   413 % \rail@ex : current end x
       
   414 % \rail@sx : starting x for \rail@cr
       
   415 % \rail@rx : rightmost previous x for \rail@cr
       
   416 %
       
   417 % \rail@tmpa : temporary count
       
   418 % \rail@tmpb : temporary count
       
   419 % \rail@tmpc : temporary count
       
   420 %
       
   421 % \rail@put : put at (\rail@x,\rail@y)
       
   422 % \rail@vput : put vector at (\rail@x,\rail@y)
       
   423 %
       
   424 % \rail@eline : end line by drawing from \rail@ex to \rail@x
       
   425 %
       
   426 % \rail@vreline : end line by drawing a vector from \rail@x to \rail@ex
       
   427 %
       
   428 % \rail@vleline : end line by drawing a vector from \rail@ex to \rail@x
       
   429 %
       
   430 % \rail@sety{LEVEL} : set \rail@y to level LEVEL
       
   431 
       
   432 \newcount\rail@x
       
   433 \newcount\rail@y
       
   434 \newcount\rail@ex
       
   435 \newcount\rail@sx
       
   436 \newcount\rail@rx
       
   437 
       
   438 \newcount\rail@tmpa
       
   439 \newcount\rail@tmpb
       
   440 \newcount\rail@tmpc
       
   441 
       
   442 \def\rail@put{\put(\number\rail@x,\number\rail@y)}
       
   443 
       
   444 \def\rail@vput{\put(\number\rail@ex,\number\rail@y)}
       
   445 
       
   446 \def\rail@eline{
       
   447 \rail@tmpb=\rail@x
       
   448 \advance\rail@tmpb by -\rail@ex
       
   449 \rail@put{\line(-1,0){\number\rail@tmpb}}
       
   450 }
       
   451 
       
   452 \def\rail@vreline{
       
   453 \rail@tmpb=\rail@x
       
   454 \advance\rail@tmpb by -\rail@ex
       
   455 \rail@vput{\vector(1,0){\number\rail@tmpb}}
       
   456 }
       
   457 
       
   458 \def\rail@vleline{
       
   459 \rail@tmpb=\rail@x
       
   460 \advance\rail@tmpb by -\rail@ex
       
   461 \rail@put{\vector(-1,0){\number\rail@tmpb}}
       
   462 }
       
   463 
       
   464 \def\rail@sety#1{
       
   465 \rail@y=#1
       
   466 \multiply\rail@y by -\rail@boxsp
       
   467 \advance\rail@y by -\rail@boxht
       
   468 }
       
   469 
       
   470 % \rail@begin{HEIGHT}{NAME} : begin a railroad diagram of height HEIGHT
       
   471 %
       
   472 % \rail@end : end a railroad diagram
       
   473 %
       
   474 % \rail@expand{IDENT} : expand IDENT
       
   475 
       
   476 \def\rail@begin#1#2{
       
   477 \item
       
   478 \begin{minipage}[t]{\linewidth}
       
   479 \ifx\@empty#2\else
       
   480 {\rail@namefont \rail@expand{#2}}\\*[\railnamesep]
       
   481 \fi
       
   482 \unitlength=\railunit
       
   483 \rail@tmpa=#1
       
   484 \multiply\rail@tmpa by \rail@boxsp
       
   485 \begin{picture}(0,\number\rail@tmpa)(0,-\number\rail@tmpa)
       
   486 \rail@ex=0
       
   487 \rail@rx=0
       
   488 \rail@x=\rail@extra
       
   489 \rail@sx=\rail@x
       
   490 \rail@sety{0}
       
   491 }
       
   492 
       
   493 \def\rail@end{
       
   494 \advance\rail@x by \rail@extra
       
   495 \rail@eline
       
   496 \end{picture}
       
   497 \end{minipage}
       
   498 }
       
   499 
       
   500 \def\rail@vend{
       
   501 \advance\rail@x by \rail@extra
       
   502 \rail@vreline
       
   503 \end{picture}
       
   504 \end{minipage}
       
   505 }
       
   506 
       
   507 \def\rail@expand#1{\@ifundefined{rail@t@#1}{#1}{\csname rail@t@#1\endcsname}}
       
   508 
       
   509 % \rail@token{TEXT}[ANNOT] : format token TEXT with annotation
       
   510 % \rail@ltoken{TEXT}[ANNOT] : format token TEXT with annotation, arrow left
       
   511 % \rail@rtoken{TEXT}[ANNOT] : format token TEXT with annotation, arrow right
       
   512 %
       
   513 % \rail@ctoken{TEXT}[ANNOT] : format token TEXT centered with annotation
       
   514 % \rail@lctoken{TEXT}[ANNOT] : format token TEXT centered with annotation, arrow left
       
   515 % \rail@rctoken{TEXT}[ANNOT] : format token TEXT centered with annotation, arrow right
       
   516 %
       
   517 % \rail@nont{TEXT}[ANNOT] : format nonterminal TEXT with annotation
       
   518 % \rail@lnont{TEXT}[ANNOT] : format nonterminal TEXT with annotation, arrow left
       
   519 % \rail@rnont{TEXT}[ANNOT] : format nonterminal TEXT with annotation. arrow right
       
   520 %
       
   521 % \rail@cnont{TEXT}[ANNOT] : format nonterminal TEXT centered with annotation
       
   522 % \rail@lcnont{TEXT}[ANNOT] : format nonterminal TEXT centered with annotation,
       
   523 %                             arrow left
       
   524 % \rail@rcnont{TEXT}[ANNOT] : format nonterminal TEXT centered with annotation,
       
   525 %                             arrow right
       
   526 %
       
   527 % \rail@term{TEXT}[ANNOT] : format terminal TEXT with annotation
       
   528 % \rail@lterm{TEXT}[ANNOT] : format terminal TEXT with annotation, arrow left
       
   529 % \rail@rterm{TEXT}[ANNOT] : format terminal TEXT with annotation, arrow right
       
   530 %
       
   531 % \rail@cterm{TEXT}[ANNOT] : format terminal TEXT centered with annotation
       
   532 % \rail@lcterm{TEXT}[ANNOT] : format terminal TEXT centered with annotation, arrow left
       
   533 % \rail@rcterm{TEXT}[ANNOT] : format terminal TEXT centered with annotation,
       
   534 %                             arrow right
       
   535 %
       
   536 % \rail@annote[TEXT] : format TEXT as annotation
       
   537 
       
   538 \def\rail@token#1[#2]{
       
   539 \rail@setbox{%
       
   540 {\rail@termfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   541 }
       
   542 \rail@oval
       
   543 }
       
   544 
       
   545 \def\rail@ltoken#1[#2]{
       
   546 \rail@setbox{%
       
   547 {\rail@termfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   548 }
       
   549 \rail@vloval
       
   550 }
       
   551 
       
   552 \def\rail@rtoken#1[#2]{
       
   553 \rail@setbox{%
       
   554 {\rail@termfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   555 }
       
   556 \rail@vroval
       
   557 }
       
   558 
       
   559 \def\rail@ctoken#1[#2]{
       
   560 \rail@setbox{%
       
   561 {\rail@termfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   562 }
       
   563 \rail@coval
       
   564 }
       
   565 
       
   566 \def\rail@lctoken#1[#2]{
       
   567 \rail@setbox{%
       
   568 {\rail@termfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   569 }
       
   570 \rail@vlcoval
       
   571 }
       
   572 
       
   573 \def\rail@rctoken#1[#2]{
       
   574 \rail@setbox{%
       
   575 {\rail@termfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   576 }
       
   577 \rail@vrcoval
       
   578 }
       
   579 
       
   580 \def\rail@nont#1[#2]{
       
   581 \rail@setbox{%
       
   582 {\rail@nontfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   583 }
       
   584 \rail@frame
       
   585 }
       
   586 
       
   587 \def\rail@lnont#1[#2]{
       
   588 \rail@setbox{%
       
   589 {\rail@nontfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   590 }
       
   591 \rail@vlframe
       
   592 }
       
   593 
       
   594 \def\rail@rnont#1[#2]{
       
   595 \rail@setbox{%
       
   596 {\rail@nontfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   597 }
       
   598 \rail@vrframe
       
   599 }
       
   600 
       
   601 \def\rail@cnont#1[#2]{
       
   602 \rail@setbox{%
       
   603 {\rail@nontfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   604 }
       
   605 \rail@cframe
       
   606 }
       
   607 
       
   608 \def\rail@lcnont#1[#2]{
       
   609 \rail@setbox{%
       
   610 {\rail@nontfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   611 }
       
   612 \rail@vlcframe
       
   613 }
       
   614 
       
   615 \def\rail@rcnont#1[#2]{
       
   616 \rail@setbox{%
       
   617 {\rail@nontfont \rail@expand{#1}}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   618 }
       
   619 \rail@vrcframe
       
   620 }
       
   621 
       
   622 \def\rail@term#1[#2]{
       
   623 \rail@setbox{%
       
   624 {\rail@termfont #1}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   625 }
       
   626 \rail@oval
       
   627 }
       
   628 
       
   629 \def\rail@lterm#1[#2]{
       
   630 \rail@setbox{%
       
   631 {\rail@termfont #1}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   632 }
       
   633 \rail@vloval
       
   634 }
       
   635 
       
   636 \def\rail@rterm#1[#2]{
       
   637 \rail@setbox{%
       
   638 {\rail@termfont #1}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   639 }
       
   640 \rail@vroval
       
   641 }
       
   642 
       
   643 \def\rail@cterm#1[#2]{
       
   644 \rail@setbox{%
       
   645 {\rail@termfont #1}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   646 }
       
   647 \rail@coval
       
   648 }
       
   649 
       
   650 \def\rail@lcterm#1[#2]{
       
   651 \rail@setbox{%
       
   652 {\rail@termfont #1}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   653 }
       
   654 \rail@vlcoval
       
   655 }
       
   656 
       
   657 \def\rail@rcterm#1[#2]{
       
   658 \rail@setbox{%
       
   659 {\rail@termfont #1}\ifx\@empty#2\else\ {\rail@annofont #2}\fi
       
   660 }
       
   661 \rail@vrcoval
       
   662 }
       
   663 
       
   664 \def\rail@annote[#1]{
       
   665 \rail@setbox{\rail@annofont #1}
       
   666 \rail@text
       
   667 }
       
   668 
       
   669 % \rail@box : temporary box for \rail@oval and \rail@frame
       
   670 %
       
   671 % \rail@setbox{TEXT} : set \rail@box to TEXT, set \rail@tmpa to width
       
   672 %
       
   673 % \rail@oval : format \rail@box of width \rail@tmpa inside an oval
       
   674 % \rail@vloval : format \rail@box of width \rail@tmpa inside an oval, vector left
       
   675 % \rail@vroval : format \rail@box of width \rail@tmpa inside an oval, vector right
       
   676 %
       
   677 % \rail@coval : same as \rail@oval, but centered between \rail@x and
       
   678 %               \rail@mx
       
   679 % \rail@vlcoval : same as \rail@oval, but centered between \rail@x and
       
   680 %                 \rail@mx, vector left
       
   681 % \rail@vrcoval : same as \rail@oval, but centered between \rail@x and
       
   682 %                 \rail@mx, vector right
       
   683 %
       
   684 % \rail@frame : format \rail@box of width \rail@tmpa inside a frame
       
   685 % \rail@vlframe : format \rail@box of width \rail@tmpa inside a frame, vector left
       
   686 % \rail@vrframe : format \rail@box of width \rail@tmpa inside a frame, vector right
       
   687 %
       
   688 % \rail@cframe : same as \rail@frame, but centered between \rail@x and
       
   689 %                \rail@mx
       
   690 % \rail@vlcframe : same as \rail@frame, but centered between \rail@x and
       
   691 %                  \rail@mx, vector left
       
   692 % \rail@vrcframe : same as \rail@frame, but centered between \rail@x and
       
   693 %                  \rail@mx, vector right
       
   694 %
       
   695 % \rail@text : format \rail@box of width \rail@tmpa above the line
       
   696 
       
   697 \newbox\rail@box
       
   698 
       
   699 \def\rail@setbox#1{
       
   700 \setbox\rail@box\hbox{\strut#1}
       
   701 \rail@tmpa=\wd\rail@box
       
   702 \divide\rail@tmpa by \railunit
       
   703 }
       
   704 
       
   705 \def\rail@oval{
       
   706 \advance\rail@x by \rail@boxlf
       
   707 \rail@eline
       
   708 \advance\rail@tmpa by \rail@ovalsp
       
   709 \ifnum\rail@tmpa<\rail@boxht\rail@tmpa=\rail@boxht\fi
       
   710 \rail@tmpb=\rail@tmpa
       
   711 \divide\rail@tmpb by 2
       
   712 \advance\rail@y by -\rail@boxhht
       
   713 \rail@put{\makebox(\number\rail@tmpa,\number\rail@boxht){\box\rail@box}}
       
   714 \advance\rail@y by \rail@boxhht
       
   715 \advance\rail@x by \rail@tmpb
       
   716 \rail@put{\oval(\number\rail@tmpa,\number\rail@boxht)}
       
   717 \advance\rail@x by \rail@tmpb
       
   718 \rail@ex=\rail@x
       
   719 \advance\rail@x by \rail@boxrt
       
   720 }
       
   721 
       
   722 \def\rail@vloval{
       
   723 \advance\rail@x by \rail@boxlf
       
   724 \rail@eline
       
   725 \advance\rail@tmpa by \rail@ovalsp
       
   726 \ifnum\rail@tmpa<\rail@boxht\rail@tmpa=\rail@boxht\fi
       
   727 \rail@tmpb=\rail@tmpa
       
   728 \divide\rail@tmpb by 2
       
   729 \advance\rail@y by -\rail@boxhht
       
   730 \rail@put{\makebox(\number\rail@tmpa,\number\rail@boxht){\box\rail@box}}
       
   731 \advance\rail@y by \rail@boxhht
       
   732 \advance\rail@x by \rail@tmpb
       
   733 \rail@put{\oval(\number\rail@tmpa,\number\rail@boxht)}
       
   734 \advance\rail@x by \rail@tmpb
       
   735 \rail@ex=\rail@x
       
   736 \advance\rail@x by \rail@boxrt
       
   737 \rail@vleline
       
   738 }
       
   739 
       
   740 \def\rail@vroval{
       
   741 \advance\rail@x by \rail@boxlf
       
   742 \rail@vreline
       
   743 \advance\rail@tmpa by \rail@ovalsp
       
   744 \ifnum\rail@tmpa<\rail@boxht\rail@tmpa=\rail@boxht\fi
       
   745 \rail@tmpb=\rail@tmpa
       
   746 \divide\rail@tmpb by 2
       
   747 \advance\rail@y by -\rail@boxhht
       
   748 \rail@put{\makebox(\number\rail@tmpa,\number\rail@boxht){\box\rail@box}}
       
   749 \advance\rail@y by \rail@boxhht
       
   750 \advance\rail@x by \rail@tmpb
       
   751 \rail@put{\oval(\number\rail@tmpa,\number\rail@boxht)}
       
   752 \advance\rail@x by \rail@tmpb
       
   753 \rail@ex=\rail@x
       
   754 \advance\rail@x by \rail@boxrt
       
   755 }
       
   756 
       
   757 \def\rail@coval{
       
   758 \rail@tmpb=\rail@tmpa
       
   759 \advance\rail@tmpb by \rail@ovalsp
       
   760 \ifnum\rail@tmpb<\rail@boxht\rail@tmpb=\rail@boxht\fi
       
   761 \advance\rail@tmpb by \rail@boxlf
       
   762 \advance\rail@tmpb by \rail@boxrt
       
   763 \rail@tmpc=\rail@mx
       
   764 \advance\rail@tmpc by -\rail@x
       
   765 \advance\rail@tmpc by -\rail@tmpb
       
   766 \divide\rail@tmpc by 2
       
   767 \ifnum\rail@tmpc>0
       
   768 \advance\rail@x by \rail@tmpc
       
   769 \fi
       
   770 \rail@oval
       
   771 }
       
   772 
       
   773 \def\rail@vlcoval{
       
   774 \rail@tmpb=\rail@tmpa
       
   775 \advance\rail@tmpb by \rail@ovalsp
       
   776 \ifnum\rail@tmpb<\rail@boxht\rail@tmpb=\rail@boxht\fi
       
   777 \advance\rail@tmpb by \rail@boxlf
       
   778 \advance\rail@tmpb by \rail@boxrt
       
   779 \rail@tmpc=\rail@mx
       
   780 \advance\rail@tmpc by -\rail@x
       
   781 \advance\rail@tmpc by -\rail@tmpb
       
   782 \divide\rail@tmpc by 2
       
   783 \ifnum\rail@tmpc>0
       
   784 \advance\rail@x by \rail@tmpc
       
   785 \fi
       
   786 \rail@vloval
       
   787 }
       
   788 
       
   789 \def\rail@vrcoval{
       
   790 \rail@tmpb=\rail@tmpa
       
   791 \advance\rail@tmpb by \rail@ovalsp
       
   792 \ifnum\rail@tmpb<\rail@boxht\rail@tmpb=\rail@boxht\fi
       
   793 \advance\rail@tmpb by \rail@boxlf
       
   794 \advance\rail@tmpb by \rail@boxrt
       
   795 \rail@tmpc=\rail@mx
       
   796 \advance\rail@tmpc by -\rail@x
       
   797 \advance\rail@tmpc by -\rail@tmpb
       
   798 \divide\rail@tmpc by 2
       
   799 \ifnum\rail@tmpc>0
       
   800 \advance\rail@x by \rail@tmpc
       
   801 \fi
       
   802 \rail@vroval
       
   803 }
       
   804 
       
   805 \def\rail@frame{
       
   806 \advance\rail@x by \rail@boxlf
       
   807 \rail@eline
       
   808 \advance\rail@tmpa by \rail@framesp
       
   809 \ifnum\rail@tmpa<\rail@boxht\rail@tmpa=\rail@boxht\fi
       
   810 \advance\rail@y by -\rail@boxhht
       
   811 \rail@put{\framebox(\number\rail@tmpa,\number\rail@boxht){\box\rail@box}}
       
   812 \advance\rail@y by \rail@boxhht
       
   813 \advance\rail@x by \rail@tmpa
       
   814 \rail@ex=\rail@x
       
   815 \advance\rail@x by \rail@boxrt
       
   816 }
       
   817 
       
   818 \def\rail@vlframe{
       
   819 \advance\rail@x by \rail@boxlf
       
   820 \rail@eline
       
   821 \advance\rail@tmpa by \rail@framesp
       
   822 \ifnum\rail@tmpa<\rail@boxht\rail@tmpa=\rail@boxht\fi
       
   823 \advance\rail@y by -\rail@boxhht
       
   824 \rail@put{\framebox(\number\rail@tmpa,\number\rail@boxht){\box\rail@box}}
       
   825 \advance\rail@y by \rail@boxhht
       
   826 \advance\rail@x by \rail@tmpa
       
   827 \rail@ex=\rail@x
       
   828 \advance\rail@x by \rail@boxrt
       
   829 \rail@vleline
       
   830 }
       
   831 
       
   832 \def\rail@vrframe{
       
   833 \advance\rail@x by \rail@boxlf
       
   834 \rail@vreline
       
   835 \advance\rail@tmpa by \rail@framesp
       
   836 \ifnum\rail@tmpa<\rail@boxht\rail@tmpa=\rail@boxht\fi
       
   837 \advance\rail@y by -\rail@boxhht
       
   838 \rail@put{\framebox(\number\rail@tmpa,\number\rail@boxht){\box\rail@box}}
       
   839 \advance\rail@y by \rail@boxhht
       
   840 \advance\rail@x by \rail@tmpa
       
   841 \rail@ex=\rail@x
       
   842 \advance\rail@x by \rail@boxrt
       
   843 }
       
   844 
       
   845 \def\rail@cframe{
       
   846 \rail@tmpb=\rail@tmpa
       
   847 \advance\rail@tmpb by \rail@framesp
       
   848 \ifnum\rail@tmpb<\rail@boxht\rail@tmpb=\rail@boxht\fi
       
   849 \advance\rail@tmpb by \rail@boxlf
       
   850 \advance\rail@tmpb by \rail@boxrt
       
   851 \rail@tmpc=\rail@mx
       
   852 \advance\rail@tmpc by -\rail@x
       
   853 \advance\rail@tmpc by -\rail@tmpb
       
   854 \divide\rail@tmpc by 2
       
   855 \ifnum\rail@tmpc>0
       
   856 \advance\rail@x by \rail@tmpc
       
   857 \fi
       
   858 \rail@frame
       
   859 }
       
   860 
       
   861 \def\rail@vlcframe{
       
   862 \rail@tmpb=\rail@tmpa
       
   863 \advance\rail@tmpb by \rail@framesp
       
   864 \ifnum\rail@tmpb<\rail@boxht\rail@tmpb=\rail@boxht\fi
       
   865 \advance\rail@tmpb by \rail@boxlf
       
   866 \advance\rail@tmpb by \rail@boxrt
       
   867 \rail@tmpc=\rail@mx
       
   868 \advance\rail@tmpc by -\rail@x
       
   869 \advance\rail@tmpc by -\rail@tmpb
       
   870 \divide\rail@tmpc by 2
       
   871 \ifnum\rail@tmpc>0
       
   872 \advance\rail@x by \rail@tmpc
       
   873 \fi
       
   874 \rail@vlframe
       
   875 }
       
   876 
       
   877 \def\rail@vrcframe{
       
   878 \rail@tmpb=\rail@tmpa
       
   879 \advance\rail@tmpb by \rail@framesp
       
   880 \ifnum\rail@tmpb<\rail@boxht\rail@tmpb=\rail@boxht\fi
       
   881 \advance\rail@tmpb by \rail@boxlf
       
   882 \advance\rail@tmpb by \rail@boxrt
       
   883 \rail@tmpc=\rail@mx
       
   884 \advance\rail@tmpc by -\rail@x
       
   885 \advance\rail@tmpc by -\rail@tmpb
       
   886 \divide\rail@tmpc by 2
       
   887 \ifnum\rail@tmpc>0
       
   888 \advance\rail@x by \rail@tmpc
       
   889 \fi
       
   890 \rail@vrframe
       
   891 }
       
   892 
       
   893 \def\rail@text{
       
   894 \advance\rail@x by \rail@textlf
       
   895 \advance\rail@y by \rail@textup
       
   896 \rail@put{\box\rail@box}
       
   897 \advance\rail@y by -\rail@textup
       
   898 \advance\rail@x by \rail@tmpa
       
   899 \advance\rail@x by \rail@textrt
       
   900 }
       
   901 
       
   902 % alternatives
       
   903 %
       
   904 % \rail@jx \rail@jy : current join point
       
   905 %
       
   906 % \rail@gx \rail@gy \rail@gex \rail@grx : global versions of \rail@x etc,
       
   907 %                                         to pass values over group closings
       
   908 %
       
   909 % \rail@mx : maximum x so far
       
   910 %
       
   911 % \rail@sy : starting \rail@y for alternatives
       
   912 %
       
   913 % \rail@jput : put at (\rail@jx,\rail@jy)
       
   914 %
       
   915 % \rail@joval[PART] : put \oval[PART] with adjust
       
   916 
       
   917 \newcount\rail@jx
       
   918 \newcount\rail@jy
       
   919 
       
   920 \newcount\rail@gx
       
   921 \newcount\rail@gy
       
   922 \newcount\rail@gex
       
   923 \newcount\rail@grx
       
   924 
       
   925 \newcount\rail@sy
       
   926 \newcount\rail@mx
       
   927 
       
   928 \def\rail@jput{
       
   929 \put(\number\rail@jx,\number\rail@jy)
       
   930 }
       
   931 
       
   932 \def\rail@joval[#1]{
       
   933 \advance\rail@jx by \rail@joinadj
       
   934 \rail@jput{\oval(\number\rail@joinsz,\number\rail@joinsz)[#1]}
       
   935 \advance\rail@jx by -\rail@joinadj
       
   936 }
       
   937 
       
   938 % \rail@barsplit : incoming split for '|'
       
   939 %
       
   940 % \rail@plussplit : incoming split for '+'
       
   941 %
       
   942 
       
   943 \def\rail@barsplit{
       
   944 \advance\rail@jy by -\rail@joinhsz
       
   945 \rail@joval[tr]
       
   946 \advance\rail@jx by \rail@joinhsz
       
   947 }
       
   948 
       
   949 \def\rail@plussplit{
       
   950 \advance\rail@jy by -\rail@joinhsz
       
   951 \advance\rail@jx by \rail@joinsz
       
   952 \rail@joval[tl]
       
   953 \advance\rail@jx by -\rail@joinhsz
       
   954 }
       
   955 
       
   956 % \rail@alt{SPLIT} : start alternatives with incoming split SPLIT
       
   957 %
       
   958 
       
   959 \def\rail@alt#1{
       
   960 \rail@sy=\rail@y
       
   961 \rail@jx=\rail@x
       
   962 \rail@jy=\rail@y
       
   963 \advance\rail@x by \rail@joinsz
       
   964 \rail@mx=0
       
   965 \let\rail@list=\@empty
       
   966 \let\rail@comma=\@empty
       
   967 \let\rail@split=#1
       
   968 \begingroup
       
   969 \rail@sx=\rail@x
       
   970 \rail@rx=0
       
   971 }
       
   972 
       
   973 % \rail@nextalt{FIX}{Y} : start next alternative at vertical position Y
       
   974 %                         and fix-up FIX
       
   975 %
       
   976 
       
   977 \def\rail@nextalt#1#2{
       
   978 \global\rail@gx=\rail@x
       
   979 \global\rail@gy=\rail@y
       
   980 \global\rail@gex=\rail@ex
       
   981 \global\rail@grx=\rail@rx
       
   982 \endgroup
       
   983 #1
       
   984 \ifnum\rail@gx>\rail@mx\rail@mx=\rail@gx\fi
       
   985 \ifnum\rail@grx>\rail@mx\rail@mx=\rail@grx\fi
       
   986 \edef\rail@list{\rail@list\rail@comma\number\rail@gex:\number\rail@gy}
       
   987 \def\rail@comma{,}
       
   988 \rail@split
       
   989 \let\rail@split=\@empty
       
   990 \rail@sety{#2}
       
   991 \rail@tmpa=\rail@jy
       
   992 \advance\rail@tmpa by -\rail@y
       
   993 \advance\rail@tmpa by -\rail@joinhsz
       
   994 \rail@jput{\line(0,-1){\number\rail@tmpa}}
       
   995 \rail@jy=\rail@y
       
   996 \advance\rail@jy by \rail@joinhsz
       
   997 \advance\rail@jx by \rail@joinhsz
       
   998 \rail@joval[bl]
       
   999 \advance\rail@jx by -\rail@joinhsz
       
  1000 \rail@ex=\rail@x
       
  1001 \begingroup
       
  1002 \rail@sx=\rail@x
       
  1003 \rail@rx=0
       
  1004 }
       
  1005 
       
  1006 % \rail@barjoin : outgoing join for first '|' alternative
       
  1007 %
       
  1008 % \rail@plusjoin : outgoing join for first '+' alternative
       
  1009 %
       
  1010 % \rail@altjoin : join for subsequent alternative
       
  1011 %
       
  1012 
       
  1013 \def\rail@barjoin{
       
  1014 \ifnum\rail@y<\rail@sy
       
  1015 \global\rail@gex=\rail@jx
       
  1016 \else
       
  1017 \global\rail@gex=\rail@ex
       
  1018 \fi
       
  1019 \advance\rail@jy by -\rail@joinhsz
       
  1020 \rail@joval[tl]
       
  1021 \advance\rail@jx by -\rail@joinhsz
       
  1022 \ifnum\rail@y<\rail@sy
       
  1023 \rail@altjoin
       
  1024 \fi
       
  1025 }
       
  1026 
       
  1027 \def\rail@plusjoin{
       
  1028 \global\rail@gex=\rail@ex
       
  1029 \advance\rail@jy by -\rail@joinhsz
       
  1030 \advance\rail@jx by -\rail@joinsz
       
  1031 \rail@joval[tr]
       
  1032 \advance\rail@jx by \rail@joinhsz
       
  1033 }
       
  1034 
       
  1035 \def\rail@altjoin{
       
  1036 \rail@eline
       
  1037 \rail@tmpa=\rail@jy
       
  1038 \advance\rail@tmpa by -\rail@y
       
  1039 \advance\rail@tmpa by -\rail@joinhsz
       
  1040 \rail@jput{\line(0,-1){\number\rail@tmpa}}
       
  1041 \rail@jy=\rail@y
       
  1042 \advance\rail@jy by \rail@joinhsz
       
  1043 \advance\rail@jx by -\rail@joinhsz
       
  1044 \rail@joval[br]
       
  1045 \advance\rail@jx by \rail@joinhsz
       
  1046 }
       
  1047 
       
  1048 % \rail@eltsplit EX:Y; : split EX:Y into \rail@ex \rail@y
       
  1049 %
       
  1050 % \rail@endalt{JOIN} : end alternatives with outgoing join JOIN
       
  1051 
       
  1052 \def\rail@eltsplit#1:#2;{\rail@ex=#1\rail@y=#2}
       
  1053 
       
  1054 \def\rail@endalt#1{
       
  1055 \global\rail@gx=\rail@x
       
  1056 \global\rail@gy=\rail@y
       
  1057 \global\rail@gex=\rail@ex
       
  1058 \global\rail@grx=\rail@rx
       
  1059 \endgroup
       
  1060 \ifnum\rail@gx>\rail@mx\rail@mx=\rail@gx\fi
       
  1061 \ifnum\rail@grx>\rail@mx\rail@mx=\rail@grx\fi
       
  1062 \edef\rail@list{\rail@list\rail@comma\number\rail@gex:\number\rail@gy}
       
  1063 \rail@x=\rail@mx
       
  1064 \rail@jx=\rail@x
       
  1065 \rail@jy=\rail@sy
       
  1066 \advance\rail@jx by \rail@joinsz
       
  1067 \let\rail@join=#1
       
  1068 \@for\rail@elt:=\rail@list\do{
       
  1069 \expandafter\rail@eltsplit\rail@elt;
       
  1070 \rail@join
       
  1071 \let\rail@join=\rail@altjoin
       
  1072 }
       
  1073 \rail@x=\rail@mx
       
  1074 \rail@y=\rail@sy
       
  1075 \rail@ex=\rail@gex
       
  1076 \advance\rail@x by \rail@joinsz
       
  1077 }
       
  1078 
       
  1079 % \rail@bar : start '|' alternatives
       
  1080 %
       
  1081 % \rail@nextbar : next '|' alternative
       
  1082 %
       
  1083 % \rail@endbar : end '|' alternatives
       
  1084 %
       
  1085 
       
  1086 \def\rail@bar{
       
  1087 \rail@alt\rail@barsplit
       
  1088 }
       
  1089 
       
  1090 \def\rail@nextbar{
       
  1091 \rail@nextalt\relax
       
  1092 }
       
  1093 
       
  1094 \def\rail@endbar{
       
  1095 \rail@endalt\rail@barjoin
       
  1096 }
       
  1097 
       
  1098 % \rail@plus : start '+' alternatives
       
  1099 %
       
  1100 % \rail@nextplus: next '+' alternative
       
  1101 %
       
  1102 % \rail@endplus : end '+' alternatives
       
  1103 %
       
  1104 
       
  1105 \def\rail@plus{
       
  1106 \rail@alt\rail@plussplit
       
  1107 }
       
  1108 
       
  1109 \def\rail@nextplus{
       
  1110 \rail@nextalt\rail@fixplus
       
  1111 }
       
  1112 
       
  1113 \def\rail@fixplus{
       
  1114 \ifnum\rail@gy<\rail@sy
       
  1115 \begingroup
       
  1116 \rail@x=\rail@gx
       
  1117 \rail@y=\rail@gy
       
  1118 \rail@ex=\rail@gex
       
  1119 \rail@rx=\rail@grx
       
  1120 \ifnum\rail@x<\rail@rx
       
  1121 \rail@x=\rail@rx
       
  1122 \fi
       
  1123 \rail@eline
       
  1124 \rail@jx=\rail@x
       
  1125 \rail@jy=\rail@y
       
  1126 \advance\rail@jy by \rail@joinhsz
       
  1127 \rail@joval[br]
       
  1128 \advance\rail@jx by \rail@joinhsz
       
  1129 \rail@tmpa=\rail@sy
       
  1130 \advance\rail@tmpa by -\rail@joinhsz
       
  1131 \advance\rail@tmpa by -\rail@jy
       
  1132 \rail@jput{\line(0,1){\number\rail@tmpa}}
       
  1133 \rail@jy=\rail@sy
       
  1134 \advance\rail@jy by -\rail@joinhsz
       
  1135 \advance\rail@jx by \rail@joinhsz
       
  1136 \rail@joval[tl]
       
  1137 \advance\rail@jy by \rail@joinhsz
       
  1138 \global\rail@gx=\rail@jx
       
  1139 \global\rail@gy=\rail@jy
       
  1140 \global\rail@gex=\rail@gx
       
  1141 \global\rail@grx=\rail@rx
       
  1142 \endgroup
       
  1143 \fi
       
  1144 }
       
  1145 
       
  1146 \def\rail@endplus{
       
  1147 \rail@endalt\rail@plusjoin
       
  1148 }
       
  1149 
       
  1150 % \rail@cr{Y} : carriage return to vertical position Y
       
  1151 
       
  1152 \def\rail@cr#1{
       
  1153 \rail@tmpa=\rail@sx
       
  1154 \advance\rail@tmpa by \rail@joinsz
       
  1155 \ifnum\rail@x<\rail@tmpa\rail@x=\rail@tmpa\fi
       
  1156 \rail@eline
       
  1157 \rail@jx=\rail@x
       
  1158 \rail@jy=\rail@y
       
  1159 \advance\rail@x by \rail@joinsz
       
  1160 \ifnum\rail@x>\rail@rx\rail@rx=\rail@x\fi
       
  1161 \advance\rail@jy by -\rail@joinhsz
       
  1162 \rail@joval[tr]
       
  1163 \advance\rail@jx by \rail@joinhsz
       
  1164 \rail@sety{#1}
       
  1165 \rail@tmpa=\rail@jy
       
  1166 \advance\rail@tmpa by -\rail@y
       
  1167 \advance\rail@tmpa by -\rail@boxsp
       
  1168 \advance\rail@tmpa by -\rail@joinhsz
       
  1169 \rail@jput{\line(0,-1){\number\rail@tmpa}}
       
  1170 \rail@jy=\rail@y
       
  1171 \advance\rail@jy by \rail@boxsp
       
  1172 \advance\rail@jy by \rail@joinhsz
       
  1173 \advance\rail@jx by -\rail@joinhsz
       
  1174 \rail@joval[br]
       
  1175 \advance\rail@jy by -\rail@joinhsz
       
  1176 \rail@tmpa=\rail@jx
       
  1177 \advance\rail@tmpa by -\rail@sx
       
  1178 \advance\rail@tmpa by -\rail@joinhsz
       
  1179 \rail@jput{\line(-1,0){\number\rail@tmpa}}
       
  1180 \rail@jx=\rail@sx
       
  1181 \advance\rail@jx by \rail@joinhsz
       
  1182 \advance\rail@jy by -\rail@joinhsz
       
  1183 \rail@joval[tl]
       
  1184 \advance\rail@jx by -\rail@joinhsz
       
  1185 \rail@tmpa=\rail@boxsp
       
  1186 \advance\rail@tmpa by -\rail@joinsz
       
  1187 \rail@jput{\line(0,-1){\number\rail@tmpa}}
       
  1188 \advance\rail@jy by -\rail@tmpa
       
  1189 \advance\rail@jx by \rail@joinhsz
       
  1190 \rail@joval[bl]
       
  1191 \rail@x=\rail@jx
       
  1192 \rail@ex=\rail@x
       
  1193 }