From ad1601f28307c9af81f8da1924f64f21ec9c2974 Mon Sep 17 00:00:00 2001 From: Karl Berry Date: Sun, 16 Aug 2015 21:17:20 +0000 Subject: acro (16aug15) git-svn-id: svn://tug.org/texlive/trunk@38132 c570f23f-e606-0410-a88d-b1316a301751 --- Master/texmf-dist/doc/latex/acro/README | 6 +- Master/texmf-dist/doc/latex/acro/acro_en.pdf | Bin 514193 -> 538085 bytes Master/texmf-dist/doc/latex/acro/acro_en.tex | 430 ++++++- Master/texmf-dist/tex/latex/acro/acro.sty | 1730 ++++++++++++++++---------- 4 files changed, 1451 insertions(+), 715 deletions(-) (limited to 'Master') diff --git a/Master/texmf-dist/doc/latex/acro/README b/Master/texmf-dist/doc/latex/acro/README index faabb9b22e2..54bb91a97ee 100644 --- a/Master/texmf-dist/doc/latex/acro/README +++ b/Master/texmf-dist/doc/latex/acro/README @@ -1,12 +1,12 @@ -------------------------------------------------------------------------- -the ACRO package v1.6b +the ACRO package v2.0 Typeset Acronyms -2015/05/10 +2015/08/16 -------------------------------------------------------------------------- Clemens Niederberger -Web: https://bitbucket.org/cgnieder/acro/ +Web: http://www.mychemistry.eu/forums/forum/acro/ E-Mail: contact@mychemistry.eu -------------------------------------------------------------------------- Copyright 2012--2015 Clemens Niederberger diff --git a/Master/texmf-dist/doc/latex/acro/acro_en.pdf b/Master/texmf-dist/doc/latex/acro/acro_en.pdf index a53fccefc36..aba65c0ac93 100644 Binary files a/Master/texmf-dist/doc/latex/acro/acro_en.pdf and b/Master/texmf-dist/doc/latex/acro/acro_en.pdf differ diff --git a/Master/texmf-dist/doc/latex/acro/acro_en.tex b/Master/texmf-dist/doc/latex/acro/acro_en.tex index 6f64ba0dd21..11b05f82fff 100644 --- a/Master/texmf-dist/doc/latex/acro/acro_en.tex +++ b/Master/texmf-dist/doc/latex/acro/acro_en.tex @@ -10,7 +10,7 @@ % % -------------------------------------------------------------------------- % Clemens Niederberger -% Web: https://bitbucket.org/cgnieder/acro/ +% Web: http://www.mychemsitry.eu/forums/forum/acro/ % E-Mail: contact@mychemistry.eu % -------------------------------------------------------------------------- % Copyright 2011-2015 Clemens Niederberger @@ -28,18 +28,11 @@ % The Current Maintainer of this work is Clemens Niederberger. % -------------------------------------------------------------------------- % The acro package consists of the files -% - acro.sty, acro0.def, acro1.def, acro_en.tex, acro_en.pdf, README +% - acro.sty, acro_en.tex, acro_en.pdf, README % -------------------------------------------------------------------------- % If you have any ideas, questions, suggestions or bugs to report, please % feel free to contact me. % -------------------------------------------------------------------------- -% -% if you want to compile this documentation you'll need the document class -% `cnpkgdoc' which you can get here: -% https://bitbucket.org/cgnieder/cnpkgdoc/ -% the class is licensed LPPL 1.3 or later -% - \documentclass[load-preamble+,scrartcl={DIV10}]{cnltx-doc} \usepackage[utf8]{inputenc} \usepackage[single,macros,accsupp,index]{acro} @@ -58,15 +51,22 @@ automatically sorts the list created by \cs{printacronyms}.% } , add-cmds = { - ac,aca,acap,acf,acflike,acfp,acfplike,acl,aclp,acp,acs,acsp, - acreset,acresetall,acsetup, - DeclareAcronym,DeclareAcronymCitation,DeclareAcronymFormat, - DeclareAcronymPDFString, - iac,Iac,iaca,Iaca,iacs,Iacs,iacl,Iacl,iacf,Iacf,iacflike,Iacflike, - printacronyms + ac, Ac, aca, Aca, acap, Acap, acdot, acf, Acf, acflike, acg, acfp, Acfp, + acfplike, aciftrailing, acl, Acl, aclp, Aclp, acp, Acp, + AcroRegisterTrailing, acs, Acs, acsp, Acsp, acspace, acreset, + acresetall, acsetup, + DeclareAcroCommand, DeclareAcronym, DeclareAcronymCitation, + DeclareAcronymFormat, DeclareAcronymPDFString, DeclarePseudoAcroCommand, + iac, Iac, iaca, Iaca, iacs, Iacs, iacl, Iacl, iacf, Iacf, iacflike, + Iacflike, + NewAcroCommand, NewPseudoAcroCommand, + printacronyms, + ProvideAcroCommand, ProvideAcroEnding, ProvidePseudoAcroCommand, + RenewAcroCommand, RenewPseudoAcroCommand } , add-silent-cmds = { - addcolon,nato,newlist,ny,setlist + addcolon, DeclareInstance, babelhyphen, ExplSyntaxOff, ExplSyntaxOn, nato, + NewDocumentCommand, newlist, ny, setlist } , index-setup = { level = \section , headers={\indexname}{\indexname} } } @@ -108,6 +108,8 @@ \textsc{Wikipedia}} \newcommand*\h[1]{\textcolor{cnltx}{\textbf{#1}}} +\ProvideAcroEnding {possessive} {'s} {'s} + % declare acronyms \DeclareAcronym{cd} { @@ -229,6 +231,17 @@ \newcommand*\latin{\textit} +\makeatletter +\newcommand*\TF{\textcolor{red}{\uline{\code{\textcolor{cs}{\textit{TF}}}}}} +\renewenvironment{commands} + {% + \cnltx@set@catcode_{12}% + \let\command\cnltx@command + \cnltxlist + } + {\endcnltxlist} +\makeatother + \begin{document} \section{Licence and Requirements} \license @@ -280,10 +293,6 @@ go with \pkg{glossaries}, then. Are you planning to add a nomenclature? You may want to choose \pkg{nomencl} (or again: \pkg{glossaries}) and so on. \acro\ does a good job for lists of abbreviations. -\section{News} -\subsection{Version 1.6} -Support for versions~0.* has been dropped. - \section{Basics} \subsection{Creating New Acronyms} \noindent\changedversion{1.0}Acronyms are created with the command @@ -298,10 +307,15 @@ documentation. \begin{options} %% short \keyval{short}{text}\Default! - the short form of the acronym. + the short form of the acronym. This option is required: an acronym must + have a short form. If this is set it \emph{must} be set as first option! + If another option is set first and notices the \option{short} option + missing it assumes that the \meta{id} should be used as short version and + sets it accordingly. A warning will be written to the log then. %% long \keyval{long}{text}\Default! - the long form of the acronym. + the long form of the acronym. This option is required: an acronym must + have a description. %% short-plural \keyval{short-plural}{text}\Default{s} the plural ending appended to the short form. @@ -392,7 +406,7 @@ documentation. \end{options} In its simplest form an acronym needs a short and a long form. Please note -that both keys \emph{must} be set and that the \key{short} key \emph{must} +that both keys \emph{must} be set and that the \option{short} key \emph{must} always be the \emph{first} key that is set. \begin{sourcecode} % preamble: @@ -444,8 +458,8 @@ citation key. The first appearance now looks as follows\footnote{The appearance of the citation of course depends on the citation style you're using.}: \acf{ny}. -\subsection{Using the Acronyms -- the Commands} -Acronyms are used with with one of the following commands: +\subsection{Using the Acronyms -- the Commands}\label{sec:using-acronyms-comm} +Acronyms are used with one of the following commands: \begin{commands} \command{ac}[\sarg\marg{id}] basic command; the first output is different from subsequent ones. @@ -900,7 +914,12 @@ There are a few options which change the general behaviour of \acro. this option. \keybool{single}\Default{false} If set to \code{true} an acronym that's used only once (with \cs{ac}) in a - document will only print the long form and will not be printed in the list. + document will only print the acronym in a specified form and will not be + printed in the list. + %% + \keychoice{single-form}{long,short,alt,first}\Default{long} + \sinceversion{2.}Determines how a single appearance of an acronym is + printed if \keyis{single}{true} has been chosen. %% \keybool{hyperref}\Default{false} If set to \code{true} the short forms of the acronyms will be linked to @@ -965,12 +984,23 @@ There are a few options which change the general behaviour of \acro. citation command that takes the cite key as argument is valid, for example \pkg*{biblatex}'s \cs*{footcite}. %% - \keyval{cite-space}{code}\Default{\cs*{nobreakspace}} + \keyval{cite-connect}{code}\Default{\cs*{nobreakspace}} Depending on the citation command in use a space should be inserted before the citation or maybe not (e.g.\ \cs*{footcite}\ldots). This option allows you to set this. Actually it can be used to place arbitrary code right before the citation. %% + \keybool{group-citation}\Default{false} + \sinceversion{2.0}If set to true the short form (or the long form) and the + citation of an acronym will be printed together in parentheses when an + acronym is used the first time. + %% + \keyval{group-cite-cmd}{control sequence}\Default{\cs*{cite}} + \sinceversion{2.0}This option determines which command is used for the + citation when an acronym is used the first time \emph{and} + \keyis{group-citation}{true}. Each citation command that takes the cite + key as argument is valid, for example \pkg*{biblatex}'s \cs*{footcite}. + %% \keybool{index}\Default{false} \sinceversion{1.1}If set to \code{true} an index entry will be recorded every time an \emph{unstarred} acronym command is used for the @@ -1139,9 +1169,9 @@ possible output forms of the acronyms. own. %% \keychoice{list-heading}{chapter,chapter*,section,section*,subsection,% - subsection*,addchap,addsec,none}\null + subsection*,subsubsection,subsubsection*,addchap,addsec,none}\null \Default{section*} - \changedversion{1.3}The heading type of the list. The last two only work + \changedversion{2.0}The heading type of the list. The last two only work with a \KOMAScript{} class that also defines the appropriate command. A special value is \code{none} which suppresses the heading. %% @@ -1188,6 +1218,108 @@ the acronym list: \acsetup{list-type=acronyms,extra-style=comma} \printacronyms +\subsection{Other Heading Command} +If you want a \option{list-heading} which is not yet provided you can add your +own option: +\begin{sourcecode} + \DeclareInstance{acro-title}{myname}{sectioning} + { name-format = command that uses #1 } +\end{sourcecode} +After that you could use \keyis{list-heading}{myname}. + +\section{Trailing Tokens and Special Action} + +\acro\ has the possibility\sinceversion{2.0} to look ahead for certain tokens +and switch a boolean if it finds them. Per default \acro\ knows about three +tokens: the \enquote{\code{dot}} (\code{.}), the \enquote{\code{dash}} +(\code{-}) and the \enquote{\code{babel-hyphen}} (\cs*{babelhyphen}). + +A token is made known to \acro\ with the following macro: +\begin{commands} + \command{AcroRegisterTrailing}[\meta{token}\marg{name}] + This registers the token \meta{token} so \acro\ looks if it follows + directly after an acronym macro. \meta{name} is the internal name for + this token. +\end{commands} +The \acro\ package already registers the above mentioned tokens: +\begin{sourcecode} + \AcroRegisterTrailing . {dot} + \AcroRegisterTrailing - {dash} + \AcroRegisterTrailing \babelhyphen {babel-hyphen} +\end{sourcecode} + +If a token is registered it doesn't mean that \acro\ looks for it. The token +must first be activated for this: +\begin{options} + \keyval{activate-trailing-tokens}{csv list of token names} + Tell \acro\ to look for trailing tokens. This is done by giving a csv + list of the internal \emph{names} of the tokens. Per default only + \code{dot} is activated. + \keyval{deactivate-trailing-tokens}{csv list of token names} + Tell \acro\ not to look for trailing tokens. This is done by giving a csv + list of the internal \emph{names} of the tokens. +\end{options} + +All the above on its own does nothing visible. However: inside of an acronym, +\ie, for example inside the long or the short form it can be tested for those +trailing options: +\begin{commands} + \command{aciftrailing}[\marg{csv list of token + names}\marg{true}\marg{false}] + Check if one of the tokens listed in \meta{csv list of token names} is + following and either place \meta{true} or \meta{false} in the input + stream. +\end{commands} +\acro\ uses this to define to further macros: +\begin{commands} + \command{acdot} Inserts a \code{.} if no \code{dot} follows. + \command{acspace} Inserts a \cs*{space} if no \code{dash} or + \code{babel-hyphen} follows. +\end{commands} +The definitions are equivalent to the following code: +\begin{sourcecode} + \newcommand*\acdot{\aciftrailing{dot}{}{.}} + \newcommand*\acspace{\aciftrailing{dash,babel-hyphen}{}{\space}} +\end{sourcecode} + +This could be used to define an acronym as follows: +\begin{sourcecode} + \DeclareAcronym{etc}{ + short = {\textit{etc}\acdot} , + long = {\textit{et cetera}} , + short-plural = , long-plural = + } +\end{sourcecode} +If now you somewhere use +\begin{sourcecode} + \ac{etc}. +\end{sourcecode} +there won't be two dots printed. + +The command \cs{acspace} is used already in the definition of the first +appearance of a macro. Let's say you're a German chemist and you have +\begin{sourcecode} + \DeclareAcronym{PU}{ + long = Polyurethan , + long-plural = e + } +\end{sourcecode} +and you use it the first time like this: +\begin{sourcecode} + \ac{PU}-Hartschaum +\end{sourcecode} +then according to German orthography and typesetting rules this should be +printed as +\begin{center} + \enquote{Polyurethan(PU)-Hartschaum} +\end{center} +\ie, with \emph{no} space between long and short form. This is exactly what +happens it you say +\begin{sourcecode} + \acsetup{activate-trailing-tokens = {dash,babel-hyphen}} +\end{sourcecode} +in the preamble. + \section{About Page Ranges} If you enable the \option{page-ref} option \acro\ adds page numbers to the list of acronyms. In version~0.\versionstar{} it would add a page reference for an @@ -1237,24 +1369,230 @@ list (provided they are displayed in the style chosen). Like with an index the references will thus not point to the acronyms directly but to the page they're on. -\appendix +\section{Defining Own Acronym Macros}\label{sec:defining-own-acronym} + +The commands\sinceversion{2.0}\sinceversion{2.0}\sinceversion{2.0} explained in +section~\ref{sec:using-acronyms-comm} have all been defined with a dedicated +command -- there is a family of dedicated commands, actually: +\begin{commands} + \command{NewAcroCommand}[\marg{cs}\marg{code}] + Defines a new \acro\ acronym command \meta{cs}. This sets up the + necessary framework needed by acronym commands and defines \meta{cs} with + an optional star argument and a mandatory argument for the acronym id + using \pkg{xparse}'s \cs*{NewDocumentCommand}. Inside \meta{code} one can + refer to the id with \code{\#1}. + \command{RenewAcroCommand}[\marg{cs}\marg{code}] + Defines a new \acro\ acronym command \meta{cs}. This sets up the + necessary framework needed by acronym commands and defines \meta{cs} with + an optional star argument and a mandatory argument for the acronym id + using \pkg{xparse}'s \cs*{RenewDocumentCommand}. Inside \meta{code} one + can refer to the id with \code{\#1}. + \command{DeclareAcroCommand}[\marg{cs}\marg{code}] + Defines a new \acro\ acronym command \meta{cs}. This sets up the + necessary framework needed by acronym commands and defines \meta{cs} with + an optional star argument and a mandatory argument for the acronym id + using \pkg{xparse}'s \cs*{DeclareDocumentCommand}. Inside \meta{code} one + can refer to the id with \code{\#1}. + \command{ProvideAcroCommand}[\marg{cs}\marg{code}] + Defines a new \acro\ acronym command \meta{cs}. This sets up the + necessary framework needed by acronym commands and defines \meta{cs} with + an optional star argument and a mandatory argument for the acronym id + using \pkg{xparse}'s \cs*{ProvideDocumentCommand}. Inside \meta{code} one + can refer to the id with \code{\#1}. +\end{commands} + +Inside these macros one can use a number of low-level expl3 +commands\footnote{Which is why you need to use them inside an expl3 + programming environment. This means in the preamble surround the + definitions with \cs*{ExplSyntaxOn} and \cs*{ExplSyntaxOff}.}. + +\paragraph{Acronym fetching commands} +\begin{commands} + \command*{acro_use:n}[ \marg{id}] + Fetches the acronym using either the first or the long form depending on + earlier uses. + \command*{acro_short:n}[ \marg{id}] + Fetches the short form of the acronym. + \command*{acro_long:n}[ \marg{id}] + Fetches the long form of the acronym. + \command*{acro_alt:n}[ \marg{id}] + Fetches the alternative short form of the acronym. +\end{commands} + +\paragraph{Acronym setup commands} +\begin{commands} + \command*{acro_first_upper:} + \acro\ setup command which tells the macros above that we want to + uppercase the first letter of the long version. Should be used + \emph{before} one of the acronym fetching commands. + \command*{acro_plural:} + \acro\ setup command which tells the macros above that we want to use + plural forms. Should be used \emph{before} one of the acronym fetching + commands. + \command*{acro_indefinite:} + \acro\ setup command which tells the macros above that we want to add the + indefinite article. Should be used \emph{before} one of the acronym + fetching commands. + \command*{acro_cite:} + \acro\ setup command which tells the macros above that we want to add the + citation in any case independent of the option \option{cite}. Should be + used \emph{before} one of the acronym fetching commands. + \command*{acro_no_cite:} + \acro\ setup command which tells the macros above that we want to have no + citation independent of the option \option{cite}. Should be used + \emph{before} one of the acronym fetching commands. + \command*{acro_index:} + \acro\ setup command which tells the macros above that we want to add an + index in any case independent of the option \option{index}. Should be + used \emph{before} one of the acronym fetching commands. +\end{commands} + +\paragraph{Additional macros for further uses} +\begin{commands} + \command*{acro_begin:} + When an acronym macro is defined \enquote{by hand}, \ie, not using + \cs{NewAcroCommand} then this should be the first macro in the code. Must + have a matching \cs*{acro_end:}. + \command*{acro_end:} + When an acronym macro is defined \enquote{by hand}, \ie, not using + \cs{NewAcroCommand} then this should be the last macro in the code. Must + have a matching \cs*{acro_begin:}. + \command*{acro_check_and_mark_if:nn}[ \marg{boolean expression} \marg{id}] + Checks if the acronym \meta{id} exists and marks it as used when + \meta{boolean} expression evaluates to \code{true}. This macro is used + inside \cs{NewAcroCommand} and friends. + \command*{acro_check_acronym:nn}[ \marg{id} \Marg{true|false}] + Checks if the acronym \meta{id} exists and marks it as used if \code{true} + or doesn't. This macro is used inside \cs*{acro_check_and_mark_if:nn}. + \command*{acro_use_acronym:n}[ \Marg{true|false}] + Mark an acronym as used or don't. This macro is used inside + \cs*{acro_check_acronym:nn}. An acronym marked as used cannot be + unmarked. + \expandable\command*{acro_if_acronym_used:n}[\TF\ \marg{id} \marg{true} + \marg{false}] + The code-level version of \cs{acifused}. This macro is expandable. +\end{commands} + +\paragraph{Examples} +The usage of above macros is best explained with a few examples. The +following definition is done by \acro: +\begin{sourcecode} + \NewAcroCommand \ac { \acro_use:n {#1} } +\end{sourcecode} +An equivalent definition for \cs{ac} would be +\begin{sourcecode} + \NewDocumentCommand \ac {sm} + { + \acro_begin: + \acro_check_and_mark_if:nn {#1} {#2} + \acro_use:n {#2} + \acro_end: + } +\end{sourcecode} +which should explain what the actual framework is which \cs{NewAcroCommand} +adds. + +Other definitions by \acro\ are for example the following ones: +\begin{sourcecode} + \NewAcroCommand \Ac + { + \acro_first_upper: + \acro_use:n {#1} + } + \NewAcroCommand \acp + { + \acro_plural: + \acro_use:n {#1} + } + \NewAcroCommand \Acp + { + \acro_plural: + \acro_first_upper: + \acro_use:n {#1} + } + \NewAcroCommand \Aclp + { + \acro_plural: + \acro_first_upper: + \acro_long:n {#1} + } +\end{sourcecode} + +\section{About Plural Forms, Possessive Forms and Similar Constructs -- the + Concept of Endings} -% \section{Commands provided in version~0.\versionstar} -% Prior to version~1.0 the following commands were available. They are still -% provided if you set the option \keyis{version}{0}. They will be mentioned -% here shortly but they won't be explained any more. If you'd like a more -% thorough description ask me for the documentation to version~0.6a. -% \begin{commands} -% \command{DeclareAcronym}[\sarg\marg{id}\Marg{\meta{short},\meta{pl}}% -% \oarg{alt.}\Marg{\meta{long},\meta{pl}}\marg{extra}\oarg{class}] -% \verbcode+% can be used only in preamble+ -% \command{DeclareAcronymFormat}[\marg{id}\marg{format}] -% \verbcode+% can be used only in preamble+ -% \command{DeclareAcronymCitation}[\marg{id}\oarg{pre}\oarg{post}\marg{cite keys}] -% \verbcode+% can be used only in preamble+ -% \command{DeclareAcronymPDFString}[\marg{id}\Marg{\meta{pdf entry},\meta{plural ending}}] -% \verbcode+% can be used only in preamble+ -% \end{commands} +\acro\ has a concept of \emph{endings}. All of \acro's plural options are +defined by saying +\begin{sourcecode} + \ProvideAcroEnding {plural} {s} {s} +\end{sourcecode} +The command's syntax and what it does is as follows: +\begin{commands} + \command{ProvideAcroEnding}[\marg{name}\marg{short default}\marg{long default}] + This macro defines the options + \begin{itemize} + \item \option*{\meta{name}-ending}, + \item \option*{short-\meta{name}-ending}, + \item \option*{alt-\meta{name}-ending} and + \item \option*{long-\meta{name}-ending}. + \end{itemize} + It also defines the acronym properties + \begin{itemize} + \item \option*{short-\meta{name}}, + \item \option*{short-\meta{name}-form}, + \item \option*{alt-\meta{name}}, + \item \option*{alt-\meta{name}-form}, + \item \option*{long-\meta{name}} and + \item \option*{long-\meta{name}-form}. + \end{itemize} + Additionally it defines a setup macro as + described in section~\ref{sec:defining-own-acronym}, + \cs*{acro_\meta{name}:}. If \meta{name} contains a \code{-} (dash) it is + replaced by \code{\_} before \cs*{acro_\meta{name}:} is built. So if you + choose \code{my-name} the corresponding macro is named + \cs*{acro_my_name:}. If you use any other non-letters you are on your + own. + + Note that you \emph{must use \cs{ProvideAcroEnding} before any acronym + definition}! +\end{commands} + +This could be used together with the macros described in +section~\ref{sec:defining-own-acronym} for adding support for possessive +forms: +\begin{example} + \ExplSyntaxOn + % this now only works because I've use the same already in the preamble so + % it does nothing here: + \ProvideAcroEnding {possessive} {'s} {'s} + + \NewAcroCommand \acg + { + \acro_possessive: + \acro_use:n {#1} + } + \ExplSyntaxOff + The \acg{cd} booklet says\ldots +\end{example} + +Please note that different endings are cumulative which you probably want to +avoid! Imagine a macro +\begin{sourcecode} + \NewAcroCommand \acgp + { + \acro_possessive: + \acro_plural: + \acro_use:n {#1} + } +\end{sourcecode} +This would give \enquote{\ac{cd}s's} instead of \enquote{\ac{cd}s'}. To solve +this you might want to consider +\begin{sourcecode} + \ProvideAcroEnding {possessive-singular} {'s} {'s} + \ProvideAcroEnding {possessive-plural} {s'} {s'} +\end{sourcecode} + +\appendix \section{All Acronyms Used in this Documentation}\label{sec:documentation_acronyms} \begin{sourcecode} diff --git a/Master/texmf-dist/tex/latex/acro/acro.sty b/Master/texmf-dist/tex/latex/acro/acro.sty index b53f44f44cb..0bf51f6373b 100644 --- a/Master/texmf-dist/tex/latex/acro/acro.sty +++ b/Master/texmf-dist/tex/latex/acro/acro.sty @@ -31,24 +31,10 @@ \RequirePackage{expl3,l3sort,xparse,l3keys2e,xtemplate} \ProvidesExplPackage {acro} - {2015/05/10} - {1.6b} + {2015/08/16} + {2.0} {Typeset Acronyms} -% -------------------------------------------------------------------------- -% check expl3 version: -\@ifpackagelater { expl3 } { 2012/11/21 } - { } - { - \PackageError {acro} { Support~package~expl3~too~old } - { - You~need~to~update~your~installation~of~the~bundles~'l3kernel'~and~ - 'l3packages'.\MessageBreak - Loading~acro~will~abort! - } - \tex_endinput:D - } - % -------------------------------------------------------------------------- % warning and error messages: \msg_new:nnn {acro} {undefined} @@ -77,69 +63,75 @@ I~encourage~you~to~remove~it~from~your~document. } -% message macros: -\bool_new:N \l__acro_silence_bool - -\cs_new_protected:Npn \acro_serious_message:nn +\msg_new:nnn {acro} {substitute-short} { - \bool_if:NTF \l__acro_silence_bool - { \msg_warning:nn } - { \msg_error:nn } + No~ short~ form~ set~ for~ acronym~ `#1'.~ Setting~ the~ short~ form~ + equal~ to~ the~ ID~ `#1'.~ If~ that~ is~ not~ what~ you~ want~ add~ an~ + explicit~ short~ form. } - -\cs_new_protected:Npn \acro_serious_message:nnn +\msg_new:nnn {acro} {ending-exists} { - \bool_if:NTF \l__acro_silence_bool - { \msg_warning:nnn } - { \msg_error:nnn } + An~ ending~ with~ the~ name~ `#1'~ already~ exists.~ I'm~ doing~ nothing. } -\cs_new_protected:Npn \acro_serious_message:nnnn +\msg_new:nnn {acro} {ending-before-acronyms} { - \bool_if:NTF \l__acro_silence_bool - { \msg_warning:nnnn } - { \msg_error:nnnn } + You~ are~ using~ \token_to_str:N \ProvideAcroEnding \c_space_tl after~ + you've~ declared~ at~ least~ one~ acronym.~ This~ will~ lead~ to~ + trouble!~ Define~ endings~ before~ any~ acronym~ declarations! } -\cs_new_protected:Npn \acro_harmless_message:nnn +\msg_new:nnn {acro} {no-alternative} { - \bool_if:NTF \l__acro_silence_bool - { \msg_info:nnn } - { \msg_warning:nnn } + There~ is~ no~ alternative~ form~ for~ acronym~ `#1'.~ Using~ the~ short~ + form~ instead. } -\cs_new_protected:Npn \acro_harmless_message:nnnn - { - \bool_if:NTF \l__acro_silence_bool - { \msg_info:nnnn } - { \msg_warning:nnnn } - } +% message macros: +\bool_new:N \l__acro_silence_bool + +\cs_new:Npn \__acro_remove_backslash:N #1 + { \exp_after:wN \use_none:n \token_to_str:N #1 } -\cs_new_protected:Npn \acro_harmless_message:nnnnn +\cs_new_protected:Npn \acro_new_message_commands:Nnnn #1#2#3#4 { - \bool_if:NTF \l__acro_silence_bool - { \msg_info:nnnnn } - { \msg_warning:nnnnn } + \clist_map_inline:nn {#2} + { + \cs_new_protected:cpn { \__acro_remove_backslash:N #1 ##1 } + { + \bool_if:NTF \l__acro_silence_bool + { \use:c { \__acro_remove_backslash:N #3 n##1 } {acro} } + { \use:c { \__acro_remove_backslash:N #4 n##1 } {acro} } + } + } } +\acro_new_message_commands:Nnnn \acro_serious_message: {n,nn,nnn} + { \msg_warning: } + { \msg_error: } + +\acro_new_message_commands:Nnnn \acro_harmless_message: {n,nn,nnn,nnnn} + { \msg_info: } + { \msg_warning: } + \cs_new_protected:Npn \acro_option_deprecated:nn #1#2 { \tl_if_blank:nTF {#2} - { \acro_harmless_message:nnnn {acro} {deprecated} {option} {#1 } } - { \acro_harmless_message:nnnnn {acro} {replaced} {option} {#1} {#2} } + { \acro_harmless_message:nnn {deprecated} {option} {#1} } + { \acro_harmless_message:nnnn {replaced} {option} {#1} {#2} } } +\cs_new_protected:Npn \acro_option_deprecated:n #1 + { \cs_new_protected:Npn \acro_option_deprecated:nn {#1} {} } \cs_new_protected:Npn \acro_command_deprecated:NN #1#2 { \tl_if_blank:nTF {#2} { - \acro_harmless_message:nnnnn {acro} {deprecated} - {command} + \acro_harmless_message:nnn {deprecated} {command} { \token_to_str:N #1 } } { - \acro_harmless_message:nnnnn {acro} {replaced} - {command} + \acro_harmless_message:nnnn {replaced} {command} { \token_to_str:N #1 } { \token_to_str:N #2 } } @@ -161,12 +153,15 @@ % -------------------------------------------------------------------------- % variants of kernel commands -\cs_generate_variant:Nn \quark_if_no_value:nTF { V } -\cs_generate_variant:Nn \tl_put_right:Nn { NV } -\cs_generate_variant:Nn \tl_if_eq:nnT { V } -\cs_generate_variant:Nn \tl_if_eq:nnF { V } -\cs_generate_variant:Nn \seq_use:Nnnn { c } -\cs_generate_variant:Nn \seq_gset_split:Nnn { c } +\cs_generate_variant:Nn \quark_if_no_value:nTF { V } +\cs_generate_variant:Nn \tl_put_right:Nn { NV, Nv } +\cs_generate_variant:Nn \tl_if_eq:nnT { V } +\cs_generate_variant:Nn \tl_if_eq:nnF { V } +\cs_generate_variant:Nn \seq_use:Nnnn { c } +\cs_generate_variant:Nn \seq_gset_split:Nnn { c } +\cs_generate_variant:Nn \prop_put:Nnn { NnV, cnx, cnv } +\cs_generate_variant:Nn \prop_get:NnNF { cn, cnc } +\cs_generate_variant:Nn \cs_generate_variant:Nn { c } % -------------------------------------------------------------------------- % boolean variables: @@ -175,7 +170,6 @@ \bool_new:N \l__acro_use_single_bool \bool_new:N \l__acro_print_only_used_bool \bool_set_true:N \l__acro_print_only_used_bool -\bool_new:N \l__acro_use_plural_bool \bool_new:N \l__acro_hyperref_loaded_bool \bool_new:N \l__acro_use_hyperref_bool \bool_new:N \l__acro_custom_format_bool @@ -193,6 +187,7 @@ \bool_new:N \l__acro_citation_all_bool \bool_new:N \l__acro_citation_first_bool \bool_set_true:N \l__acro_citation_first_bool +\bool_new:N \l__acro_group_citation_bool \bool_new:N \l__acro_acc_supp_bool \bool_new:N \l__acro_following_page_bool \bool_new:N \l__acro_following_pages_bool @@ -214,11 +209,14 @@ \bool_new:N \l__acro_place_label_bool \bool_new:N \l__acro_list_all_pages_bool \bool_set_true:N \l__acro_list_all_pages_bool +\bool_new:N \g__acro_first_acronym_declared_bool +\bool_new:N \l__acro_include_endings_format_bool % -------------------------------------------------------------------------- % token list variables: \tl_new:N \l__acro_ignore_tl \tl_new:N \l__acro_short_format_tl +\tl_new:N \l__acro_alt_format_tl \tl_new:N \l__acro_list_short_format_tl \tl_new:N \l__acro_long_format_tl \tl_new:N \l__acro_first_long_format_tl @@ -254,17 +252,14 @@ \tl_new:N \l__acro_list_name_tl \tl_set:Nn \l__acro_list_name_tl { Acronyms } \tl_new:N \l__acro_short_tl -\tl_new:N \l__acro_short_plural_tl -\tl_new:N \l__acro_default_plural_tl -\tl_set:Nn \l__acro_default_plural_tl { s } \tl_new:N \l__acro_alt_tl \tl_new:N \l__acro_long_tl \tl_new:N \l__acro_long_pre_tl \tl_new:N \l__acro_long_post_tl \tl_new:N \l__acro_custom_format_tl \tl_new:N \l__acro_first_between_tl -\tl_new:N \l__acro_citation_space_tl -\tl_set:Nn \l__acro_citation_space_tl { \nobreakspace } +\tl_new:N \l__acro_citation_connect_tl +\tl_new:N \l__acro_between_group_connect_citation_tl \tl_new:N \l__acro_extra_brackets_tl \tl_new:N \l__acro_extra_punct_tl \tl_new:N \l__acro_first_brackets_tl @@ -280,6 +275,8 @@ \tl_new:N \l__acro_acc_supp_options_tl \tl_new:N \l__acro_label_prefix_tl \tl_set:Nn \l__acro_label_prefix_tl { ac: } +\tl_new:N \l__acro_single_form_tl +\tl_set:Nn \l__acro_single_form_tl {long} % -------------------------------------------------------------------------- % length variables: @@ -292,7 +289,7 @@ \cs_new:Npn \acro_no_break: { \tex_penalty:D \c_ten_thousand } \cs_new_protected:Npn \__acro_first_upper_case:n #1 - { \tl_mixed_case:n {#1} } + { \tl_upper_case:n { \tl_head:n {#1} } \tl_tail:n {#1} } \cs_generate_variant:Nn \__acro_first_upper_case:n { x } \cs_generate_variant:Nn \tl_mixed_case:n { x } @@ -305,94 +302,133 @@ % options: \keys_define:nn {acro} { - version .code:n = - \acro_option_deprecated:nn { version } { } , + version .code:n = \acro_option_deprecated:n {version} , messages .choice: , messages / silent .code:n = \bool_set_true:N \l__acro_silence_bool , - messages / loud .code:n = + messages / loud .code:n = \bool_set_false:N \l__acro_silence_bool , - accsupp .bool_set:N = \l__acro_acc_supp_bool , - accsupp-options .tl_set:N = \l__acro_acc_supp_options_tl , - macros .bool_set:N = \l__acro_create_macros_bool , - xspace .bool_set:N = \l__acro_xspace_bool , - strict .bool_set:N = \l__acro_strict_bool , - sort .bool_set:N = \l__acro_sort_bool , + messages .value_required:n = true , + accsupp .bool_set:N = \l__acro_acc_supp_bool , + accsupp-options .tl_set:N = \l__acro_acc_supp_options_tl , + macros .bool_set:N = \l__acro_create_macros_bool , + xspace .bool_set:N = \l__acro_xspace_bool , + strict .bool_set:N = \l__acro_strict_bool , + sort .bool_set:N = \l__acro_sort_bool , short-format .code:n = \tl_set:Nn \l__acro_short_format_tl {#1} - \tl_set:Nn \l__acro_list_short_format_tl {#1} , + \tl_set_eq:NN \l__acro_alt_format_tl \l__acro_short_format_tl + \tl_set:Nn \l__acro_list_short_format_tl {#1} , + short-format .value_required:n = true , long-format .code:n = \tl_set:Nn \l__acro_long_format_tl {#1} \tl_set:Nn \l__acro_first_long_format_tl {#1} - \tl_set:Nn \l__acro_list_long_format_tl {#1} , + \tl_set:Nn \l__acro_list_long_format_tl {#1} , + long-format .value_required:n = true , first-long-format .code:n = - \tl_set:Nn \l__acro_first_long_format_tl {#1} , - display-foreign .bool_set:N = \l__acro_foreign_bool , - foreign-format .tl_set:N = \l__acro_foreign_format_tl , - list-short-format .tl_set:N = \l__acro_list_short_format_tl , - list-long-format .tl_set:N = \l__acro_list_long_format_tl , + \tl_set:Nn \l__acro_first_long_format_tl {#1} , + first-long-format .value_required:n = true , + format-include-endings .bool_set:N = \l__acro_include_endings_format_bool , + display-foreign .bool_set:N = \l__acro_foreign_bool , + foreign-format .tl_set:N = \l__acro_foreign_format_tl , + foreign-format .value_required:n = true , + list-short-format .tl_set:N = \l__acro_list_short_format_tl , + list-short-format .value_required:n = true , + list-long-format .tl_set:N = \l__acro_list_long_format_tl , + list-long-format .value_required:n = true , list-foreign-format .tl_set:N = \l__acro_foreign_list_format_tl , - extra-format .tl_set:N = \l__acro_extra_format_tl , - single .bool_set:N = \l__acro_use_single_bool , - first-style .tl_set:N = \l__acro_first_instance_tl , - extra-style .tl_set:N = \l__acro_extra_instance_tl , - label .bool_set:N = \l__acro_place_label_bool , - label-prefix .tl_set:N = \l__acro_label_prefix_tl , + list-foreign-format .value_required:n = true , + extra-format .tl_set:N = \l__acro_extra_format_tl , + extra-format .value_required:n = true , + single .bool_set:N = \l__acro_use_single_bool , + single-form .tl_set:N = \l__acro_single_form_tl , + single-form .value_required:n = true , + first-style .tl_set:N = \l__acro_first_instance_tl , + first-style .value_required:n = true , + extra-style .tl_set:N = \l__acro_extra_instance_tl , + extra-style .value_required:n = true , + label .bool_set:N = \l__acro_place_label_bool , + label-prefix .tl_set:N = \l__acro_label_prefix_tl , + label-prefix .value_required:n = true , pages .choice: , pages / all .code:n = - \bool_set_true:N \l__acro_list_all_pages_bool , + \bool_set_true:N \l__acro_list_all_pages_bool , pages / first .code:n = \bool_set_true:N \l__acro_place_label_bool - \bool_set_false:N \l__acro_list_all_pages_bool , - page-ref .tl_set:N = \l__acro_page_instance_tl , - page-name .tl_set:N = \l__acro_page_name_tl , - pages-name .tl_set:N = \l__acro_pages_name_tl , + \bool_set_false:N \l__acro_list_all_pages_bool , + pages .value_required:n = true , + page-ref .tl_set:N = \l__acro_page_instance_tl , + page-ref .value_required:n = true , + page-name .tl_set:N = \l__acro_page_name_tl , + page-name .value_required:n = true , + pages-name .tl_set:N = \l__acro_pages_name_tl , + pages-name .value_required:n = true , page-ranges .code:n = \bool_set_false:N \l__acro_following_page_bool \bool_set_false:N \l__acro_following_pages_bool - \acro_option_deprecated:nn { pages-ranges } { } , - following-page .bool_set:N = \l__acro_following_page_bool , - following-pages .bool_set:N = \l__acro_following_pages_bool , - record-pages .code:n = - \acro_option_deprecated:nn { record-pages } { } , - next-page .tl_set:N = \l__acro_next_page_tl , - next-pages .tl_set:N = \l__acro_next_pages_tl , - list-style .tl_set:N = \l__acro_list_instance_tl , - list-type .tl_set:N = \l__acro_list_type_tl , + \acro_option_deprecated:n {pages-ranges} , + following-page .bool_set:N = \l__acro_following_page_bool , + following-pages .bool_set:N = \l__acro_following_pages_bool , + record-pages .code:n = \acro_option_deprecated:n {record-pages} , + next-page .tl_set:N = \l__acro_next_page_tl , + next-page .value_required:n = true , + next-pages .tl_set:N = \l__acro_next_pages_tl , + next-pages .value_required:n = true , + list-style .tl_set:N = \l__acro_list_instance_tl , + list-style .value_required:n = true , + list-type .tl_set:N = \l__acro_list_type_tl , + list-type .value_required:n = true , list-header .code:n = - \acro_option_deprecated:nn { list-header } { list-heading } - \tl_set:Nn \l__acro_list_title_tl {#1} , - list-heading .tl_set:N = \l__acro_list_title_tl , - list-name .tl_set:N = \l__acro_list_name_tl , - list-table-width .dim_set:N = \l__acro_table_width_dim , - hyperref .bool_set:N = \l__acro_use_hyperref_bool , - only-used .bool_set:N = \l__acro_print_only_used_bool , + \acro_option_deprecated:nn {list-header} {list-heading} + \tl_set:Nn \l__acro_list_title_tl {#1} , + list-heading .tl_set:N = \l__acro_list_title_tl , + list-heading .value_required:n = true , + list-name .tl_set:N = \l__acro_list_name_tl , + list-name .value_required:n = true , + list-table-width .dim_set:N = \l__acro_table_width_dim , + list-table-width .value_required:n = true , + hyperref .bool_set:N = \l__acro_use_hyperref_bool , + only-used .bool_set:N = \l__acro_print_only_used_bool , mark-as-used .choice: , mark-as-used / first .code:n = - \bool_gset_true:N \g__acro_mark_first_as_used_bool , + \bool_gset_true:N \g__acro_mark_first_as_used_bool , mark-as-used / any .code:n = - \bool_gset_false:N \g__acro_mark_first_as_used_bool , - plural-ending .tl_set:N = \l__acro_default_plural_tl , - list-caps .bool_set:N = \l__acro_capitalize_list_bool , - cite .choice: , + \bool_gset_false:N \g__acro_mark_first_as_used_bool , + mark-as-used .default:n = any , + list-caps .bool_set:N = \l__acro_capitalize_list_bool , + cite .choice: , cite / all .code:n = \bool_set_true:N \l__acro_citation_all_bool - \bool_set_true:N \l__acro_citation_first_bool , + \bool_set_true:N \l__acro_citation_first_bool , cite / none .code:n = \bool_set_false:N \l__acro_citation_all_bool - \bool_set_false:N \l__acro_citation_first_bool , + \bool_set_false:N \l__acro_citation_first_bool , cite / first .code:n = \bool_set_false:N \l__acro_citation_all_bool - \bool_set_true:N \l__acro_citation_first_bool , -% cite .default:n = all , + \bool_set_true:N \l__acro_citation_first_bool , + cite .default:n = all , cite-cmd .code:n = - \cs_set:Npn \__acro_citation_cmd:w {#1} , - cite-space .tl_set:N = \l__acro_citation_space_tl , - index .bool_set:N = \l__acro_addto_index_bool , + \cs_set:Npn \__acro_citation_cmd:w {#1} , + cite-cmd .value_required:n = true , + group-cite-cmd .code:n = + \cs_set:Npn \__acro_group_citation_cmd:w {#1} , + group-cite-cmd .value_required:n = true , + group-citation .bool_set:N = \l__acro_group_citation_bool , + cite-connect .tl_set:N = \l__acro_citation_connect_tl , + cite-connect .initial:n = \nobreakspace , + cite-connect .value_required:n = true , + cite-space .code:n = + \acro_option_deprecated:nn {cite-space} {cite-connect} , + group-cite-connect .tl_set:N = \l__acro_between_group_connect_citation_tl , + group-cite-connect .initial:n = {,\nobreakspace} , + group-cite-connect .value_required:n = true , + index .bool_set:N = \l__acro_addto_index_bool , index-cmd .code:n = \cs_set:Npn \__acro_index_cmd:n {#1} , + index-cmd .value_required:n = true , uc-cmd .code:n = - \cs_set_eq:NN \__acro_first_upper_case:n #1 + \cs_set_eq:NN \__acro_first_upper_case:n #1 , + uc-cmd .value_required:n = true } \AtBeginDocument @@ -415,32 +451,42 @@ { \keys_set:nn {acro} {#1} \ignorespaces } % -------------------------------------------------------------------------- -\cs_new_protected:Npn \acro_plural: - { \bool_set_true:N \l__acro_use_plural_bool } - -\cs_new_protected:Npn \acro_upper: - { \bool_set_true:N \l__acro_first_upper_bool } - % typeset the short form: -\cs_new:Npn \__acro_write_short:n #1 +% #1: ID +% #2: short form +\cs_new_protected:Npn \acro_write_short:nn #1#2 { \mode_if_horizontal:F { \leavevmode } \group_begin: \bool_if:NTF \l__acro_custom_format_bool { \l__acro_custom_format_tl } { \l__acro_short_format_tl } - { #1 } + {#2} \group_end: - \bool_if:NT \l__acro_use_plural_bool - { \tl_use:N \l__acro_short_plural_tl } } -\cs_generate_variant:Nn \__acro_write_short:n { V } +\cs_generate_variant:Nn \acro_write_short:nn { nV , nv } + +% #1: ID +% #2: alt form +\cs_new_protected:Npn \acro_write_alt:nn #1#2 + { + \mode_if_horizontal:F { \leavevmode } + \group_begin: + \bool_if:NTF \l__acro_custom_format_bool + { \l__acro_custom_format_tl } + { \l__acro_alt_format_tl } + {#2} + \group_end: + } +\cs_generate_variant:Nn \acro_write_alt:nn { nV , nv } % typeset the longform,...: % TODO: rethink the formatting mechanism % right now a custom format gets applied additionally to the global one % although before it -\cs_new_protected:Npn \__acro_write_long:Nn #1#2 +% #1: tl holding format +% #2: long form +\cs_new_protected:Npn \acro_write_long:Nn #1#2 { \mode_if_horizontal:F { \leavevmode } \group_begin: @@ -457,7 +503,7 @@ } \group_end: } -\cs_generate_variant:Nn \__acro_write_long:Nn { NV,No,Nf } +\cs_generate_variant:Nn \acro_write_long:Nn { NV,No,Nf } % -------------------------------------------------------------------------- % hyperref support @@ -474,21 +520,25 @@ } } -\cs_new_protected:Npn \__acro_make_link:nNN #1#2#3 +% #1: tl var +% #2: id +% #3: text +\cs_new_protected:Npn \__acro_make_link:Nnn #1#2#3 { \bool_if:nTF { \l__acro_use_hyperref_bool && \l__acro_hyperref_loaded_bool } { - \tl_set:Nn #2 + \tl_set:Nn #1 { - \acro_hyper_link:nn {#1} { \phantom {#3} } - \__acro_is_single:nTF {#1} + \acro_hyper_link:nn {#2} { \phantom {#3} } + \acro_if_is_single:nTF {#2} { \hbox_overlap_left:n {#3} } { \acro_color_link:n { \hbox_overlap_left:n {#3} } } } } - { \tl_set:Nn #2 {#3} } + { \tl_set:Nn #1 {#3} } } +\cs_generate_variant:Nn \__acro_make_link:Nnn {NnV} \cs_new:Npn \acro_color_link:n #1 { @@ -545,13 +595,14 @@ \AssignTemplateKeys \bool_if:nT { !\l__acro_first_only_short_bool && !\l__acro_first_reversed_bool } { - \__acro_indefinite:nn {#1} { long } - \__acro_write_long:No \l__acro_first_long_format_tl {#3} - \tl_use:N \c_space_tl + \acro_write_indefinite:nn {#1} {long} + \acro_write_long:No \l__acro_first_long_format_tl {#3} + \acro_endings:nn {#1} {long} + \acro_space: \tl_if_blank:VF \l__acro_first_between_tl { \tl_use:N \l__acro_first_between_tl - \tl_use:N \c_space_tl + \acro_space: } } \bool_if:nT @@ -575,41 +626,58 @@ } \bool_if:nT { \l__acro_first_reversed_bool || \l__acro_first_only_short_bool } - { \__acro_indefinite:nn {#1} { short } } - \__acro_acc_supp:nn {#1} { \__acro_write_short:n {#2} } + { \acro_write_indefinite:nn {#1} {short} } + \group_begin: + \bool_if:nT + { !\l__acro_first_reversed_bool && !\l__acro_first_only_short_bool } + { + \prop_map_inline:Nn \l__acro_trailing_tokens_prop + { \acro_deactivate_trailing_action:n {##1} } + } + \acro_acc_supp:nn {#1} { \acro_write_short:nn {#1} {#2} } + \acro_endings:nn {#1} {short} + \group_end: + \bool_if:nT + { \l__acro_group_citation_bool && !\l__acro_first_reversed_bool } + { \acro_group_cite:n {#1} } \bool_if:nT { \l__acro_first_use_brackets_bool && !\l__acro_first_reversed_bool } { \tl_tail:N \l__acro_first_brackets_tl } - \bool_if:nT - { !\l__acro_first_only_short_bool && \l__acro_first_reversed_bool } + \bool_if:NT \l__acro_first_reversed_bool { - \tl_if_blank:VF \l__acro_first_between_tl + \bool_if:NF \l__acro_first_only_short_bool { + \tl_if_blank:VF \l__acro_first_between_tl + { + \tl_use:N \c_space_tl + \tl_use:N \l__acro_first_between_tl + } \tl_use:N \c_space_tl - \tl_use:N \l__acro_first_between_tl - } - \tl_use:N \c_space_tl - \bool_if:nT - { \l__acro_first_use_brackets_bool && \l__acro_first_reversed_bool } - { \tl_head:N \l__acro_first_brackets_tl } - \__acro_write_long:No \l__acro_first_long_format_tl {#3} - \bool_if:nT { \l__acro_foreign_bool && \l__acro_first_reversed_bool } - { - \prop_get:NnNT \l__acro_foreign_prop {#1} \l__acro_foreign_tl + \bool_if:NT \l__acro_first_use_brackets_bool + { \tl_head:N \l__acro_first_brackets_tl } + \acro_write_long:No \l__acro_first_long_format_tl {#3} + \bool_if:NT \l__acro_foreign_bool { - \tl_use:N \l__acro_foreign_sep_tl - \group_begin: - \tl_use:N \l__acro_foreign_format_tl - \tl_use:N \l__acro_foreign_tl - \group_end: + \prop_get:NnNT \l__acro_foreign_prop {#1} \l__acro_foreign_tl + { + \tl_use:N \l__acro_foreign_sep_tl + \group_begin: + \tl_use:N \l__acro_foreign_format_tl + \tl_use:N \l__acro_foreign_tl + \group_end: + } } } \bool_if:nT - { \l__acro_first_use_brackets_bool && \l__acro_first_reversed_bool } + { \l__acro_group_citation_bool && !\l__acro_first_reversed_bool } + { \acro_group_cite:n {#1} } + \bool_if:nT + { \l__acro_first_use_brackets_bool && !\l__acro_first_only_short_bool } { \tl_tail:N \l__acro_first_brackets_tl } } - \__acro_cite_if:Nn \l__acro_citation_first_bool {#1} - \__acro_index_if:Nn \l__acro_addto_index_bool {#1} + \bool_if:NF \l__acro_group_citation_bool + { \acro_cite_if:Nn \l__acro_citation_first_bool {#1} } + \acro_index_if:Nn \l__acro_addto_index_bool {#1} } % template for footnotes, sidenotes, ... @@ -628,13 +696,13 @@ } { \AssignTemplateKeys - \__acro_indefinite:nn {#1} { short } - \__acro_acc_supp:nn {#1} { \__acro_write_short:n {#2} } + \acro_write_indefinite:nn {#1} {short} + \acro_acc_supp:nn {#1} { \acro_write_short:nn {#1} {#2} } \bool_if:NT \l__acro_use_note_bool { \__acro_note_command:n { - \__acro_write_long:No \l__acro_first_long_format_tl {#3} + \acro_write_long:No \l__acro_first_long_format_tl {#3} \bool_if:NT \l__acro_foreign_bool { \prop_get:NnNT \l__acro_foreign_prop {#1} \l__acro_foreign_tl @@ -648,8 +716,8 @@ ) } } - \__acro_cite_if:Nn \l__acro_citation_first_bool {#1} - \__acro_index_if:Nn \l__acro_addto_index_bool {#1} + \acro_cite_if:Nn \l__acro_citation_first_bool {#1} + \acro_index_if:Nn \l__acro_addto_index_bool {#1} } } } @@ -727,7 +795,7 @@ { \tl_use:N \l__acro_extra_punct_tl \tl_use:N \c_space_tl } \bool_if:NT \l__acro_extra_use_brackets_bool { \tl_head:N \l__acro_extra_brackets_tl } - \__acro_write_long:Nn \l__acro_extra_format_tl {#1} + \acro_write_long:Nn \l__acro_extra_format_tl {#1} \bool_if:NT \l__acro_extra_use_brackets_bool { \tl_tail:N \l__acro_extra_brackets_tl } } @@ -963,12 +1031,12 @@ % the title of the list: \cs_new:Npn \acro_list_title_format:n #1 {#1} -\DeclareObjectType { acro-title } { 1 } +\DeclareObjectType {acro-title} {1} -\DeclareTemplateInterface { acro-title } { sectioning } { 1 } +\DeclareTemplateInterface {acro-title} {sectioning} {1} { name-format : function 1 = #1 } -\DeclareTemplateCode { acro-title } { sectioning } { 1 } +\DeclareTemplateCode {acro-title} {sectioning} {1} { name-format = \acro_list_title_format:n } { \AssignTemplateKeys @@ -976,27 +1044,31 @@ } % the different styles: -\DeclareInstance { acro-title } { chapter* } { sectioning } +\DeclareInstance {acro-title} {chapter*} {sectioning} { name-format = \chapter* {#1} } -\DeclareInstance { acro-title } { part* } { sectioning } +\DeclareInstance {acro-title} {part*} {sectioning} { name-format = \part* {#1} } -\DeclareInstance { acro-title } { section* } { sectioning } +\DeclareInstance {acro-title} {section*} {sectioning} { name-format = \section* {#1} } -\DeclareInstance { acro-title } { subsection* } { sectioning } +\DeclareInstance {acro-title} {subsection*} {sectioning} { name-format = \subsection* {#1} } -\DeclareInstance { acro-title } { chapter } { sectioning } +\DeclareInstance {acro-title} {subsubsection*} {sectioning} + { name-format = \subsubsection* {#1} } +\DeclareInstance {acro-title} {chapter} {sectioning} { name-format = \chapter {#1} } -\DeclareInstance { acro-title } { part } { sectioning } +\DeclareInstance {acro-title} {part} {sectioning} { name-format = \part {#1} } -\DeclareInstance { acro-title } { section } { sectioning } +\DeclareInstance {acro-title} {section} {sectioning} { name-format = \section {#1} } -\DeclareInstance { acro-title } { subsection } { sectioning } +\DeclareInstance {acro-title} {subsection} {sectioning} { name-format = \subsection {#1} } -\DeclareInstance { acro-title } { addchap } { sectioning } +\DeclareInstance {acro-title} {subsubsection} {sectioning} + { name-format = \subsubsection {#1} } +\DeclareInstance {acro-title} {addchap} {sectioning} { name-format = \addchap {#1} } -\DeclareInstance { acro-title } { addsec } { sectioning } +\DeclareInstance {acro-title} {addsec} {sectioning} { name-format = \addsec {#1} } -\DeclareInstance { acro-title } { none } { sectioning } +\DeclareInstance {acro-title} {none} {sectioning} { name-format = \use_none:n {#1} } % -------------------------------------------------------------------------- @@ -1124,21 +1196,21 @@ \acro_hyper_target:nn {##1} { - \__acro_acc_supp:nn + \acro_acc_supp:nn {##1} - { \__acro_write_short:n { \l__acro_list_short_format_tl { ##2 } } } + { \acro_write_short:nn {##1} { \l__acro_list_short_format_tl {##2} } } } ] } \cs_set:Npn \acro_print_list_long:n ##1 { - \__acro_write_long:Nf \l__acro_list_long_format_tl + \acro_write_long:Nf \l__acro_list_long_format_tl { \prop_if_in:NnTF \l__acro_list_prop {##1} - { \prop_get:Nn \l__acro_list_prop {##1} } - { \prop_get:Nn \l__acro_long_prop {##1} } + { \prop_item:Nn \l__acro_list_prop {##1} } + { \prop_item:Nn \l__acro_long_prop {##1} } } - \__acro_cite_if:Nn \l__acro_citation_all_bool {##1} + \acro_cite_if:Nn \l__acro_citation_all_bool {##1} } \cs_set_protected:Npn \acro_print_list_extra:n ##1 { @@ -1180,21 +1252,21 @@ \acro_hyper_target:nn {##1} { - \__acro_acc_supp:nn + \acro_acc_supp:nn {##1} - { \__acro_write_short:n { \l__acro_list_short_format_tl { ##2 } } } + { \acro_write_short:nn {##1} { \l__acro_list_short_format_tl {##2} } } } & } \cs_set:Npn \acro_print_list_long:n ##1 { - \__acro_write_long:Nf \l__acro_list_long_format_tl + \acro_write_long:Nf \l__acro_list_long_format_tl { \prop_if_in:NnTF \l__acro_list_prop {##1} - { \prop_get:Nn \l__acro_list_prop {##1} } - { \prop_get:Nn \l__acro_long_prop {##1} } + { \prop_item:Nn \l__acro_list_prop {##1} } + { \prop_item:Nn \l__acro_long_prop {##1} } } - \__acro_cite_if:Nn \l__acro_citation_all_bool {##1} + \acro_cite_if:Nn \l__acro_citation_all_bool {##1} } \cs_set_protected:Npn \acro_print_list_extra:n ##1 { @@ -1210,9 +1282,14 @@ { \UseInstance { acro-page-number } { \l__acro_page_instance_tl } {##1} } \tabularnewline } - \exp_args:Noo \begin { \l__acro_list_table_tl } { \l__acro_list_table_spec_tl } - \acro_list_allow_items:nn {#2} {#3} - \exp_args:No \end { \l__acro_list_table_tl } + % \exp_args:Noo \begin { \l__acro_list_table_tl } { \l__acro_list_table_spec_tl } + % \acro_list_allow_items:nn {#2} {#3} + % \exp_args:No \end { \l__acro_list_table_tl } + \use:x { + \exp_not:N \begin { \exp_not:V \l__acro_list_table_tl } { \exp_not:V \l__acro_list_table_spec_tl } + \exp_not:n { \acro_list_allow_items:nn {#2} {#3} } + \exp_not:N \end { \exp_not:V \l__acro_list_table_tl } + } } % extra-table template: @@ -1235,21 +1312,21 @@ \acro_hyper_target:nn {##1} { - \__acro_acc_supp:nn + \acro_acc_supp:nn {##1} - { \__acro_write_short:n { \l__acro_list_short_format_tl { ##2 } } } + { \acro_write_short:nn {##1} { \l__acro_list_short_format_tl {##2} } } } & } \cs_set:Npn \acro_print_list_long:n ##1 { - \__acro_write_long:Nf \l__acro_list_long_format_tl + \acro_write_long:Nf \l__acro_list_long_format_tl { \prop_if_in:NnTF \l__acro_list_prop {##1} - { \prop_get:Nn \l__acro_list_prop {##1} } - { \prop_get:Nn \l__acro_long_prop {##1} } + { \prop_item:Nn \l__acro_list_prop {##1} } + { \prop_item:Nn \l__acro_long_prop {##1} } } - \__acro_cite_if:Nn \l__acro_citation_all_bool {##1} + \acro_cite_if:Nn \l__acro_citation_all_bool {##1} & } \cs_set_protected:Npn \acro_print_list_extra:n ##1 @@ -1267,9 +1344,11 @@ { \UseInstance { acro-page-number } { \l__acro_page_instance_tl } {##1} } \tabularnewline } - \exp_args:Noo \begin { \l__acro_list_table_tl } { \l__acro_list_table_spec_tl } + \exp_args:Noo + \begin { \l__acro_list_table_tl } { \l__acro_list_table_spec_tl } \acro_list_allow_items:nn {#2} {#3} - \exp_args:No \end { \l__acro_list_table_tl } + \exp_args:No + \end { \l__acro_list_table_tl } } % extra-table-rev template: @@ -1291,20 +1370,20 @@ { \acro_hyper_target:nn {##1} - { \__acro_acc_supp:nn {##1} { \__acro_write_short:n { ##2 } } } + { \acro_acc_supp:nn {##1} { \acro_write_short:nn {##1} {##2} } } & } \cs_set_protected:Npn \acro_print_list_extra:n ##1 { \bool_if:NT \l__acro_capitalize_list_bool { \bool_set_true:N \l__acro_first_upper_bool } - \__acro_write_long:Nf \l__acro_long_format_tl + \acro_write_long:Nf \l__acro_long_format_tl { \prop_if_in:NnTF \l__acro_list_prop {##1} - { \prop_get:Nn \l__acro_list_prop {##1} } - { \prop_get:Nn \l__acro_long_prop {##1} } + { \prop_item:Nn \l__acro_list_prop {##1} } + { \prop_item:Nn \l__acro_long_prop {##1} } } - \__acro_cite_if:Nn \l__acro_citation_all_bool {##1} + \acro_cite_if:Nn \l__acro_citation_all_bool {##1} & } \cs_set_protected:Npn \acro_print_list_long:n ##1 @@ -1360,20 +1439,18 @@ \acro_is_used:nTF {#1} { % this is not the first time - \__acro_indefinite:nn {#1} {short} - \__acro_acc_supp:nn + \acro_write_indefinite:nn {#1} {short} + \acro_acc_supp:nn {#1} - { \__acro_write_short:V \l__acro_short_tl } + { \acro_write_short:nV {#1} \l__acro_short_tl } + \acro_endings:nn {#1} {short} \acro_after:n {#1} } { % this is the first time \bool_gset_true:c { g__acro_#1_first_use_bool } - \__acro_is_single:nTF {#1} - { - \__acro_indefinite:nn {#1} {long} - \__acro_write_long:NV \l__acro_long_format_tl \l__acro_long_tl - } + \acro_if_is_single:nTF {#1} + { \acro_single:n {#1} } { \UseInstance {acro-first} { \l__acro_first_instance_tl } {#1} @@ -1383,7 +1460,35 @@ } } -\prg_new_conditional:Npnn \__acro_is_single:n #1 { p,T,TF } +\cs_new_protected:Npn \acro_single_form:nn #1#2 + { + \acro_write_indefinite:nn {#1} {#2} + \str_case:nnF {#2} + { + {long} { + \acro_write_long:NV \l__acro_long_format_tl \l__acro_long_tl + \acro_endings:nn {#1} {#2} + \acro_cite:n {#1} + } + {first} { + \UseInstance {acro-first} { \l__acro_first_instance_tl } + {#1} + { \l__acro_short_tl } + { \l__acro_long_tl } + } + } + { + \use:c {acro_write_#2:nv} {#1} {l__acro_#2_tl} + \acro_endings:nn {#1} {#2} + \acro_cite:n {#1} + } + } +\cs_generate_variant:Nn \acro_single_form:nn {nV} + +\cs_new_protected:Npn \acro_single:n #1 + { \acro_single_form:nV {#1} \l__acro_single_form_tl } + +\prg_new_conditional:Npnn \acro_if_is_single:n #1 { p,T,TF } { \bool_if:nTF { !\l__acro_use_single_bool || \cs_if_exist_p:c { acro@#1@twice } } { \prg_return_false: } { \prg_return_true: } @@ -1397,19 +1502,23 @@ \cs_new_protected:Npn \acro_defined:n #1 { \prop_if_in:NnF \l__acro_short_prop {#1} - { \acro_serious_message:nnn {acro} {undefined} {#1} } + { \acro_serious_message:nn {undefined} {#1} } } \cs_new_protected:Npn \acro_get:n #1 { - \bool_if:NF \l__acro_in_list_bool - { \leavevmode } - % \acro_defined:n {#1} + \bool_if:NF \l__acro_in_list_bool { \leavevmode } \__acro_activate_hyperref_support: + % short: \prop_get:NnNF \l__acro_short_prop {#1} \l__acro_tmpa_tl {} - \__acro_make_link:nNN {#1} \l__acro_short_tl \l__acro_tmpa_tl - \prop_get:NnNF \l__acro_short_plural_prop {#1} \l__acro_short_plural_tl {} + \__acro_make_link:NnV \l__acro_short_tl {#1} \l__acro_tmpa_tl + % alt: + \prop_get:NnNTF \l__acro_alt_prop {#1} \l__acro_tmpa_tl + { \__acro_make_link:NnV \l__acro_alt_tl {#1} \l__acro_tmpa_tl } + { \tl_set_eq:NN \l__acro_alt_tl \l__acro_short_tl } + % long: \prop_get:NnNF \l__acro_long_prop {#1} \l__acro_long_tl {} + % formatting \prop_get:NnNTF \l__acro_long_format_prop {#1} \l__acro_custom_long_format_tl { \bool_set_true:N \l__acro_custom_long_format_bool } @@ -1417,31 +1526,193 @@ \prop_get:NnNF \l__acro_first_long_format_prop {#1} \l__acro_first_long_format_tl {}% to avoid hanging compilation if first-long-format hasn't been set - \prop_get:NnNT \l__acro_long_pre_prop {#1} \l__acro_long_pre_tl - { \tl_put_left:NV \l__acro_long_tl \l__acro_long_pre_tl } - \prop_get:NnNF \l__acro_alt_prop {#1} \l__acro_tmpb_tl {} - \__acro_make_link:nNN {#1} \l__acro_alt_tl \l__acro_tmpb_tl \prop_get:NnNTF \l__acro_format_prop {#1} \l__acro_custom_format_tl { \bool_set_true:N \l__acro_custom_format_bool } { \bool_set_false:N \l__acro_custom_format_bool } - \__acro_set_plural:n {#1} + \seq_map_inline:Nn \l__acro_endings_seq + { + \bool_if:cT {l__acro_##1_bool} + { \__acro_set_ending_for:nnn {##1} {#1} {long} } + } \prop_get:NnNT \l__acro_long_post_prop {#1} \l__acro_long_post_tl { \tl_put_right:NV \l__acro_long_tl \l__acro_long_post_tl } + \prop_get:NnNT \l__acro_long_pre_prop {#1} \l__acro_long_pre_tl + { \tl_put_left:NV \l__acro_long_tl \l__acro_long_pre_tl } + } + +% -------------------------------------------------------------------------- +% plural endings and similar concepts: +\seq_new:N \l__acro_endings_seq + +% #1: ending +% #2: ID +\cs_new_protected:Npn \__acro_set_ending:nn #1#2 + { + \bool_if:cT {l__acro_#1_bool} + { + \__acro_set_ending_for:nnn {#1} {#2} {short} + \__acro_set_ending_for:nnn {#1} {#2} {alt} + \__acro_set_ending_for:nnn {#1} {#2} {long} + } } -\cs_new_protected:Npn \__acro_set_plural:n #1 +\tl_new:N \l__acro_endings_tl + +% #1: ending +% #2: id +% #3: short|alt|long +\cs_new_protected:Npn \__acro_set_ending_for:nnn #1#2#3 { - \bool_if:NT \l__acro_use_plural_bool + \bool_if:nTF { \prop_item:cn {l__acro_#3_#1_form_prop} {#2} } + { \prop_get:cncF {l__acro_#3_#1_prop} {#2} {l__acro_#3_tl} {} } { - \bool_if:nTF { \prop_get:Nn \l__acro_long_plural_form_prop {#1} } - { \prop_get:NnNF \l__acro_long_plural_prop {#1} \l__acro_long_tl {} } + \tl_set:cx {l__acro_#3_#1_tl} + { \prop_item:cn {l__acro_#3_#1_prop} {#2} } + } + } + +\cs_new_protected:Npn \__acro_set_endings:n #1 + { + \seq_map_inline:Nn \l__acro_endings_seq + { \__acro_set_ending:nn {##1} {#1} } + } + +\cs_new_protected:Npn \acro_endings:nn #1#2 + { + \group_begin: + \bool_if:NTF \l__acro_include_endings_format_bool + { + \bool_if:NTF \l__acro_custom_format_bool + { \l__acro_custom_format_tl } + { \tl_use:c {l__acro_#2_format_tl} } + } + { \use:n } + { + \seq_map_inline:Nn \l__acro_endings_seq + { + \__acro_set_ending_for:nnn {##1} {#1} {#2} + \bool_if:cT {l__acro_##1_bool} + { \tl_use:c {l__acro_#2_##1_tl} } + } + } + \group_end: + } + +% #1: name +% #2: default short +% #3: default long +\cs_new_protected:Npn \acro_provide_ending:nnn #1#2#3 + { + \seq_if_in:NnTF \l__acro_endings_seq {#1} + { \acro_harmless_message:nn {ending-exists} {#1} } + { + % registering: + \bool_if:NT \g__acro_first_acronym_declared_bool + { \acro_serious_message:n {ending-before-acronyms} } + \seq_put_right:Nn \l__acro_endings_seq {#1} + \bool_new:c {l__acro_#1_bool} + % short variables + \acro_define_and_set_ending_variables:nnn {short} {#1} {#2} + % alt variables + \acro_define_and_set_ending_variables:nnn {alt} {#1} {#2} + % long variables + \acro_define_and_set_ending_variables:nnn {long} {#1} {#3} + % define setup command: + \tl_set:Nn \l__acro_tmpa_tl {#1} + \tl_replace_all:Nnn \l__acro_tmpa_tl {-} {_} + \cs_new_protected:cpn {acro_ \l__acro_tmpa_tl :} + { \bool_set_true:c {l__acro_#1_bool} } + % acronym properties: + % short-: + \acro_declare_key:nnn {short_#1} {short-#1} + { + \prop_put:cnn {l__acro_short_#1_form_prop} {##1} { \c_false_bool } + \prop_put:cnx {l__acro_pdfstring_short_#1_prop} + {##1} { \prop_get:Nn \l__acro_short_prop {##1} \exp_not:n {##2} } + } + % short--form: + \acro_declare_key_generic:nnn {short_#1_form} {short-#1-form} + { + \__acro_key_check:nn {##1} {short-#1-form} + \prop_put:cnn {l__acro_short_#1_form_prop} {##1} { \c_true_bool } + \prop_put:cnn {l__acro_short_#1_prop} {##1} {##2} + \prop_put:cnn {l__acro_pdfstring_short_#1_prop} {##1} {##2} + } + % alt-: + \acro_declare_key:nnn {alt_#1} {alt-#1} + { + \prop_put:cnn {l__acro_alt_#1_form_prop} {##1} { \c_false_bool } + \prop_put:cnx {l__acro_pdfstring_alt_#1_prop} + {##1} { \prop_get:Nn \l__acro_alt_prop {##1} \exp_not:n {##2} } + } + % alt--form: + \acro_declare_key_generic:nnn {alt_#1_form} {alt-#1-form} + { + \__acro_key_check:nn {##1} {alt-#1-form} + \prop_put:cnn {l__acro_alt_#1_form_prop} {##1} { \c_true_bool } + \prop_put:cnn {l__acro_alt_#1_prop} {##1} {##2} + \prop_put:cnn {l__acro_pdfstring_alt_#1_prop} {##1} {##2} + } + % long-: + \acro_declare_key:nnn {long_#1} {long-#1} + { \prop_put:cnn {l__acro_long_#1_form_prop} {##1} { \c_false_bool } } + % long--form: + \acro_declare_key_generic:nnn {long_#1_form} {long-#1-form} + { + \__acro_key_check:nn {##1} {long-#1-form} + \prop_put:cnn {l__acro_long_#1_form_prop} {##1} { \c_true_bool } + \prop_put:cnn {l__acro_long_#1_prop} {##1} {##2} + } + % options: + % short--ending + % alt--ending + % long--ending + % -ending + \keys_define:nn {acro} + { + short-#1-ending .tl_set:c = {l__acro_default_short_#1_tl} , + alt-#1-ending .tl_set:c = {l__acro_default_alt_#1_tl} , + long-#1-ending .tl_set:c = {l__acro_default_long_#1_tl} , + #1-ending .code:n = + \tl_set:cn {l__acro_default_short_#1_tl} {##1} + \tl_set:cn {l__acro_default_alt_#1_tl} {##1} + \tl_set:cn {l__acro_default_long_#1_tl} {##1} + } + % pdfstrings: + \prop_new:c {l__acro_pdfstring_short_#1_prop} + \cs_new:cpn {acro_pdf_string_short_#1:n} ##1 + { + \acro_if_star_gobble:nTF {##1} + { \prop_item:cn {l__acro_pdfstring_short_#1_prop} } + { \prop_item:cn {l__acro_pdfstring_short_#1_prop} {##1} } + } + \cs_new:cpn {acpdfstring#1} { \use:c {acro_pdf_string_short_#1:n} } + \prop_new:c {l__acro_pdfstring_alt_#1_prop} + \cs_new:cpn {acro_pdf_string_alt_#1:n} ##1 { - \tl_put_right:Nn \l__acro_long_tl - { \prop_get:Nn \l__acro_long_plural_prop {#1} } + \acro_if_star_gobble:nTF {##1} + { \prop_item:cn {l__acro_pdfstring_alt_#1_prop} } + { \prop_item:cn {l__acro_pdfstring_alt_#1_prop} {##1} } } + \cs_new:cpn {acpdfstringalt#1} { \use:c {acro_pdf_string_alt_#1:n} } } } +% #1: short|alt|long +% #2: ending +% #3: default ending +\cs_new_protected:Npn \acro_define_and_set_ending_variables:nnn #1#2#3 + { + \prop_new:c {l__acro_#1_#2_prop} + \prop_new:c {l__acro_#1_#2_form_prop} + \tl_new:c {l__acro_#1_#2_tl} + \tl_new:c {l__acro_default_#1_#2_tl} + \tl_set:cn {l__acro_default_#1_#2_tl} {#3} + } + +\NewDocumentCommand \ProvideAcroEnding {mmm} + { \acro_provide_ending:nnn {#1} {#2} {#3} } + % -------------------------------------------------------------------------- % enable us to know if the acronym is used only once and provide a different % style for that: @@ -1585,7 +1856,8 @@ \token_to_str:N \providecommand \token_to_str:N \acro@used@once [4] {} ^^J \token_to_str:N \providecommand \token_to_str:N \acro@used@twice [4] {} ^^J \token_to_str:N \providecommand \token_to_str:N \acro@pages [2] {} ^^J - \token_to_str:N \providecommand \token_to_str:N \acro@rerun@check {} + \token_to_str:N \providecommand \token_to_str:N \acro@rerun@check {} ^^J + \token_to_str:N \providecommand \token_to_str:N \acro@print@list {} } } \fi @@ -1593,8 +1865,8 @@ % -------------------------------------------------------------------------- \cs_new:Npn \acro_after:n #1 { - \__acro_cite_if:Nn \l__acro_citation_all_bool {#1} - \__acro_index_if:Nn \l__acro_addto_index_bool {#1} + \acro_cite_if:Nn \l__acro_citation_all_bool {#1} + \acro_index_if:Nn \l__acro_addto_index_bool {#1} } % the standard internals: @@ -1602,12 +1874,13 @@ { \acro_get:n {#1} \acro_is_used:n {#1} - \__acro_indefinite:nn {#1} { short } - \__acro_is_single:nT {#1} + \acro_write_indefinite:nn {#1} {short} + \acro_if_is_single:nT {#1} { \cs_set_eq:NN \acro_hyper_link:nn \use_ii:nn } - \__acro_acc_supp:nn + \acro_acc_supp:nn {#1} - { \__acro_write_short:V \l__acro_short_tl } + { \acro_write_short:nV {#1} \l__acro_short_tl } + \acro_endings:nn {#1} {short} \acro_after:n {#1} } @@ -1616,12 +1889,14 @@ { \acro_get:n {#1} \acro_is_used:n {#1} - \__acro_indefinite:nn {#1} { alt } - \__acro_is_single:nT {#1} + \acro_alt_error:n {#1} + \acro_write_indefinite:nn {#1} {alt} + \acro_if_is_single:nT {#1} { \cs_set_eq:NN \acro_hyper_link:nn \use_ii:nn } - \__acro_acc_supp:nn + \acro_acc_supp:nn {#1} - { \__acro_write_short:V \l__acro_alt_tl } + { \acro_write_alt:nV {#1} \l__acro_alt_tl } + \acro_endings:nn {#1} {alt} \acro_after:n {#1} } @@ -1630,10 +1905,11 @@ { \acro_get:n {#1} \acro_is_used:n {#1} - \__acro_indefinite:nn {#1} { long } - \__acro_is_single:nT {#1} + \acro_write_indefinite:nn {#1} {long} + \acro_if_is_single:nT {#1} { \cs_set_eq:NN \acro_hyper_link:nn \use_ii:nn } - \__acro_write_long:NV \l__acro_long_format_tl \l__acro_long_tl + \acro_write_long:NV \l__acro_long_format_tl \l__acro_long_tl + \acro_endings:nn {#1} {long} \acro_after:n {#1} } @@ -1643,9 +1919,9 @@ \bool_gset_true:c { g__acro_#1_first_use_bool } \acro_get:n {#1} \acro_is_used:n {#1} - \__acro_is_single:nT {#1} + \acro_if_is_single:nT {#1} { \cs_set_eq:NN \acro_hyper_link:nn \use_ii:nn } - \UseInstance { acro-first } { \l__acro_first_instance_tl } + \UseInstance {acro-first} { \l__acro_first_instance_tl } {#1} { \l__acro_short_tl } { \l__acro_long_tl } @@ -1657,7 +1933,7 @@ \bool_gset_true:c { g__acro_#1_first_use_bool } \acro_get:n {#1} \acro_is_used:n {#1} - \__acro_is_single:nT {#1} + \acro_if_is_single:nT {#1} { \cs_set_eq:NN \acro_hyper_link:nn \use_ii:nn } \UseInstance { acro-first } { \l__acro_first_instance_tl } {#1} @@ -1668,9 +1944,7 @@ % ---------------------------------------------------------------------------- % citations: \cs_new:Npn \__acro_citation_cmd:w { \cite } %{} - -\cs_new_protected:Npn \acro_cite: - { \bool_set_true:N \l__acro_citation_all_bool } +\cs_new:Npn \__acro_group_citation_cmd:w { \cite } %{} % #1 pre % #2 post @@ -1687,27 +1961,38 @@ } \cs_generate_variant:Nn \__acro_cite:nnn { VVV } -\cs_new_protected:Npn \__acro_cite_if:Nn #1#2 +\cs_new_protected:Npn \acro_cite:n #1 { - \bool_if:NT #1 + \prop_get:NnNT \l__acro_citation_prop {#1} \l__acro_tmpa_tl { - \prop_get:NnNT \l__acro_citation_prop {#2} \l__acro_tmpa_tl - { - \prop_get:NnN \l__acro_citation_pre_prop {#2} \l__acro_tmpb_tl - \prop_get:NnN \l__acro_citation_post_prop {#2} \l__acro_tmpc_tl - \acro_no_break: - \tl_use:N \l__acro_citation_space_tl - \__acro_cite:VVV - \l__acro_tmpb_tl - \l__acro_tmpc_tl - \l__acro_tmpa_tl - } + \prop_get:NnN \l__acro_citation_pre_prop {#1} \l__acro_tmpb_tl + \prop_get:NnN \l__acro_citation_post_prop {#1} \l__acro_tmpc_tl + \acro_no_break: + \tl_use:N \l__acro_citation_connect_tl + \__acro_cite:VVV + \l__acro_tmpb_tl + \l__acro_tmpc_tl + \l__acro_tmpa_tl } } +\cs_new_protected:Npn \acro_group_cite:n #1 + { + \group_begin: + \cs_set_eq:NN \__acro_citation_cmd:w \__acro_group_citation_cmd:w + \tl_set_eq:NN + \l__acro_citation_connect_tl + \l__acro_between_group_connect_citation_tl + \acro_cite_if:Nn \l__acro_citation_first_bool {#1} + \group_end: + } + +\cs_new_protected:Npn \acro_cite_if:Nn #1#2 + { \bool_if:NT #1 { \acro_cite:n {#2} } } + % ---------------------------------------------------------------------------- % indexing: -\cs_new_protected:Npn \__acro_index_if:Nn #1#2 +\cs_new_protected:Npn \acro_index_if:Nn #1#2 { \bool_if:nT { #1 && \l__acro_mark_as_used_bool } { @@ -1722,9 +2007,6 @@ } } -\cs_new_protected:Npn \acro_index: - { \bool_set_true:N \l__acro_addto_index_bool } - \cs_new:Npn \__acro_index_cmd:n { \index } % #1: cmd @@ -1752,50 +2034,60 @@ % ---------------------------------------------------------------------------- % accessability support -\cs_new_eq:NN \__acro_acc_supp:nn \use_ii:nn +\cs_new_eq:NN \acro_acc_supp:nn \use_ii:nn -\cs_new:Npn \acro_acc_supp:nnn #1#2#3 +\cs_new_protected:Npn \acro_get_acc_supp:nn #1#2 + { + \prop_get:NnNF \l__acro_acc_supp_prop {#1} \l__acro_acc_supp_tl + { \prop_get:NnNF \l__acro_short_prop {#1} \l__acro_acc_supp_tl {} } + \seq_map_inline:Nn \l__acro_endings_seq + { + \bool_if:cT {l__acro_##1_bool} + { + \tl_put_right:Nv + \l__acro_acc_supp_tl + {l__acro_short_##1_tl} + } + } + \acro_do_acc_supp:VVn + \l__acro_acc_supp_tl + \l__acro_acc_supp_options_tl + {#2} + } + +\cs_new:Npn \acro_do_acc_supp:nnn #1#2#3 { \BeginAccSupp { ActualText = #1 , #2 } #3 \EndAccSupp { } } -\cs_generate_variant:Nn \acro_acc_supp:nnn { VV } +\cs_generate_variant:Nn \acro_do_acc_supp:nnn { VV } + +% macro to redefine to adapt definition of \acro_acc_supp:nn, for cases like +% http://tex.stackexchange.com/a/161521/ +\cs_new_protected:Npn \acro_set_accsupp: + { \cs_set_eq:NN \acro_acc_supp:nn \acro_get_acc_supp:nn } \AtBeginDocument { \bool_if:NT \l__acro_acc_supp_bool { - \RequirePackage { accsupp } - \cs_set_protected:Npn \__acro_acc_supp:nn #1#2 - { - \prop_get:NnNF \l__acro_acc_supp_prop {#1} \l__acro_acc_supp_tl - { \prop_get:NnNF \l__acro_short_prop {#1} \l__acro_acc_supp_tl {} } - \bool_if:NT \l__acro_use_plural_bool - { \tl_put_right:NV \l__acro_acc_supp_tl \l__acro_short_plural_tl } - \acro_acc_supp:VVn - \l__acro_acc_supp_tl - \l__acro_acc_supp_options_tl - {#2} - } + \RequirePackage {accsupp} + \acro_set_accsupp: } } % -------------------------------------------------------------------------- % indefinite articles: -\cs_new_protected:Npn \acro_indefinite: - { - \bool_if:NTF \l__acro_first_upper_bool - { \bool_set_true:N \l__acro_upper_indefinite_bool } - { \bool_set_true:N \l__acro_indefinite_bool } - } -\cs_new_protected:Npn \__acro_indefinite:nn #1#2 +% #1: ID +% #2: short|long|alt +\cs_new_protected:Npn \acro_write_indefinite:nn #1#2 { \bool_if:NT \l__acro_indefinite_bool { \prop_get:cn { l__acro_#2_indefinite_prop } {#1} ~ } \bool_if:NT \l__acro_upper_indefinite_bool - { + { % \bool_set_true:N \l__acro_first_upper_bool \__acro_first_upper_case:x { \prop_get:cn { l__acro_#2_indefinite_prop } {#1} } ~ } @@ -1889,407 +2181,466 @@ { \cs_if_exist:NF \acro@printed@list { \cs_new:Npn \acro@printed@list { printed } } } % -------------------------------------------------------------------------- -% the user commands: -% #1: ID -% #2: true|false -\cs_new_protected:Npn \acro_check_acronym:nn #1#2 +% trailing tokens and what to do when present +\prop_new:N \l__acro_trailing_tokens_prop +\prop_new:N \l__acro_trailing_actions_prop +\bool_new:N \l__acro_trailing_tokens_bool +\tl_new:N \l__acro_trailing_tokens_tl + +\cs_new_protected:Npn \acro_new_trailing_token:n #1 + { \bool_new:c {l__acro_trailing_#1_bool} } +\cs_new_protected:Npn \acro_activate_trailing_action:n #1 + { \bool_set_true:c {l__acro_trailing_#1_bool} } +\cs_new_protected:Npn \acro_deactivate_trailing_action:n #1 + { \bool_set_false:c {l__acro_trailing_#1_bool} } + +% register a new token but don't activate its action: +% #1: token +% #2: name +\cs_new_protected:Npn \acro_register_trailing_token:Nn #1#2 { - \acro_defined:n {#1} - \acro_use_acronym:n {#2} + \prop_put:Nnn \l__acro_trailing_tokens_prop {#2} {#1} + \prop_put:Nnn \l__acro_trailing_actions_prop {#1} + { \acro_activate_trailing_action:n {#2} } + \acro_new_trailing_token:n {#2} } -% automatic: -\NewDocumentCommand \ac { sm } +\NewDocumentCommand \AcroRegisterTrailing {mm} + { \acro_register_trailing_token:Nn #1 {#2} } + +% activate a token: +\cs_new_protected:Npn \acro_activate_trailing_token:n #1 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_use:n {#2} - \group_end: + \prop_get:NnN \l__acro_trailing_tokens_prop {#1} \l__acro_tmpa_tl + \tl_put_right:NV \l__acro_trailing_tokens_tl \l__acro_tmpa_tl } -\NewDocumentCommand \iac { sm } +% deactivate a token: +\cs_new_protected:Npn \acro_deactivate_trailing_token:n #1 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_indefinite: - \acro_use:n {#2} - \group_end: + \prop_get:NnN \l__acro_trailing_tokens_prop {#1} \l__acro_tmpa_tl + \tl_remove_all:NV \l__acro_trailing_tokens_tl \l__acro_tmpa_tl } -\NewDocumentCommand \Iac { sm } +% #1: name +\prg_new_conditional:Npnn \acro_if_trailing_token:n #1 {p,T,F,TF} { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_indefinite: - \acro_use:n {#2} - \group_end: + \bool_if:cTF {l__acro_trailing_#1_bool} + { \prg_return_true: } + { \prg_return_false: } } -\NewDocumentCommand \Ac { sm } +% #1: csv list of names +\prg_new_protected_conditional:Npnn \acro_if_trailing_tokens:n #1 {T,F,TF} { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_use:n {#2} - \group_end: + \bool_set_false:N \l__acro_trailing_tokens_bool + \clist_map_inline:nn {#1} + { + \bool_if:cT {l__acro_trailing_##1_bool} + { + \bool_set_true:N \l__acro_trailing_tokens_bool + \clist_map_break: + } + } + \bool_if:NTF \l__acro_trailing_tokens_bool + { \prg_return_true: } + { \prg_return_false: } } -\NewDocumentCommand \acp { sm } +\cs_new_protected:Npn \aciftrailing { \acro_if_trailing_tokens:nTF } + +\cs_new_protected:Npn \acro_treat_trail: { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_use:n {#2} - \group_end: + \tl_map_inline:Nn \l__acro_trailing_tokens_tl + { + \token_if_eq_meaning:NNT \l_peek_token ##1 + { \prop_get:Nn \l__acro_trailing_actions_prop {##1} } + } } -\NewDocumentCommand \Acp { sm } +% register some tokens to be checked for: +\AcroRegisterTrailing . {dot} +\AcroRegisterTrailing - {dash} +\AcroRegisterTrailing \babelhyphen {babel-hyphen} + +% options for activating actions: +\keys_define:nn {acro} { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_upper: - \acro_use:n {#2} - \group_end: + activate-trailing-tokens .code:n = + \clist_map_inline:nn {#1} { \acro_activate_trailing_token:n {##1} } , + activate-trailing-tokens .initial:n = dot , + deactivate-trailing-tokens .code:n = + \clist_map_inline:nn {#1} { \acro_deactivate_trailing_token:n {##1} } } -% short: -\NewDocumentCommand \acs { sm } +% some user macros: +\cs_new_protected:Npn \acro_dot: { \aciftrailing {dot} {} {.} } +\cs_new_eq:NN \acdot \acro_dot: + +\cs_new_protected:Npn \acro_space: + { \aciftrailing {dash,babel-hyphen} {} {\space} } +\cs_new_eq:NN \acspace \acro_space: + +% --------------------------------------------------------------------------- +% reset outputs, they'll behave like the first time again (!not like the _only_ +% time!): +\cs_new_protected:Npn \acro_reset:n #1 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_short:n {#2} - \group_end: + \bool_gset_false:c { g__acro_#1_used_bool } + \bool_gset_false:c { g__acro_#1_first_use_bool } } -\NewDocumentCommand \iacs { sm } +\cs_new_protected:Npn \acro_mark_as_used:n #1 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_indefinite: - \acro_short:n {#2} - \group_end: + \bool_gset_true:c { g__acro_#1_used_bool } + \bool_gset_true:c { g__acro_#1_first_use_bool } + \bool_gset_true:c { g__acro_#1_in_list_bool } + \if@filesw + \iow_shipout_x:Nn \@auxout + { \token_to_str:N \acro@used@once {#1} {} {} {} } + \iow_shipout_x:Nn \@auxout + { \token_to_str:N \acro@used@twice {#1} {} {} {} } + \fi } -\NewDocumentCommand \Iacs { sm } + +\cs_new_protected:Npn \acro_reset_all: + { \prop_map_inline:Nn \l__acro_short_prop { \acro_reset:n {##1} } } + +\cs_new_protected:Npn \acro_mark_all_as_used: + { \prop_map_inline:Nn \l__acro_short_prop { \acro_mark_as_used:n {##1} } } + +\DeclareExpandableDocumentCommand \acifused { m } + { \acro_if_acronym_used:nTF {#1} } + +\prg_new_conditional:Npnn \acro_if_acronym_used:n #1 { p,T,F,TF } { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_indefinite: - \acro_short:n {#2} - \group_end: + \bool_if:nTF + { + \bool_if_p:c { g__acro_#1_used_bool } && + ( !\__acro_is_single_p:n {#1} ) + } + { \prg_return_true: } + { \prg_return_false: } } -\NewDocumentCommand \acsp { sm } +\NewDocumentCommand \acresetall {} + { \acro_reset_all: } + +\NewDocumentCommand \acuseall {} + { \acro_mark_all_as_used: } + +\NewDocumentCommand \acreset { > { \SplitList { , } } m } + { \ProcessList {#1} { \acro_reset:n } \ignorespaces } + +\NewDocumentCommand \acuse { > { \SplitList { , } } m } + { \ProcessList {#1} { \acro_mark_as_used:n } \ignorespaces } + +% -------------------------------------------------------------------------- +% the user commands -- preparation: +\cs_new_protected:Npn \acro_begin: { \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_short:n {#2} - \group_end: + \__acro_check_after_end:w } -% alt: -\NewDocumentCommand \aca { sm } +\cs_new_protected:Npn \__acro_check_after_end:w #1 \acro_end: { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_alt:n {#2} - \group_end: + \cs_set:Npn \__acro_execute: + { + \acro_treat_trail: + #1 + \acro_end: % this will end the group opened by \acro_begin: + } + \peek_after:Nw \__acro_execute: } -\NewDocumentCommand \iaca { sm } +\cs_new_protected:Npn \acro_end: { \group_end: } + +% #1: ID +% #2: true|false +\cs_new_protected:Npn \acro_check_acronym:nn #1#2 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_indefinite: - \acro_alt:n {#2} - \group_end: + \acro_defined:n {#1} + \acro_use_acronym:n {#2} } -\NewDocumentCommand \Iaca { sm } +% #1: boolean +% #2: ID +\cs_new_protected:Npn \acro_check_and_mark_if:nn #1#2 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_indefinite: - \acro_alt:n {#2} - \group_end: + \bool_if:nTF {#1} + { \acro_check_acronym:nn {#2} {false} } + { \acro_check_acronym:nn {#2} {true} } } -\NewDocumentCommand \acap { sm } +% commands for (re)defining \ac-like macros: +\cs_new_protected:Npn \acro_define_new_acro_command:NN #1#2 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_alt:n {#2} - \group_end: + % #1: csname + % #2: definition where `#1' refers to the ID + \cs_new_protected:Npn #1 ##1##2 + { + \cs_set:Npn \__acro_tmp_command:n ####1 {##2} + \exp_args:NNnx #2 ##1 {sm} + { + \acro_begin: + \acro_check_and_mark_if:nn {########1} {########2} + \exp_not:o { \__acro_tmp_command:n {####2} } + \acro_end: + } + } } +\cs_generate_variant:Nn \acro_define_new_acro_command:NN {cc} -% long: -\NewDocumentCommand \acl { sm } +% commands for (re)defining \acflike-like macros: +\cs_new_protected:Npn \acro_define_new_acro_pseudo_command:NN #1#2 { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_long:n {#2} - \group_end: + % #1: csname + % #2: definition where `#1' refers to the ID and `#2' to the pseudo long form + \cs_new_protected:Npn #1 ##1##2 + { + \cs_set:Npn \__acro_tmp_command:nn ####1####2 {##2} + \exp_args:NNnx #2 ##1 {smm} + { + \acro_begin: + \acro_check_and_mark_if:nn {########1} {########2} + \exp_not:o { \__acro_tmp_command:nn {####2} {####3} } + \acro_end: + } + } } +\cs_generate_variant:Nn \acro_define_new_acro_pseudo_command:NN {cc} -\NewDocumentCommand \iacl { sm } +\clist_map_inline:nn {New,Renew,Declare,Provide} { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_indefinite: - \acro_long:n {#2} - \group_end: + \acro_define_new_acro_command:cc + {#1AcroCommand} + {#1DocumentCommand} + \acro_define_new_acro_pseudo_command:cc + {#1PseudoAcroCommand} + {#1DocumentCommand} } -\NewDocumentCommand \Iacl { sm } +% -------------------------------------------------------------------------- +% user commands -- facilities +\cs_new_protected:Npn \acro_first_upper: { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_indefinite: - \acro_long:n {#2} - \group_end: + \bool_if:NTF \l__acro_indefinite_bool + { + \bool_set_false:N \l__acro_indefinite_bool + \bool_set_true:N \l__acro_upper_indefinite_bool + } + { \bool_set_true:N \l__acro_first_upper_bool } } -\NewDocumentCommand \Acl { sm } +\cs_new_protected:Npn \acro_indefinite: { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_long:n {#2} - \group_end: + \bool_if:NTF \l__acro_first_upper_bool + { + \bool_set_true:N \l__acro_upper_indefinite_bool + \bool_set_false:N \l__acro_first_upper_bool + } + { \bool_set_true:N \l__acro_indefinite_bool } } -\NewDocumentCommand \aclp { sm } +\cs_new_protected:Npn \acro_cite: { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_long:n {#2} - \group_end: + \bool_set_true:N \l__acro_citation_all_bool + \bool_set_true:N \l__acro_citation_first_bool } -\NewDocumentCommand \Aclp { sm } +\cs_new_protected:Npn \acro_no_cite: { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_upper: - \acro_long:n {#2} - \group_end: + \bool_set_false:N \l__acro_citation_all_bool + \bool_set_false:N \l__acro_citation_first_bool } -% first: -\NewDocumentCommand \acf { sm } +\cs_new_protected:Npn \acro_index: + { \bool_set_true:N \l__acro_addto_index_bool } + +% similar macros \acro_: are defined by \acro_provide_ending:nnn + +% -------------------------------------------------------------------------- +% the user commands +% automatic: +\NewAcroCommand \ac + { \acro_use:n {#1} } + +\NewAcroCommand \iac { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_first:n {#2} - \group_end: + \acro_indefinite: + \acro_use:n {#1} } -\NewDocumentCommand \iacf { sm } +\NewAcroCommand \Iac { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_indefinite: - \acro_first:n {#2} - \group_end: + \acro_first_upper: + \acro_indefinite: + \acro_use:n {#1} } -\NewDocumentCommand \Iacf { sm } +\NewAcroCommand \Ac { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_indefinite: - \acro_first:n {#2} - \group_end: + \acro_first_upper: + \acro_use:n {#1} } -\NewDocumentCommand \Acf { sm } +\NewAcroCommand \acp { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_first:n {#2} - \group_end: + \acro_plural: + \acro_use:n {#1} } -\NewDocumentCommand \acfp { sm } +\NewAcroCommand \Acp { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_first:n {#2} - \group_end: + \acro_plural: + \acro_first_upper: + \acro_use:n {#1} } -\NewDocumentCommand \Acfp { sm } +\NewAcroCommand \acsingle { \acro_get:n {#1} \acro_single:n {#1} } + +% short: +\NewAcroCommand \acs + { \acro_short:n {#1} } + +\NewAcroCommand \iacs { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_upper: - \acro_first:n {#2} - \group_end: + \acro_indefinite: + \acro_short:n {#1} } -% first-like: -\NewDocumentCommand \acflike { smm } +\NewAcroCommand \Iacs { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_first_like:nn {#2} {#3} - \group_end: + \acro_first_upper: + \acro_indefinite: + \acro_short:n {#1} } -\NewDocumentCommand \iacflike { smm } +\NewAcroCommand \acsp { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_indefinite: - \acro_first_like:nn {#2} {#3} - \group_end: + \acro_plural: + \acro_short:n {#1} } -\NewDocumentCommand \Iacflike { smm } +% alt: +\NewAcroCommand \aca + { \acro_alt:n {#1} } + +\NewAcroCommand \iaca { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_upper: - \acro_indefinite: - \acro_first_like:nn {#2} {#3} - \group_end: + \acro_indefinite: + \acro_alt:n {#1} } -\NewDocumentCommand \acfplike { smm } +\NewAcroCommand \Iaca { - \group_begin: - \IfBooleanTF #1 - { \acro_check_acronym:nn {#2} {false} } - { \acro_check_acronym:nn {#2} {true} } - \acro_plural: - \acro_first_like:nn {#2} {#3} - \group_end: + \acro_first_upper: + \acro_indefinite: + \acro_alt:n {#1} } -% reset outputs, they'll behave like the first time again (!not like the _only_ -% time!): -\cs_new_protected:Npn \acro_reset:n #1 +\NewAcroCommand \acap { - \bool_gset_false:c { g__acro_#1_used_bool } - \bool_gset_false:c { g__acro_#1_first_use_bool } + \acro_plural: + \acro_alt:n {#1} } -\cs_new_protected:Npn \acro_mark_as_used:n #1 +% long: +\NewAcroCommand \acl + { \acro_long:n {#1} } + +\NewAcroCommand \iacl { - \bool_gset_true:c { g__acro_#1_used_bool } - \bool_gset_true:c { g__acro_#1_first_use_bool } - \bool_gset_true:c { g__acro_#1_in_list_bool } - \if@filesw - \iow_shipout_x:Nn \@auxout - { \token_to_str:N \acro@used@once {#1} {} {} {} } - \iow_shipout_x:Nn \@auxout - { \token_to_str:N \acro@used@twice {#1} {} {} {} } - \fi + \acro_indefinite: + \acro_long:n {#1} } +\NewAcroCommand \Iacl + { + \acro_first_upper: + \acro_indefinite: + \acro_long:n {#1} + } -\cs_new_protected:Npn \acro_reset_all: - { \prop_map_inline:Nn \l__acro_short_prop { \acro_reset:n {##1} } } +\NewAcroCommand \Acl + { + \acro_first_upper: + \acro_long:n {#1} + } -\cs_new_protected:Npn \acro_mark_all_as_used: - { \prop_map_inline:Nn \l__acro_short_prop { \acro_mark_as_used:n {##1} } } +\NewAcroCommand \aclp + { + \acro_plural: + \acro_long:n {#1} + } -\DeclareExpandableDocumentCommand \acifused { m } - { \acro_if_acronym_used:nTF {#1} } +\NewAcroCommand \Aclp + { + \acro_plural: + \acro_first_upper: + \acro_long:n {#1} + } -\prg_new_conditional:Npnn \acro_if_acronym_used:n #1 { p,T,F,TF } +% first: +\NewAcroCommand \acf + { \acro_first:n {#1} } + +\NewAcroCommand \iacf { - \bool_if:nTF - { - \bool_if_p:c { g__acro_#1_used_bool } && - ( !\__acro_is_single_p:n {#1} ) - } - { \prg_return_true: } - { \prg_return_false: } + \acro_indefinite: + \acro_first:n {#1} } -\NewDocumentCommand \acresetall {} - { \acro_reset_all: } +\NewAcroCommand \Iacf + { + \acro_first_upper: + \acro_indefinite: + \acro_first:n {#1} + } -\NewDocumentCommand \acuseall {} - { \acro_mark_all_as_used: } +\NewAcroCommand \Acf + { + \acro_first_upper: + \acro_first:n {#1} + } -\NewDocumentCommand \acreset { > { \SplitList { , } } m } - { \ProcessList {#1} { \acro_reset:n } \ignorespaces } +\NewAcroCommand \acfp + { + \acro_plural: + \acro_first:n {#1} + } -\NewDocumentCommand \acuse { > { \SplitList { , } } m } - { \ProcessList {#1} { \acro_mark_as_used:n } \ignorespaces } +\NewAcroCommand \Acfp + { + \acro_plural: + \acro_first_upper: + \acro_first:n {#1} + } + +% first-like: +\NewPseudoAcroCommand \acflike + { \acro_first_like:nn {#1} {#2} } + +\NewPseudoAcroCommand \iacflike + { + \acro_indefinite: + \acro_first_like:nn {#1} {#2} + } + +\NewPseudoAcroCommand \Iacflike + { + \acro_first_upper: + \acro_indefinite: + \acro_first_like:nn {#1} {#2} + } + +\NewPseudoAcroCommand \acfplike + { + \acro_plural: + \acro_first_like:nn {#1} {#2} + } % --------------------------------------------------------------------------- % process options: @@ -2298,10 +2649,10 @@ % --------------------------------------------------------------------------- % PDF bookmark support \cs_new:Npn \acpdfstring - { \acro_pdf_string:n } + { \acro_pdf_string_short:n } -\cs_new:Npn \acpdfstringplural - { \acro_pdf_string_plural:n } +\cs_new:Npn \acpdfstringalt + { \acro_pdf_string_alt:n } \prg_new_conditional:Npnn \acro_if_star_gobble:n #1 {TF} { @@ -2312,18 +2663,18 @@ \fi: } -\cs_new:Npn \acro_pdf_string:n #1 +\cs_new:Npn \acro_pdf_string_short:n #1 { \acro_if_star_gobble:nTF {#1} - { \prop_get:Nn \l__acro_pdfstring_prop } - { \prop_get:Nn \l__acro_pdfstring_prop {#1} } + { \prop_item:Nn \l__acro_pdfstring_short_prop } + { \prop_item:Nn \l__acro_pdfstring_short_prop {#1} } } - -\cs_new:Npn \acro_pdf_string_plural:n #1 + +\cs_new:Npn \acro_pdf_string_alt:n #1 { \acro_if_star_gobble:nTF {#1} - { \prop_get:Nn \l__acro_pdfstring_plural_prop } - { \prop_get:Nn \l__acro_pdfstring_plural_prop {#1} } + { \prop_item:Nn \l__acro_pdfstring_alt_prop } + { \prop_item:Nn \l__acro_pdfstring_alt_prop {#1} } } \AtBeginDocument @@ -2340,7 +2691,7 @@ \cs_set_eq:NN \Acl \acpdfstring \cs_set_eq:NN \acf \acpdfstring \cs_set_eq:NN \Acf \acpdfstring - \cs_set_eq:NN \aca \acpdfstring + \cs_set_eq:NN \aca \acpdfstringalt \cs_set_eq:NN \acp \acpdfstringplural \cs_set_eq:NN \Acp \acpdfstringplural \cs_set_eq:NN \acsp \acpdfstringplural @@ -2348,7 +2699,7 @@ \cs_set_eq:NN \Aclp \acpdfstringplural \cs_set_eq:NN \acfp \acpdfstringplural \cs_set_eq:NN \Acfp \acpdfstringplural - \cs_set_eq:NN \acap \acpdfstringplural + \cs_set_eq:NN \acap \acpdfstringaltplural } \cs_set_protected:Npn \acro_hyper_page:n #1 { \hyperpage {#1} } } {} @@ -2374,26 +2725,31 @@ \msg_new:nnn {acro} {doubled-key} { - It~seems~to~me~you~have~used~the~`#1'~key~before.~If~you~haven't~there's~ - something~different~wrong~and~I'm~lost.~You~'re~on~your~own~now. + It~ seems~ to~ me~ you~ have~ used~ the~ `#2'~ key~ twice~ in~ the~ + declaration~ of~ acronym~ `#1'.~ If~ you~ haven't~ there's~ + something~ different~ wrong~ and~ I'm~ lost.~ You~'re~ on~ your~ own~ + then. } \cs_new_protected:Npn \__acro_key_check:nn #1#2 { \tl_if_blank:VT \l__acro_current_key_tl - { \acro_serious_message:nn {acro} {no-id} } + { \acro_serious_message:n {no-id} } \bool_if:cF { l__acro_#1_short_set_bool } - { \acro_serious_message:nnnn {acro} {before-short} {#1} {#2} } + { + \keys_set:nn { acro / declare-acronym } { short = {#1} } + \acro_harmless_message:nn {substitute-short} {#1} + } \bool_new:c { l__acro_#1_#2_set_bool } \bool_set_true:c { l__acro_#1_#2_set_bool } } -\cs_new_protected:Npn \__acro_first_key_check:n #1 +\cs_new_protected:Npn \__acro_first_key_check:nn #1#2 { \cs_if_exist:cTF { l__acro_#1_short_set_bool } { \bool_if:cT { l__acro_#1_short_set_bool } - { \acro_serious_message:nnn {acro} {doubled-key} {#1} } + { \acro_serious_message:nnn {doubled-key} {#1} {#2} } } { \bool_new:c { l__acro_#1_short_set_bool } @@ -2409,11 +2765,8 @@ % #3: action \cs_new_protected:Npn \acro_declare_key_generic:nnn #1#2#3 { - \prop_new:c { l__acro_#1_prop } - \cs_new_protected:cpn { __acro_declare_#1:nn } ##1##2 - { - #3 - } + \prop_clear_new:c { l__acro_#1_prop } + \cs_new_protected:cpn { __acro_declare_#1:nn } ##1##2 {#3} \cs_generate_variant:cn { __acro_declare_#1:nn } { V } \keys_define:nn { acro / declare-acronym } { @@ -2421,7 +2774,6 @@ \use:c {__acro_declare_#1:Vn} \l__acro_current_key_tl {##1} } } -\cs_generate_variant:Nn \cs_generate_variant:Nn {c} % #1: name in associated cs % #2: key name @@ -2462,52 +2814,53 @@ % short: \acro_declare_key_generic:nnn {short} {short} { - \__acro_first_key_check:n {#1} + \__acro_first_key_check:nn {#1} {short} \prop_put:Nnn \l__acro_short_prop {#1} {#2} \prop_put:Nnn \l__acro_sort_prop {#1} {#1} \prop_put:Nnn \l__acro_index_sort_prop {#1} {#1} \prop_put:Nnn \l__acro_alt_prop {#1} {#2} - \prop_put:Nnx \l__acro_pdfstring_prop {#1} { \exp_not:n {#2} } - \prop_put:Nnn \l__acro_short_plural_prop - {#1} { \l__acro_default_plural_tl } - \prop_put:Nnx \l__acro_short_indefinite_prop - {#1} { \l__acro_default_indefinite_tl } - \prop_put:Nnx \l__acro_alt_indefinite_prop - {#1} { \l__acro_default_indefinite_tl } - \prop_put:Nnx \l__acro_pdfstring_plural_prop - {#1} { \exp_not:n {#2} \exp_not:V \l__acro_default_plural_tl } + \prop_put:Nnn \l__acro_pdfstring_short_prop {#1} {#2} + \prop_put:Nnn \l__acro_pdfstring_alt_prop {#1} {#2} + \seq_map_inline:Nn \l__acro_endings_seq + { + \prop_put:cnv {l__acro_short_##1_prop} + {#1} {l__acro_default_short_##1_tl} + \prop_put:cnx {l__acro_pdfstring_short_##1_prop} + {#1} { \exp_not:n {#2} \exp_not:v {l__acro_default_short_##1_tl} } + \prop_put:cnn {l__acro_short_##1_form_prop} {#1} { \c_false_bool } + \prop_put:cnv {l__acro_alt_##1_prop} + {#1} {l__acro_default_alt_##1_tl} + \prop_put:cnx {l__acro_pdfstring_alt_##1_prop} + {#1} { \exp_not:n {#2} \exp_not:v {l__acro_default_short_##1_tl} } + \prop_put:cnn {l__acro_alt_##1_form_prop} {#1} { \c_false_bool } + } + \prop_put:NnV \l__acro_short_indefinite_prop + {#1} \l__acro_default_indefinite_tl + \prop_put:NnV \l__acro_alt_indefinite_prop + {#1} \l__acro_default_indefinite_tl } -% short plural: -\acro_declare_simple_key:n {short-plural} - % long: \acro_declare_key:nnn {long} {long} { - \prop_put:Nnn \l__acro_long_plural_form_prop {#1} { \c_false_bool } - \prop_put:Nnx \l__acro_long_indefinite_prop - {#1} { \l__acro_default_indefinite_tl } - \bool_if:cF { l__acro_#1_long-plural_set_bool } + \seq_map_inline:Nn \l__acro_endings_seq + { \prop_put:cnn {l__acro_long_##1_form_prop} {#1} { \c_false_bool } } + \prop_put:NnV \l__acro_long_indefinite_prop + {#1} + \l__acro_default_indefinite_tl + \seq_map_inline:Nn \l__acro_endings_seq { - \prop_put:Nnn \l__acro_long_plural_prop - {#1} { \l__acro_default_plural_tl } + \bool_if:cF {l__acro_#1_long-##1_set_bool} + { \prop_put:cnv {l__acro_long_##1_prop} {#1} {l__acro_default_long_##1_tl} } } } % list: \acro_declare_simple_key:n {list} -% long plural: -\acro_declare_key:nnn {long_plural} {long-plural} - { \prop_put:Nnn \l__acro_long_plural_form_prop {#1} { \c_false_bool } } - -% long plural form: -\acro_declare_key_generic:nnn {long_plural_form} {long-plural-form} - { - \__acro_key_check:nn {#1} { long-plural-form } - \prop_put:Nnn \l__acro_long_plural_form_prop {#1} { \c_true_bool } - \prop_put:Nnn \l__acro_long_plural_prop {#1} {#2} - } +% defines `short-plural', `long-plural' and `long-plural-form' as well as the +% options `plural-ending', `short-plural-ending' and `long-plural-ending': +\ProvideAcroEnding {plural} {s} {s} % short indefinite article: \acro_declare_simple_key:n {short-indefinite} @@ -2531,8 +2884,15 @@ % alternative: \acro_declare_key:nnn {alt} {alt} { - \prop_put:Nnx \l__acro_alt_indefinite_prop - {#1} { \l__acro_default_indefinite_tl } + \prop_put:Nnn \l__acro_pdfstring_alt_prop {#1} {#2} + \prop_put:NnV \l__acro_alt_indefinite_prop + {#1} \l__acro_default_indefinite_tl + } + +\cs_set_protected:Npn \acro_alt_error:n #1 + { + \bool_if:cF {l__acro_#1_alt_set_bool} + { \acro_harmless_message:nn {no-alternative} {#1} } } % alt. indefinite article: @@ -2554,20 +2914,22 @@ \acro_declare_simple_key:n {first-long-format} % pdfstring: -\prop_new:N \l__acro_pdfstring_prop -\prop_new:N \l__acro_pdfstring_plural_prop +\prop_new:N \l__acro_pdfstring_short_prop \cs_new_protected:Npn \__acro_declare_pdfstring:nw #1#2/#3/#4 \acro_stop: { \__acro_key_check:nn {#1} { pdfstring } - \prop_put:Nnx \l__acro_pdfstring_prop {#1} {#2} - \tl_if_empty:nTF { #3 } + \prop_put:Nnn \l__acro_pdfstring_short_prop {#1} {#2} + \seq_map_inline:Nn \l__acro_endings_seq { - \prop_put:Nnx \l__acro_pdfstring_plural_prop - {#1} { \exp_not:n {#2} \exp_not:V \l__acro_default_plural_tl } - } - { - \prop_put:Nnx \l__acro_pdfstring_plural_prop - {#1} { \exp_not:n { #2#3 } } + \tl_if_empty:nTF {#3} + { + \prop_put:cnx {l__acro_pdfstring_short_##1_prop} + {#1} { \exp_not:n {#2} \exp_not:v {l__acro_default_short_##1_tl} } + } + { + \prop_put:cnn {l__acro_pdfstring_short_##1_prop} + {#1} {#2#3} + } } } \cs_generate_variant:Nn \__acro_declare_pdfstring:nw { V } @@ -2577,6 +2939,28 @@ \__acro_declare_pdfstring:Vw \l__acro_current_key_tl #1 // \acro_stop: , } +\prop_new:N \l__acro_pdfstring_alt_prop +\cs_new_protected:Npn \__acro_declare_pdfstring_alt:nw #1#2/#3/#4 \acro_stop: + { + \__acro_key_check:nn {#1} { pdfstring-alt } + \prop_put:Nnn \l__acro_pdfstring_alt_prop {#1} {#2} + \seq_map_inline:Nn \l__acro_endings_seq + { + \tl_if_empty:nTF {#3} + { + \prop_put:cnx {l__acro_pdfstring_alt_##1_prop} + {#1} { \exp_not:n {#2} \exp_not:v {l__acro_default_alt_##1_tl} } + } + { \prop_put:cnn {l__acro_pdfstring_alt_##1_prop} {#1} {#2#3} } + } + } +\cs_generate_variant:Nn \__acro_declare_pdfstring_alt:nw { V } +\keys_define:nn { acro / declare-acronym } + { + pdfstring-alt .code:n = + \__acro_declare_pdfstring_alt:Vw \l__acro_current_key_tl #1 // \acro_stop: , + } + % class: \acro_declare_simple_key:n {class} @@ -2656,7 +3040,7 @@ { \bool_if:NTF \l__acro_strict_bool { \cs_set:cpn {#1} { \ac {#1} \acro_xspace: } } - { \acro_serious_message:nnn {acro} {macro} {#1} } + { \acro_serious_message:nn {macro} {#1} } } { \cs_new:cpn {#1} { \ac {#1} \acro_xspace: } } } @@ -2666,6 +3050,7 @@ % internal acronym declaring function: \cs_new_protected:Npn \acro_declare_acronym:nn #1#2 { + \bool_gset_true:N \g__acro_first_acronym_declared_bool \tl_set:Nn \l__acro_current_key_tl {#1} \keys_set:nn { acro / declare-acronym } {#2} \bool_new:c { g__acro_#1_first_use_bool } @@ -2678,9 +3063,9 @@ \acro_define_acronym_macro:n {#1} \tl_clear:N \l__acro_current_key_tl \bool_if:cF { l__acro_#1_short_set_bool } - { \acro_serious_message:nnnn {acro} {missing} {#1} {short} } + { \acro_serious_message:nnn {missing} {#1} {short} } \bool_if:cF { l__acro_#1_long_set_bool } - { \acro_serious_message:nnnn {acro} {missing} {#1} {long} } + { \acro_serious_message:nnn {missing} {#1} {long} } } % -------------------------------------------------------------------------- @@ -2708,7 +3093,7 @@ exclude-classes .tl_set:N = \l__acro_excluded_classes_tl , name .tl_set:N = \l__acro_list_name_tl , header .code:n = - \acro_option_deprecated:nn { header } { heading } + \acro_option_deprecated:nn {header} {heading} \tl_set:Nn \l__acro_list_title_tl {#1} , heading .tl_set:N = \l__acro_list_title_tl , sort .bool_set:N = \l__acro_sort_bool @@ -2727,7 +3112,7 @@ \iow_now:Nx \@auxout { \string \acro@print@list } \bool_if:NT \l__acro_sort_bool { \acro_sort_prop:N \l__acro_short_prop } - \UseInstance { acro-title } { \l__acro_list_title_tl } + \UseInstance {acro-title} { \l__acro_list_title_tl } { \l__acro_list_name_tl } \cs_if_exist:NTF \acro@printed@list { @@ -2902,14 +3287,27 @@ 2015/05/10 v1.6b - \ProcessKeysPackageOptions , - correct bug http://tex.stackexchange.com/q/236860/ : option `pages = first' works again +2015/08/16 v2.0 - fix https://bitbucket.org/cgnieder/acro/issue/36 + - implement https://bitbucket.org/cgnieder/acro/issue/39 + - implement https://bitbucket.org/cgnieder/acro/issue/40 + (=> new option `group-cite-cmd') + - add ideas for https://bitbucket.org/cgnieder/acro/issue/41 + - implement https://bitbucket.org/cgnieder/acro/issue/18 + - implement https://bitbucket.org/cgnieder/acro/issue/43 + - further generalization for defining user commands: + \NewAcroCommand, \NewPseudoAcroCommand and siblings + - bug fix in indefinite versions with first-upper + - add `short--form' equivalent to + `long--form' + (https://bitbucket.org/cgnieder/acro/issue/44) + - implement https://bitbucket.org/cgnieder/acro/issue/35 + - new option `single-form' % -------------------------------------------------------------------------- +update => http://tex.stackexchange.com/questions/236362 + % TODO: -- issue 18: https://bitbucket.org/cgnieder/acro/issue/18 - extend option `macros' to also define uppercase macros, possibly as a choice -- https://bitbucket.org/cgnieder/acro/issue/18 -- options user1, user2, user3? (Genitiv lang, Akkusativ lang,...) Bsp: ``des - Bundesinstituts für Risikobewertung'' - Option `totoc'!? - revise list styles to allow _full_ customization by creating own instances! this probably needs a handfull of macros that give access to the entries -- cgit v1.2.3