doc-src/underscore.sty
 changeset 26862 a79d7d5f1d06
equal inserted replaced
26861:e6fe036ec21d 26862:a79d7d5f1d06

     1 % underscore.sty     21-Sep-2005   Donald Arseneau   asnd@triumf.ca

     2 % Make the "_" character print as "\textunderscore" in text.

     3 % Copyright 1998,2001,2005,2006 Donald Arseneau;

     4 % License: LPPL version 1.2 or later.

     5 % Instructions follow after the definitions.

     6

     7 \ProvidesPackage{underscore}[2006/09/13]

     8

     9 \begingroup

    10  \catcode\_=\active
       
    11  \gdef _{% \relax % No relax gives a small vulnerability in alignments
       
    12    \ifx\if@safe@actives\iftrue % must be outermost test!
       
    13       \string_%
       
    14    \else
       
    15       \ifx\protect\@typeset@protect
       
    16          \ifmmode \sb \else \BreakableUnderscore \fi
       
    17       \else
       
    18          \ifx\protect\@unexpandable@protect \noexpand_%
       
    19          \else \protect_%
       
    20       \fi\fi
       
    21     \fi}
       
    22   \global\let\ActiveUnderscore=_
       
    23   \gdef\normalUnderscoreDef{\let_\ActiveUnderscore}
       
    24 \endgroup
       
    25 
       
    26 % At begin: set catcode; fix \long \ttdefault so I can use it in comparisons; 
       
    27 % reapply definition of active _ in output routine (\@firstofone to strip
       
    28 % away braces, so avoiding deeper nesting).
       
    29 \AtBeginDocument{%
       
    30   {\immediate\write\@auxout{\catcode\number\string\_ \string\active}}%

    31   \catcode\string\_\string=\active
       
    32   \edef\ttdefault{\ttdefault}%
       
    33   \output=\expandafter\expandafter\expandafter
       
    34      {\expandafter\expandafter\expandafter\normalUnderscoreDef
       
    35       \expandafter\@firstofone\the\output}%
       
    36 }
       
    37 
       
    38 \newcommand{\BreakableUnderscore}{\leavevmode\nobreak\hskip\z@skip
       
    39  \ifx\f@family\ttdefault \string_\else \textunderscore\fi
       
    40  \usc@dischyph\nobreak\hskip\z@skip}
       
    41 
       
    42 \DeclareRobustCommand{\_}{%
       
    43   \ifmmode \nfss@text{\textunderscore}\else \BreakableUnderscore \fi}
       
    44 
       
    45 
       
    46 \let\usc@dischyph\@dischyph
       
    47 \DeclareOption{nohyphen}{\def\usc@dischyph{\discretionary{}{}{}}}
       
    48 \DeclareOption{strings}{\catcode\_=\active}

    49

    50 \ProcessOptions

    51 \ifnum\catcode\_=\active\else \endinput \fi
       
    52 
       
    53 %%%%%%%%   Redefine commands that use character strings   %%%%%%%%
       
    54 
       
    55 \@ifundefined{UnderscoreCommands}{\let\UnderscoreCommands\@empty}{}
       
    56 \expandafter\def\expandafter\UnderscoreCommands\expandafter{%
       
    57   \UnderscoreCommands
       
    58   \do\include \do\includeonly
       
    59   \do\@input \do\@iinput \do\InputIfFileExists
       
    60   \do\ref \do\pageref \do\newlabel
       
    61   \do\bibitem \do\@bibitem \do\cite \do\nocite \do\bibcite
       
    62   \do\Ginclude@graphics \do\@setckpt
       
    63 }
       
    64 
       
    65 % Macro to redefine a macro to pre-process its string argument
       
    66 % with \protect -> \string.
       
    67 \def\do#1{% Avoid double processing if user includes command twice!
       
    68  \@ifundefined{US\string_\expandafter\@gobble\string#1}{%
       
    69    \edef\@tempb{\meaning#1}% Check if macro is just a protection shell...
       
    70    \def\@tempc{\protect}%
       
    71    \edef\@tempc{\meaning\@tempc\string#1\space\space}%
       
    72    \ifx\@tempb\@tempc % just a shell: hook into the protected inner command
       
    73      \expandafter\do
       
    74        \csname \expandafter\@gobble\string#1 \expandafter\endcsname
       
    75    \else % Check if macro takes an optional argument
       
    76      \def\@tempc{\@ifnextchar[}%
       
    77      \edef\@tempa{\def\noexpand\@tempa####1\meaning\@tempc}%
       
    78      \@tempa##2##3\@tempa{##2\relax}%
       
    79      \edef\@tempb{\meaning#1\meaning\@tempc}%
       
    80      \edef\@tempc{\noexpand\@tempd \csname
       
    81         US\string_\expandafter\@gobble\string#1\endcsname}%
       
    82      \if \expandafter\@tempa\@tempb \relax 12\@tempa % then no optional arg
       
    83        \@tempc #1\US@prot
       
    84      \else  % There is optional arg
       
    85        \@tempc #1\US@protopt
       
    86      \fi
       
    87    \fi
       
    88  }{}}
       
    89 
       
    90 \def\@tempd#1#2#3{\let#1#2\def#2{#3#1}}
       
    91 
       
    92 \def\US@prot#1#2{\let\@@protect\protect \let\protect\string
       
    93   \edef\US@temp##1{##1{#2}}\restore@protect\US@temp#1}
       
    94 \def\US@protopt#1{\@ifnextchar[{\US@protarg#1}{\US@prot#1}}
       
    95 \def\US@protarg #1[#2]{\US@prot{{#1[#2]}}}
       
    96 
       
    97 \UnderscoreCommands
       
    98 \let\do\relax \let\@tempd\relax  % un-do
       
    99 
       
   100 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
       
   101 
       
   102 \endinput
       
   103 
       
   104 underscore.sty    13-Sep-2006  Donald Arseneau
       
   105 
       
   106 Features:
       
   107 ~~~~~~~~~
       
   108 The "\_" command (which normally prints an underscore character or
       
   109 facsimile) is altered so that the hyphenation of constituent words
       
   110 is not affected, and hyphenation is permitted after the underscore.
       
   111 For example, "compound\_fracture" hyphenates as com- pound\_- frac- ture.
       
   112 If you prefer the underscore to break without a hyphen (but still with 
       
   113 the same rules for explicit hyphen-breaks) then use the [nohyphen]
       
   114 package option.
       
   115 
       
   116 A simple "_" acts just like "\_" in text mode, but makes a subscript
       
   117 in math mode: activation_energy $E_a$
       
   118 
       
   119 Both forms use an underscore character if the font encoding contains
       
   120 one (e.g., "\usepackage[T1]{fontenc}" or typewriter fonts in any encoding),
       
   121 but they use a rule if there is no proper character.
       
   122 
       
   123 Deficiencies:
       
   124 ~~~~~~~~~~~~~
       
   125 The skips and penalties ruin any kerning with the underscore character
       
   126 (when a character is used).  However, there doesn't seem to be much, if
       
   127 any, such kerning in the ec fonts, and there is never any kerning with
       
   128 a rule.
       
   129 
       
   130 You must avoid "_" in file names and in cite or ref tags, or you must use 
       
   131 the babel package, with its active-character controls, or you must give 
       
   132 the [strings] option, which attempts to redefine several commands (and 
       
   133 may not work perfectly).  Even without the [strings] option or babel, you 
       
   134 can use occasional underscores like: "\include{file\string_name}".
       
   135 
       
   136 Option: [strings]
       
   137 ~~~~~~~~~~~~~~~~~
       
   138 The default operation is quite simple and needs no customization; but
       
   139 you must avoid using "_" in any place where LaTeX uses an argument as
       
   140 a string of characters for some control function or as a name.  These
       
   141 include the tags for "\cite" and "\ref", file names for "\input", 
       
   142 "\include", and "\includegraphics", environment names, counter names,
       
   143 and placement parameters (like "[t]").  The problem with these contexts
       
   144 is that they are moving arguments' but LaTeX does not switch on' the
       
   145 "\protect" mechanism for them.
       
   146 
       
   147 If you need to use the underscore character in these places, the package
       
   148 option [strings] is provided to redefine commands that take such a string
       
   149 argument so that protection is applied (with "\protect" being "\string").
       
   150 The list of commands is given in "\UnderscoreCommands", with "\do" before
       
   151 each; plus several others covering "\input", "\includegraphics, "\cite", 
       
   152 "\ref", and their variants.  Not included are many commands regarding font 
       
   153 names, everything with counter names, environment names, page styles, and 
       
   154 versions of "\ref" and "\cite" defined by external packages (e.g., "\vref" 
       
   155 and "\citeyear").
       
   156 
       
   157 You can add to the list of supported commands by defining "\UnderscoreCommands"
       
   158 before loading this package; e.g.
       
   159 
       
   160    \usepackage{chicago}
       
   161    \newcommand{\UnderscoreCommands}{%   (\cite already done)
       
   162      \do\citeNP \do\citeA \do\citeANP \do\citeN \do\shortcite
       
   163      \do\shortciteNP \do\shortciteA \do\shortciteANP \do\shortciteN
       
   164      \do\citeyear \do\citeyearNP
       
   165    }
       
   166    \usepackage[strings]{underscore}
       
   167 
       
   168 Not all commands can be supported this way!  Only commands that take a
       
   169 string argument *first* can be protected.  One optional argument before
       
   170 the string argument is also permitted, as exemplified by "\cite": both
       
   171 "\cite{tags}" and "\cite[text]{tags}" are allowed.  A command like
       
   172 "\@addtoreset" which takes two counter names as arguments could not
       
   173 be protected by listing it in "\UnderscoreCommands".
       
   174 
       
   175 *When you use the [strings] option, you must load this package
       
   176 last* (or nearly last).
       
   177 
       
   178 There are two reasons: 1) The redefinitions done for protection must come
       
   179 after other packages define their customized versions of those commands.
       
   180 2) The [strings] option requires the "_" character to be activated immediately
       
   181 in order for the cite and ref tags to be read properly from the .aux file
       
   182 as plain strings, and this catcode setting might disrupt other packages.
       
   183 
       
   184 The babel package implements a protection mechanism for many commands,
       
   185 and will be a complete fix for most documents without the [strings] option.
       
   186 Many add-on packages are compatible with babel, so they will get the
       
   187 strings protection also.  However, there are several commands that are 
       
   188 not covered by babel, but can easily be supported by the [strings] and 
       
   189 "\UnderscoreCommands" mechanism.  Beware that using both [strings] and
       
   190 babel might lead to conflicts, but none are seen yet (load babel last).
       
   191 
       
   192 Implementation Notes:
       
   193 ~~~~~~~~~~~~~~~~~~~~~
       
   194 The first setting of "_" to be an active character is performed in a local
       
   195 group so as to not interfere with other packages.  The catcode setting
       
   196 is repeated with "\AtBeginDocument" so the definition is in effect for the
       
   197 text.  However, the catcode setting is repeated immediately when the
       
   198 [strings] option is detected.
       
   199 
       
   200 The definition of the active "_" is essentially:
       
   201 
       
   202        \ifmmode \sb \else \BreakableUnderscore \fi
       
   203 
       
   204 where "\sb" retains the normal subscript meaning of "_" and where
       
   205 "\BreakableUnderscore" is essentially "\_".  The rest of the definition
       
   206 handles the "\protect"ion without causing "\relax" to be inserted before
       
   207 the character.
       
   208 
       
   209 "\BreakableUnderscore" uses "\nobreak\hskip\z@skip" to separate the
       
   210 underscore from surrounding words, thus allowing TeX to hyphenate them,
       
   211 but preventing free breaks around the underscore. Next, it checks the
       
   212 current font family, and uses the underscore character from tt fonts or
       
   213 otherwise "\textunderscore" (which is a character or rule depending on
       
   214 the font encoding).  After the underscore, it inserts a discretionary
       
   215 hyphenation point as "\usc@dischyph", which is usually just "\-"
       
   216 except that it still works in the tabbing environment, although it
       
   217 will give "\discretionary{}{}{}" under the [nohyphen] option.  After
       
   218 that, another piece of non-breaking interword glue is inserted. 
       
   219 Ordinarily, the comparison "\ifx\f@family\ttdefault" will always fail 
       
   220 because "\ttdefault" is long' whereas "\f@family" is not (boooo hisss),

   221 but "\ttdefault" is redefined to be non-long by "\AtBeginDocument".

   222

   223 The "\_" command is then defined to use "\BreakableUnderscore".

   224

   225 If the [strings] option is not given, then that is all!

   226

   227 Under the [strings] option, the list of special commands is processed to:

   228

   229  - retain the original command as "\US_"*command* (e.g., "\US_ref")

   230  - redefine the command as "\US@prot\US_command" for ordinary commands

   231    ("\US@prot\US_ref") or as "\US@protopt\US_command" when an optional

   232    argument is possible (e.g., "\US@protopt\US_bibitem").

   233  - self-protecting commands ("\cite") retain their self-protection.

   234

   235 Diagnosing the state of the pre-existing command is done by painful

   236 contortions involving "\meaning".

   237

   238 "\US@prot" and "\US@protopt" read the argument, process it with

   239 "\protect" enabled, then invoke the saved "\US_command".

   240

   241 Modifications:

   242 ~~~~~~~~~~~~~~

   243 13-Sep-2006  Reassert my definition in the output routine (listings).

   244 21-Sep-2005  \includegraphics safe.

   245 12-Oct-2001  Babel (safe@actives) compatibility and [nohyphen] option.

   246

   247 Test file integrity:  ASCII 32-57, 58-126:  !"#\$%&'()*+,-./0123456789

   248 :;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_abcdefghijklmnopqrstuvwxyz{|}~`