manpagez: man pages & more
info groff
Home | html | info | man

File: groff.info,  Node: Diversions,  Next: Punning Names,  Prev: Traps,  Up: GNU troff Reference

5.29 Diversions
===============

In 'roff' systems it is possible to format text as if for output, but
instead of writing it immediately, one can "divert" the formatted text
into a named storage area.  It is retrieved later by specifying its name
after a control character.  The same name space is used for such
diversions as for strings and macros; see *note Identifiers::.  Such
text is sometimes said to be "stored in a macro", but this coinage
obscures the important distinction between macros and strings on one
hand and diversions on the other; the former store _unformatted_ input
text, and the latter capture _formatted_ output.  Diversions also do not
interpret arguments.  Applications of diversions include "keeps"
(preventing a page break from occurring at an inconvenient place by
forcing a set of output lines to be set as a group), footnotes, tables
of contents, and indices.  For orthogonality it is said that GNU 'troff'
is in the "top-level diversion" if no diversion is active (that is,
formatted output is being "diverted" immediately to the output device).

   Dereferencing an undefined diversion will create an empty one of that
name and cause a warning in category 'mac' to be emitted.  *Note
Warnings::, for information about the enablement and suppression of
warnings.  A diversion does not exist for the purpose of testing with
the 'd' conditional operator until its initial definition ends (*note
Operators in Conditionals::).  The following requests are used to create
and alter diversions.

 -- Request: .di [name]
 -- Request: .da [name]
     Start collecting formatted output in a diversion called NAME.  The
     'da' request appends to a diversion called NAME, creating it if
     necessary.  If NAME already exists as an alias, the target of the
     alias is replaced or appended to; recall *note Strings::.  The
     pending output line is diverted as well.  Switching to another
     environment (with the 'ev' request) before invoking 'di' or 'da'
     avoids including any pending output line in the diversion; see
     *note Environments::.

     Invoking 'di' or 'da' without an argument stops diverting output to
     the diversion named by the most recent corresponding request.  If
     'di' or 'da' is called without an argument when there is no current
     diversion, a warning in category 'di' is produced.  *Note
     Warnings::, for information about the enablement and suppression of
     warnings.

          Before the diversion.
          .di yyy
          In the diversion.
          .br
          .di
          After the diversion.
          .br
              => After the diversion.
          .yyy
              => Before the diversion.  In the diversion.

   GNU 'troff' supports "box" requests to exclude a partially collected
line from a diversion, as this is often desirable.

 -- Request: .box [name]
 -- Request: .boxa [name]
     Divert (or append) output to NAME, similarly to the 'di' and 'da'
     requests, respectively.  Any pending output line is _not_ included
     in the diversion.  Without an argument, stop diverting output; any
     pending output line inside the diversion is discarded.

          Before the box.
          .box xxx
          In the box.
          .br
          Hidden treasure.
          .box
          After the box.
          .br
              => Before the box.  After the box.
          .xxx
              => In the box.

   Apart from pending output line inclusion and the request names that
