Sometimes in my document I wish to use an acronym. Sometimes I want the acronym to appear in title case (for example if it appears in a title).*
*I need this to work in all environments, not specifically titles.
Variants on this question have been asked all over the site, however none of the proposed solutions actually work. The closest example is one that would require me to rewrite my entire glossary file, something I am unwilling to do, as it is shared by other documents and other people.
Three solutions proposed use titlecaps, mfirstuc, and stringstrings, however none of them work on acronyms.
\documentclass{article}
\usepackage{glossaries}
\usepackage{titlecaps}
\usepackage{mfirstuc}
\usepackage{stringstrings}
\newacronym{srs}{SRS}{spaced repetition system}
\begin{document}
\titlecap{\gls{srs}}
\capitalisewords{\gls{srs}}
\capitalizetitle{\gls{srs}}
\end{document}
Without having to modify my glossary, and preferably without having to include a huge wodge of impenetrable code in my tex file, how can I capitalise the first letter of an acronym sometimes?
EDIT: For clarity I am looking for a way to get
Spaced Repetition System
and not Spaced repetition system
, or SPACED REPETITION SYSTEM
.
Best Answer
\capitialisewords
works by applying\makefirstuc
to each space-separated element of its argument. In the case of\capitalisewords{\gls{src}}
, there are no spaces in the argument, so it simply does\makefirstuc{\gls{src}}
.\makefirstuc
applies a set of rules when deciding how to change the case:\protect
, in which case it's discarded and the rules are reapplied).Examples:
\makefirstuc{\emph{word}}
becomes\emph{\uppercase word}
(first case)\makefirstuc{\oe-ligature}
becomes\uppercase\oe-ligature
(second case)\makefirstuc{word}
becomes\uppercase word
(The uppercasing command used is actually
\mfirstucMakeUppercase
, which may be defined as\MakeUppercase
or\MakeTextUppercase
.)So
\makefirstuc{\gls{src}}
comes under the first case. This means that it tries to do\gls{\uppercase src}
. That is, it tries to change the case of the label.If the actually text that requires case-changing is hidden within the argument of
\makefirstuc
(or\capitialisewords
) the first letter can't be accessed. Since\gls
is robust, it can't even be expanded before being passed as the argument. This is why theglossaries
package provides\Gls
, because the case-changing has to be performed deep inside the internals of the command.I don't know how similar packages deal with the presence of formatting commands (such as
\emph
) within the text that needs to have its case-changed, but none of them will be able to access the text if it's embedded within a robust command.The only solution here is to use one of the expandable commands like this:
This actually works better in page headings, as you're unlikely to want each page header added to the location list for the entry, which is what can happen if you use
\gls
in a section or chapter heading. (See Why shouldn't I use commands like \gls in \section, \chapter, \caption etc?)You can, of course, define a custom command, such as:
or (index and hyperlink)
Edit:
Take care using
\ecapitialisewords
as it fully expands the argument, which can have unexpected results if the text contains commands. For example:This superficially looks like case 1 with
\strong{spaced}
, but full expansion means that it's now attempting to doThis now follows the rules: discard initial
\protect
, then apply case 1, which ends up aswhich is incorrect. There are two solutions. Either only use robust commands:
or first fetch the value of the field and store it in a command using
\glsfetchfield
and then apply\capitialisewords
:There is still a problem here. The value of the
long
key is still fully expanded. (You can show the value using\showglslong{srs}
after you define the entry. This uses\show
on the internal command used to store the value of thelong
field.) This happens because the field expansion is on by default for thelong
key. You can switch this off using\glsnoexpandfields
:This now works correctly.
Note that
\xcapitalisewords
is a shortcut for\expandafter\capitalisewords\expandafter
so you can doAs from
glossaries
v4.22, you can usewhich effectively does the same thing as the
\TCac
example above, but the second argument is the field name (e.g.first
ortext
ordesc
).