% \iffalse %% %% File: chemcompounds.dtx Copyright (C) 2005-2007 Stephan Schenk %% $Id: chemcompounds.dtx,v 1.8 2006/12/01 15:21:58 schenk Exp $ %% %% Stephan Schenk (mail@schenk-stephan.de) %% % This program may be distributed and/or modified under the % conditions of the LaTeX Project Public License, either version 1.3 % of this license or (at your option) any later version. % The latest version of this license is in % http://www.latex-project.org/lppl.txt % % This package consists of the files chemcompounds.dtx and chemcompounds.ins % %% %% To produce the documentation, do the following: %% %% latex chemcompounds.dtx %% latex chemcompounds.dtx %% makeindex -s gglo.ist -o chemcompounds.gls chemcompounds.glo %% latex chemcompounds.dtx %% %<*driver> \ProvidesFile{chemcompounds.dtx} % %\NeedsTeXFormat{LaTeX2e} %\ProvidesPackage{chemcompounds} %<*package> [2006/12/01 v1.1.3 Dictionary for compound numbering] % % %<*driver> \documentclass{ltxdoc} \GetFileInfo{chemcompounds.dtx} \RecordChanges \begin{document} \DocInput{\filename} \PrintChanges \end{document} % % \fi % % \CheckSum{198} % % \CharacterTable % {Upper-case \A\B\C\D\E\F\G\H\I\J\K\L\M\N\O\P\Q\R\S\T\U\V\W\X\Y\Z % Lower-case \a\b\c\d\e\f\g\h\i\j\k\l\m\n\o\p\q\r\s\t\u\v\w\x\y\z % Digits \0\1\2\3\4\5\6\7\8\9 % Exclamation \! Double quote \" Hash (number) \# % Dollar \$ Percent \% Ampersand \& % Acute accent \' Left paren \( Right paren \) % Asterisk \* Plus \+ Comma \, % Minus \- Point \. Solidus \/ % Colon \: Semicolon \; Less than \< % Equals \= Greater than \> Question mark \? % Commercial at \@ Left bracket \[ Backslash \\ % Right bracket \] Circumflex \^ Underscore \_ % Grave accent \` Left brace \{ Vertical bar \| % Right brace \} Tilde \~} % % % % \changes{1.1.3}{2006/12/01}{Updated documentation.} % \changes{1.1.2}{2005/10/24}{Posted on CTAN on 2005/10/24.} % \changes{1.0.0}{2005/07/21}{First version posted on CTAN.} % % \title{The \textsf{chemcompounds} package\thanks{This file describes % version \fileversion\ and has been last revised \filedate.}} % \author{Stephan Schenk\\mail (at) schenk-stephan.de} % \maketitle % % \setcounter{tocdepth}{1} % % \begin{abstract} % The \texttt{\filename} package allows for a simple consecutive numbering of % chemical compounds. Optionally, it is possible to supply a custom name for % each compound. By default the compounds are numbered following the order of % their appearance in the text. % \end{abstract} % % \tableofcontents % % \section{Introduction} % % In chemical publications it is often necessary to consecutively number every % compound mentioned in the text. Although this can be simply accomplished by % manually inserting the corresponding numbers into the text, it is generally % much more tedious work since the numbering scheme tends to change several % times during the evolvement of the manuscript. For this reason it would be % nice to have an automaticism which will take care of every change. % % Being myself a chemist, I've been using the \texttt{chemcono} package by % Stefan Schulz for this purpose quite successfully over several years. This % package creates a library very similar to |thebibliography|. Users can now % refer to entries in the library by a command very similar to |\cite|. Thus, % once you change the library entry every reference to it will be updated % automatically upon running \LaTeX\ on the file. There is only one issue % associated with this package: You get a list of all declared compounds % inside your document wich at least looks odd. I therefore decided to write a % new package \texttt{chemcompounds} described in this document to address % this problem. % % When taking a closer look at the \texttt{chemcono} package, I realised that % the only thing one has to do is to get rid of everything which produces % text. Thus, as a basis I used the mechanism of |\bibitem| and |\cite| in % pretty much the same way as \texttt{chemcono} does by extracting the % corresponding code from |article.cls| and |latex.ltx| but deleting any % unnecessary commands producing output. I also introduced several lines of % code to make the printing of the compound names more customisable. % % Currently, the packages knows two different modes of operation. In % the default |implicit| mode, a compound name is created automatically as a % consecutive number when the compound is referenced for the first time by % |\compound|. Thus, all compounds will be numbered % consecutively in the order they appear in the text. If the automatically % generated name is not appropriate, a custom name can be given to a compound % by means of the |\declarecompound| command described below. % % In |noimplicit| mode names are not generated fully automatically. Instead, for % every compound a |\declarecompound| must be issued. This will again create a % subsequent number and a custom name can be given as an optional argument. The % main difference to |implicit| mode is that thus compounds will be % numbered in the order of the corresponding |\declarecompound| commands rather % than in the order of their appearance in the text. % % % \section{The user interface} % % Because of the way the implementation works, two \LaTeX\ runs are required % to get everything right. This should not be a problem since you have to run % \LaTeX\ twice anyway to get the table of contents and references right. The % package will issue a ``labels have changed'' warning if you have to rerun % \LaTeX. For every unknown compound name the package will issue a warning, too. % % \subsection{Package options} % % \begin{list}{}{\leftmargin=0pt \labelsep=0pt} % % \item % \DescribeMacro{implicit} % This option causes the package to operate in |implicit| mode. This is the % default. % % \item % \DescribeMacro{noimplicit} % This option is the opposite of |implicit| and causes the package to operate in % |noimplicit| mode. % % \end{list} % % \subsection{Assigning and accessing compound names} % % \begin{list}{}{\leftmargin=0pt \labelsep=0pt} % % \item % \DescribeMacro{\declarecompound} % |\declarecompound[|\meta{optional name}|]{|\meta{label}|}|\\ % assigns a name to a compound. % If the optional argument is omitted, a consecutive number is automatically % taken as compound name. This command can only occur in the preamble. % A personal recommendation is to keep all |\declarecompound|s together in a % separate file and |\input| this file in the preamble. % % In |implicit| mode, if no optional argument is given, the command does nothing % since the automatic compound name will be generated by |\compound|. % % \item % \DescribeMacro{\compound} % |\compound{|\meta{label1}|,|\meta{label2}|,|\dots|}|\\ % prints the name of a compound. If a list of labels is given as argument, a % list of names separated by |\compoundseparator| is created. In |implicit| mode % this command also creates a new compound name if the label is used for the % first time and a custom name has not already been assigned to this compound. % % \item % \DescribeMacro{\compound*} % The starred version works in almost exactly the same way as |\compound|. The % only difference is that it does not create any output at all. However, it % still creates the label in |implicit| mode. It can thus be used to create % ``hidden'' compounds in |implicit| mode. This, i.e., can be useful if some % compounds are depicted in an illustration or scheme which are only later or % even never mentioned in the text but the numbering scheme should take care of % them. % % \item % \DescribeMacro{\compound+} % The version with a '|+|' really prints only the name of a compound. In % |implicit| mode, no label is created. Thus, it is the opposite of the starred % command. % % \end{list} % % % % \subsection{Customization} % % The commands in this section can be used to fine-tune the appearance of the % compound names. In order to change the default behaviour you have to % |\renewcommand| the corresponding commands. The defaults for every command % are given in parentheses. % % \begin{list}{}{\leftmargin=0pt \labelsep=0pt} % % \item % \DescribeMacro{\compoundseparator} % |\compoundseparator| (\verb*<,\penalty\@m\ <)\\ % defines the separator in a list of compound names. % % \item % \DescribeMacro{\compoundglobalprefix} % |\compoundglobalprefix| ()\\ % defines the prefix for a list of compound names. This will be printed also in % case the list has length one. % % \item % \DescribeMacro{\compoundglobalsuffix} % |\compoundglobalsuffix| ()\\ % defines the suffix for a list of compound names. This will be printed also in % case the list has length one. % % \item % \DescribeMacro{\compoundprefix} % |\compoundprefix| ()\\ % defines the prefix for every compound. % % \item % \DescribeMacro{\compoundsuffix} % |\compoundsuffix| ()\\ % defines the suffix for every compound. % % \item % \DescribeMacro{\compoundstyle} % |\compoundstyle| (|\textbf|)\\ % defines the style of each name. % % \item % \DescribeMacro{\printcompound} % |\printcompound| % (|{\compoundprefix}{\compoundstyle{#1}}{\compoundsuffix}|)\\ % is used to actually format the name of each compound. If the previous % possibilities are not sufficient to meet your formatting demands the thing % you should redefine is this one. % % \end{list} % % % % \subsection{Examples} % % The following examples using % \begin{verbatim} % \declarecompound{label1} % \declarecompound{label2} % \declarecompound[5b]{label3} % \compound{label1} and \compound{label1,label2,label3} % \end{verbatim} % should clarify the meaning of the above commands. The first two % |\declarecommand|s could be omitted in |implicit| mode. % % \begin{itemize} % % \item % Using the defaults results in \textbf{1} and \textbf{1}, \textbf{2}, % \textbf{5b}. % % \item % \begin{verbatim} % \renewcommand{\compoundstyle}{\underbar} % \end{verbatim} % gives \underbar 1 and \underbar 1, \underbar 2, \underbar{5b}. % % \item % \begin{verbatim} % \renewcommand{\compoundseparator}{;} % \end{verbatim} % gives \textbf{1} and \textbf{1}; \textbf{2}; \textbf{5b}. % % \item % \begin{verbatim} % \renewcommand{\compoundglobalprefix}{(} % \renewcommand{\compoundglobalsuffix}{)} % \end{verbatim} % gives (\textbf{1}) and (\textbf{1}, \textbf{2}, \textbf{5b}). % % \item % \begin{verbatim} % \renewcommand{\compoundprefix}{(} % \renewcommand{\compoundsuffix}{)} % \end{verbatim} % gives (\textbf{1}) and (\textbf{1}), (\textbf{2}), (\textbf{5b}). % % \item % \begin{verbatim} % \renewcommand{\compoundglobalprefix}{\textbf{[}} % \renewcommand{\compoundglobalsuffix}{\textbf{]}} % \renewcommand{\compoundprefix}{\ensuremath{\langle}} % \renewcommand{\compoundsuffix}{\ensuremath{\rangle}} % \renewcommand{\compoundstyle}{\emph} % \end{verbatim} % gives \textbf{[}$\langle$\emph{1}$\rangle$\textbf{]} and % \textbf{[}$\langle$\emph{1}$\rangle$, % $\langle$\emph{2}$\rangle$, $\langle$\emph{5b}$\rangle$\textbf{]}. % % \end{itemize} % % \noindent % As shown above customization is not limited solely to parentheses etc.\ % but can include formating commands, too. % % % % \StopEventually{} % % \section{The implementation} % %\iffalse %<*package> %\fi % % \subsection{Identification} % The package identifies itself at the top using something like % \iffalse % Identification is already done on top of the file. Thus the following % code should be printed in the documentation but should not be included % in the package. % %<*!package> % \fi % \begin{macrocode} \NeedsTeXFormat{LaTeX2e} \ProvidesPackage{chemcompounds} [\filedate\space \fileversion\space Dictionary for compound numbering] % \end{macrocode} % \iffalse % %<*package> % \fi % % \subsection{Package options} % % \begin{macro}{\ifchemcompounds@implicit} % \changes{1.1.0}{2005/10/06}{New.} % Define a new boolean variable defining whether |implicit| mode is enabled. % \begin{macrocode} \newif\ifchemcompounds@implicit % \end{macrocode} % \end{macro} % % \begin{macro}{implicit} % \changes{1.1.0}{2005/10/07}{New option.} % \begin{macro}{noimplicit} % \changes{1.1.0}{2005/10/06}{New option.} % The following package options set |ifchemcompounds@implicit| either to true or % false. The default is |implicit| mode. % \begin{macrocode} \DeclareOption{implicit}{\chemcompounds@implicittrue} \DeclareOption{noimplicit}{\chemcompounds@implicitfalse} \ExecuteOptions{implicit} % \end{macrocode} % \end{macro} % \end{macro} % % Process options. % \changes{1.1.0}{2005/10/06}{Added code to process options.} % \begin{macrocode} \ProcessOptions % \end{macrocode} % % % \subsection{User interface} % % The work flow for creating and accessing compound names was borrowed from the % definition of |\bibitem| and |\cite|. % % \begin{macro}{\compoundseparator} % \changes{1.1.0}{2005/10/06}{Changed default value to include trailing % space.} % \begin{macro}{\compoundglobalprefix} % \begin{macro}{\compoundglobalsuffix} % \begin{macro}{\compoundprefix} % \begin{macro}{\compoundsuffix} % \begin{macro}{\compoundstyle} % \begin{macro}{\printcompound} % \changes{1.1.2}{2005/10/18}{New. Previous \cs{@compound} % command.} % The following definitions define the default layout of the names in the text % (no surrounding parentheses, multiple compound names separated by comma, % names in bold face). |\printcompound| defines the way each name is % printed. % \begin{macrocode} \def\compoundseparator{,\penalty\@m\ } \let\compoundglobalprefix\@empty \let\compoundglobalsuffix\@empty \let\compoundprefix\@empty \let\compoundsuffix\@empty \def\compoundstyle{\textbf} \def\printcompound#1{{\compoundprefix}{\compoundstyle{#1}}{\compoundsuffix}} % \end{macrocode} % \end{macro} % \end{macro} % \end{macro} % \end{macro} % \end{macro} % \end{macro} % \end{macro} % % \begin{macro}{\declarecompound} % \changes{1.1.0}{2005/10/07}{Only in preamble.} % This command is used to assign a name to a compound. % It just looks ahead whether an optional argument was given % and calls the appropriate internal command. To avoid problems with the % creation of the labels, this command is only allowed in the preamble. % \begin{macrocode} \def\declarecompound{\@ifnextchar[\@ldeclarecompound\@declarecompound} \@onlypreamble\declarecompound % \end{macrocode} % \end{macro} % % \begin{macro}{\ifchemcompounds@print} % \changes{1.1.2}{2005/10/18}{New.} % Define a new boolean variable indicating whether the starred version of % |\compound| was used. % \begin{macrocode} \newif\ifchemcompounds@print % \end{macrocode} % \end{macro} % % \begin{macro}{\ifchemcompounds@create} % \changes{1.1.3}{2006/12/01}{New.} % Define a new boolean variable indicating whether a label name shall be % created automatically in |implicit| mode. % \begin{macrocode} \newif\ifchemcompounds@create % \end{macrocode} % \end{macro} % % \begin{macro}{\compound} % \changes{1.1.3}{2006/12/01}{Abandon use of \cs{@ifstar} since this breaks % compatibility with amsmath (reported by J. Ryan).} % \changes{1.1.3}{2006/12/01}{Set chemcompounds@create appropriately.} % \changes{1.1.2}{2005/10/18}{Only check for starred version and call internal % command. Functionality moved to \cs{@compound}.} % \changes{1.1.1}{2005/10/11}{Changed label prefix to 'comp'.} % \changes{1.1.0}{2005/10/07}{Changed definition of % \cs{compoundseparator}. Inserted \cs{@createcompoundhook}.} % \changes{1.0.1}{2005/10/05}{Replaced \cs{hbox} by \cs{mbox} % to work around some spacing issues when printing the compound name.} % \begin{macro}{\compound*} % \changes{1.1.2}{2005/10/18}{New.} % \begin{macro}{\compound+} % \changes{1.1.3}{2006/12/01}{New (suggested by J. Hooper).} % This command will finally print the name associated with a compound label. % The starred version just creates the label (in |implicit| mode) without % printing the value. % The command itself just checks whether the starred or plussed version is used, % sets the internal flags appropriately and calls the internal command % |\@compound|. % \begin{macrocode} \DeclareRobustCommand{\compound}{% \chemcompounds@createtrue \chemcompounds@printtrue \@ifnextchar *{\chemcompounds@printfalse\@firstoftwo\@compound} {% \@ifnextchar +{\chemcompounds@createfalse\@firstoftwo\@compound} {\@compound} } } % \end{macrocode} % \end{macro} % \end{macro} % \end{macro} % % % % \subsection{Internal commands} % % \begin{macro}{\@compound} % \changes{1.1.2}{2005/10/18}{New. Previous functionality moved to % \cs{printcompound}.} % This command retrieves the name associated with a compound and prints it % in the text using the previously defined format. The code is a modified % version of the definition of |\cite| in |latex.ltx|. % If this command is invoked by |\compound*|, |\ifchemcompounds@print| will be % false and all output will be suppressed. % \begin{macrocode} \def\@compound#1{% % \end{macrocode} % Print optional prefix to a list of compounds. % \begin{macrocode} \ifchemcompounds@print \compoundglobalprefix \fi % \end{macrocode} % Now loop over every label in the argument list. % \begin{macrocode} \let\@compounda\@empty \@for\@compoundb:=#1\do{% \edef\@compoundb{\expandafter\@firstofone\@compoundb}% % \end{macrocode} % Print separator. Note that it is empty for the first entry and % |\compoundseparator| otherwise. % \begin{macrocode} \ifchemcompounds@print \@compounda \def\@compounda{{\compoundseparator}}% \fi % \end{macrocode} % If compound is undefined, print '\textbf{?}' and raise a warning. % \begin{macrocode} \@ifcompoundundefined{\@compoundb}{% \ifchemcompounds@print \mbox{\reset@font\bfseries ?}% \fi \G@refundefinedtrue \@latex@warning {compound `\@compoundb' on page \thepage\space undefined}% }{% % \end{macrocode} % If compound is known print formatted name. % \begin{macrocode} \ifchemcompounds@print \mbox{\printcompound{\@nameuse{comp@\@compoundb}}}% \fi }% % \end{macrocode} % In |implicit| mode |\@createcompoundhook| will generate a new name if this has % not been done before. In |noimplicit| mode this does nothing. % \begin{macrocode} \@createcompoundhook{\@compoundb}% }% % \end{macrocode} % Print optional suffix to a list of compounds. % \begin{macrocode} \ifchemcompounds@print \compoundglobalsuffix % \end{macrocode} % Although nothing is printed, under certain conditions an additional % space is created. Remove it. % \begin{macrocode} \else \unskip \fi } % \end{macrocode} % \end{macro} % % \begin{macro}{\chemcompounds@counter} % Define a new counter which will be used for generating the compound names. % \begin{macrocode} \newcounter{chemcompounds@counter} % \end{macrocode} % \end{macro} % % \begin{macro}{\chemcompounds@label} % \changes{1.1.1}{2005/10/11}{Changed label prefix to 'comp' since 'c' is % already in use.} % \changes{1.1.0}{2005/10/06}{Labels are now prefixed with 'c' making them % hopefully unique.} % The next command will be used in the |.aux| file and defines a new label for % every compound. % \begin{macrocode} \def\chemcompounds@label{\@newl@bel {comp}} % \end{macrocode} % \end{macro} % % \begin{macro}{\chemcompounds@writelabel} % \changes{1.1.2}{2005/10/18}{Added \cs{ignorespaces}.} % \changes{1.1.1}{2005/10/10}{\cs{noexpand} the label value. Required % for improved robustness.} % \changes{1.1.0}{2005/10/06}{New.} % Write the label and its value to the |aux| file. % \begin{macrocode} \def\chemcompounds@writelabel#1#2{% \if@filesw \begingroup \def\protect{\noexpand}% \immediate\write\@auxout{ \string\chemcompounds@label{#1}{#2} }% \endgroup \fi \ignorespaces } % \end{macrocode} % \end{macro} % % \begin{macro}{\@ldeclarecompound} % \changes{1.1.0}{2005/10/06}{Completly rewritten.} % The next command gets called if an additional argument was supplied to % |\declarecompound|. It creates the compound with the given name as soon as % the |aux| file is writeable. This command can only be used in the preamble. % \begin{macrocode} \def\@ldeclarecompound[#1]#2{% \AtBeginDocument{\@createcompound[#1]{#2}} } \@onlypreamble\@ldeclarecompound % \end{macrocode} % \end{macro} % % \begin{macro}{\@declarecompound} % \changes{1.1.0}{2005/10/06}{Completely rewritten.} % In |implicit| mode this command does nothing since default names are created % automatically by |\compound|. % \begin{macrocode} \ifchemcompounds@implicit \let\@declarecompound\@gobble % \end{macrocode} % In |noimplicit| mode this simply creates the compound as soon as % the |aux| file is writeable. % \begin{macrocode} \else \def\@declarecompound#1{% \AtBeginDocument{\@createcompound{#1}} } \fi \@onlypreamble\@declarecompound % \end{macrocode} % This command can only be used in the preamble. % \end{macro} % % \begin{macro}{\@ifcompoundundefined} % \changes{1.1.1}{2005/10/11}{Changed label prefix to 'comp'.} % \changes{1.1.0}{2005/10/06}{New.} % Test whether a compound has already been defined by testing the associated % label. % \begin{macrocode} \def\@ifcompoundundefined#1{% \@ifundefined{comp@#1} } % \end{macrocode} % \end{macro} % % \begin{macro}{\@createcompound} % \changes{1.1.0}{2005/10/06}{New.} % This command is used to create a new compound name. It just looks ahead % whether an optional argument was given and calls the appropriate command. % \begin{macrocode} \def\@createcompound{% \@ifnextchar[\@@lcreatecompound\@@createcompound } % \end{macrocode} % \end{macro} % % \begin{macro}{\@@createcompound} % \changes{1.1.0}{2005/10/06}{New.} % If a compound name has not yet been created this command increments % |chemcompounds@counter| and takes the new value as the compound name. % The new compound name is written to the |aux| file and a flag is set to % indicate that a name for this compound has already been created. % \begin{macrocode} \def\@@createcompound#1{% \@ifnotcompoundcreated{#1}{% \stepcounter{chemcompounds@counter}% \chemcompounds@writelabel{#1}{\the\value{chemcompounds@counter}} \@compoundcreated{#1}% }% } % \end{macrocode} % \end{macro} % % \begin{macro}{\@@lcreatecompound} % \changes{1.1.0}{2005/10/06}{New.} % This command creates a compound name from the first parameter and writes it % to the |aux| file. A flag is set to indicate that a name for this compound has % already been created. % \begin{macrocode} \def\@@lcreatecompound[#1]#2{% \chemcompounds@writelabel{#2}{#1} \@compoundcreated{#2}% } % \end{macrocode} % \end{macro} % % \begin{macro}{\@compoundcreated} % \changes{1.1.1}{2005/10/11}{Changed label prefix to 'compc'.} % \changes{1.1.0}{2005/10/06}{New.} % Set a flag indicating that the compound name has been created. This is done by % defining an appropriate label in |implicit| mode. % \begin{macrocode} \ifchemcompounds@implicit \def\@compoundcreated#1{% \global\@namedef{compc@#1}{}% } % \end{macrocode} % In |noimplicit| mode this is unnecessary, thus just gobble the argument. % \begin{macrocode} \else \let\@compoundcreated\@gobble \fi % \end{macrocode} % \end{macro} % % \begin{macro}{\@ifnotcompoundcreated} % \changes{1.1.1}{2005/10/11}{Changed label prefix to 'compc'.} % \changes{1.1.0}{2005/10/07}{New.} % Check whether a new compound name has already been created. % In |implicit| mode existence of the corresponding label (flag) is checked. % If it does not exist, the code given as the second argument is executed. % \begin{macrocode} \ifchemcompounds@implicit \def\@ifnotcompoundcreated#1#2{% \@ifundefined{compc@#1}{#2}{}% } % \end{macrocode} % In |noimplicit| mode the label (flag) is unused and a new name will always be. % created. Therefore just execute the code given as second argument. % \begin{macrocode} \else \let\@ifnotcompoundcreated\@secondoftwo \fi % \end{macrocode} % \end{macro} % % \begin{macro}{\@createcompoundhook} % \changes{1.1.3}{2006/12/01}{Implicit definition now checks for % chemcompounds@create} % \changes{1.1.0}{2005/10/07}{New.} % This command gets called everytime a compound name is printed. % In |implicit| mode this command creates a new compound name if % |\ifchemcompounds@create| is true. The |\compound+| command sets % this boolean to false. % \begin{macrocode} \ifchemcompounds@implicit \def\@createcompoundhook#1{% \ifchemcompounds@create \@createcompound{#1}% \fi } % \end{macrocode} % In |noimplicit| mode this is unnecessary. Therefore just gobble the argument. % \begin{macrocode} \else \let\@createcompoundhook\@gobble \fi % \end{macrocode} % \end{macro} % % \begin{macrocode} \endinput % \end{macrocode} % %\iffalse % %\fi % % \Finale