populate them, boxes are handled exactly as diversions are.  All of the
following 'groff' language elements can be used with them
interchangeably.

 -- Register: \n[.z]
 -- Register: \n[.d]
     Diversions may be nested.  The read-only string-valued register
     '.z' contains the name of the current diversion.  The read-only
     register '.d' contains the current vertical place in the diversion.
     If the input text is not being diverted, '.d' reports the same
     location as the register 'nl'.

 -- Register: \n[.h]
     The read-only register '.h' stores the "high-water mark" on the
     current page or in the current diversion.  It corresponds to the
     text baseline of the lowest line on the page.(1)  (*note
     Diversions-Footnote-1::)

          .tm .h==\n[.h], nl==\n[nl]
              => .h==0, nl==-1
          This is a test.
          .br
          .sp 2
          .tm .h==\n[.h], nl==\n[nl]
              => .h==40, nl==120

     As implied by the example, vertical motion does not produce text
     baselines and thus does not increase the value interpolated by
     '\n[.h]'.

 -- Register: \n[dn]
 -- Register: \n[dl]
     After completing a diversion, the writable registers 'dn' and 'dl'
     contain its vertical and horizontal sizes.  Only the lines just
     processed are counted: for the computation of 'dn' and 'dl', the
     requests 'da' and 'boxa' are handled as if 'di' and 'box' had been
     used, respectively--lines that have been already stored in the
     diversion (box) are not taken into account.

          .\" Center text both horizontally and vertically.
          .\" Macro .(c starts centering mode; .)c terminates it.
          .
          .\" Disable the escape character with .eo so that we
          .\" don't have to double backslashes on the "\n"s.
          .eo
          .de (c
          .  br
          .  ev (c
          .  evc 0
          .  in 0
          .  nf
          .  di @c
          ..
          .de )c
          .  br
          .  ev
          .  di
          .  nr @s (((\n[.t]u - \n[dn]u) / 2u) - 1v)
          .  sp \n[@s]u
          .  ce 1000
          .  @c
          .  ce 0
          .  sp \n[@s]u
          .  br
          .  fi
          .  rr @s
          .  rm @c
          ..
          .ec

 -- Escape sequence: \!anything
 -- Escape sequence: \?anything\?
     "Transparently" embed ANYTHING into the current diversion,
     preventing requests, macro calls, and escape sequences from being
     interpreted when read into a diversion.  This is useful for
     preventing them from taking effect until the diverted text is
     actually output.  The '\!' escape sequence transparently embeds
     input up to and including the end of the line.  The '\?' escape
     sequence transparently embeds input until its own next occurrence.

     ANYTHING may not contain newlines; use '\!' by itself to embed
     newlines in a diversion.  The escape sequence '\?' is also
     recognized in copy mode and turned into a single internal code; it
     is this code that terminates ANYTHING.  Thus the following example
     prints 4.

          .nr x 1
          .nf
          .di d
          \?\\?\\\\?\\\\\\\\nx\\\\?\\?\?
          .di
          .nr x 2
          .di e
          .d
          .di
          .nr x 3
          .di f
          .e
          .di
          .nr x 4
          .f

     Both escape sequences read the data in copy mode.

     If '\!' is used in the top-level diversion, its argument is
     directly embedded into GNU 'troff''s intermediate output.  This can
     be used, for example, to control a postprocessor that processes the
     data before it is sent to an output driver.

     The '\?' escape used in the top-level diversion produces no output
     at all; its argument is simply ignored.

 -- Request: .output contents
     Emit CONTENTS directly to GNU 'troff''s intermediate output
     (subject to copy mode interpretation); this is similar to '\!' used
     at the top level.  An initial neutral double quote in CONTENTS is
     stripped to allow embedding of leading spaces.

     This request can't be used before the first page has started--if
     you get an error, simply insert '.br' before the 'output' request.

     Use with caution!  It is normally only needed for mark-up used by a
     postprocessor that does something with the output before sending it
     to the output device, filtering out CONTENTS again.

 -- Request: .asciify div
     "Unformat" the diversion DIV in a way such that Unicode basic Latin
     (ASCII) characters, characters translated with the 'trin' request,
     space characters, and some escape sequences, that were formatted
     and diverted into DIV are treated like ordinary input characters
     when DIV is reread.  Doing so can be useful in conjunction with the
     'writem' request.  'asciify' can be also used for gross hacks; for
     example, the following sets register 'n' to 1.

          .tr @.
          .di x
          @nr n 1
          .br
          .di
          .tr @@
          .asciify x
          .x

     'asciify' cannot return all items in a diversion to their source
     equivalent: nodes such as those produced by the '\N' escape
     sequence will remain nodes, so the result cannot be guaranteed to
     be a pure string.  *Note Copy Mode::.  Glyph parameters such as the
     type face and size are not preserved; use 'unformat' to achieve
     that.

 -- Request: .unformat div
     Like 'asciify', unformat the diversion DIV.  However, 'unformat'
     handles only tabs and spaces between words, the latter usually
     arising from spaces or newlines in the input.  Tabs are treated as
     input tokens, and spaces become adjustable again.  The vertical
     sizes of lines are not preserved, but glyph information (font, type
     size, space width, and so on) is retained.

© manpagez.com 2000-2024
Individual documents may contain additional copyright information.