Showing posts with label cleveref. Show all posts
Showing posts with label cleveref. Show all posts

Tuesday, August 07, 2007

cleveref incompatibilities with Elsevier and Springer

elsart problems: If you try using cleveref with any of the elsart packages, you may get this error:
! TeX capacity exceeded, sorry [input stack size=5000].
\cl@part ->\cl@part
\@elt {section}
This is due to a flaw in the elsart packages. They setup some part counters even though part isn't defined. This confuses cleveref. To fix this, add the following anywhere in your preamble:
\makeatletter \let\cl@part\relax \makeatother
Later, you can use cleveref's poorman option to strip all of the cleveref stuff from your document. After that, you can remove this line.

svjour problems: Similarly, if you try combining cleveref with Springer journal support files, you may get this error:
! TeX capacity exceeded, sorry [input stack size=5000].
\cl@chapter ->\cl@chapter
\@elt {theorem}
Again, this is due to a flaw in the Springer packages. They setup some chapter counters even though chapter isn't defined. To fix this, add the following anywhere in your preamble:
\makeatletter \let\cl@chapter\relax \makeatother
Again, this can be removed after cleveref's poorman procedure is applied.

Source and acknowledgments: The Springer solution was given by "Dan" in a comp.text.tex post. I used it to generate the elsart solution.

Wednesday, July 18, 2007

Traditional way to change cleveref defaults

UPDATE: cleveref also includes a set of defaults for the ntheorem package when the ntheorem option is given. I've just put those defaults into cleveref_nthoerem_defaults.tex. Include it with \input{cleveref_ntheorem_defaults.tex} after (or instead of) including the other file.

Because it will probably be a long time until a simpler way of changing cleveref defaults gets implemented, I needed a way to change these defaults without adding tens of lines to my LaTeX source. I came up with cleveref_defaults.tex, which basically contains all of the default lines from the cleveref documentation, plus a set of table defaults. You can include it with:
\input{cleveref_defaults.tex}
Then, go ahead and modify cleveref_defaults.tex to match your conventions (e.g., change the four "eq." to "Eq." and the four "eqs." to "Eqs.").

Protype for simplifying changing cleveref defaults

UPDATE: I have created crefntheoremdefaults.tex, which does this same stuff to the ntheorem package. You have to be sure to include the crefdefaults.tex file first. The files crefntheoremdefault_constants.tex and crefntheoremdefault_formats.tex play a similar role as the analogous ones below.

I think the package cleveref is great. In fact, I think it has much of what has been missing from LaTeX for a long time. See its documentation for more information about the package.

My only gripe about cleveref is that it is tedious to change something like all of the default "eq." and "eqs." to "Eq." and "Eqs.", respectively. So I put together these scripts as a kind of proof of concept (they also setup cleveref to handle table references, something that is not done by default at the moment):

The first script, crefdefaults.tex, is simply crefdefault_constants.tex concatenated with crefdefault_formats.tex. Therefore,
\input{crefdefaults.tex}
is equivalent to
\input{crefdefault_constants.tex}
\input{crefdefault_formats.tex}
However, if the poorman option is used and the corresponding sed script is applied, the resulting file will need to have the content of crefdefault_formats.tex removed; crefdefault_constants.tex should not be removed. In other words, if you are planning on using poorman, use the 2-line include and comment the crefdefault_formats.tex line out of the script that results from the sed script.

What's the outcome of this? I can now do
\renewcommand{\crefenumilabelformat}[3]{\textup{(#2#1#3)}}
in order to change every item reference so that it is surrounded by upright round braces. Additionally, changing "eq." to "Eq." and "eqs." to "Eqs." is as simple as it was in hyperref (for use with \autoref); that is, it is these two lines:
\renewcommand{\crefequationname}{Eq.}
\renewcommand{\crefpluralequationname}{Eqs.}
Unfortunately, the output of the poorman sed filter is a little messy. However, if these are someday integrated into cleveref, that could be fixed. There are other shortcuts built into crefdefaults.tex as well. It probably requires documentation, but it's just a prototype for now.

Good idea? Bad?

Monday, July 09, 2007

\cref* and \crefrange*: temporarily disable cleveref hyperlinks

UPDATE: I've e-mail chatted with the author of cleveref, and it sounds like the changes below (the * macros and the new defaults) may get built into the next release. So that's exciting. The author has recently sent me new versions of cleveref that include these suggestions. Only time will tell when it's on CTAN. So that's exciting.

I've also had a chance to reflect on the poorman option of cleveref. It's an interesting idea. When loaded with this option, cleveref will generate a sed script that the author can use on the source files that will change each of the cleveref macros into old-fashioned references with everything typed out. That is, if you have a journal that does not support cleveref, you run sed on your source code before uploading it, and your journal works with the resulting files that are stripped of cleveref code. That's pretty clever.

I think that by the 1.0 version of cleveref package, it will be ready to replace hyperref's \autoref macro.

One thing that hyperref gives you that cleveref does not are starred versions of the referencing commands that disable hyperlinks. For example, in hyperref, \ref* and \autoref* work exactly like \ref and \autoref but are not hyperlinked. That's nice. Of course, there is no \Autoref or \autorefs or \Autorefs.

A major nice thing that cleveref does is let you format your expanded references with more detail than hyperref. For example, you can make an equation reference expand as "Equation (1)" where the "1" gets linked while having a figure reference expand as "Fig. 1" with the whole "Fig. 1" linked. Of course, this assumes that you've loaded both cleveref and hyperref, like this:
\usepackage{hyperref}
\usepackage[hyperref]{cleveref}
Additionally, cleveref does give the equivalent of those special versions of \autoref. cleveref supports single and multiple references, including reference ranges.

So consider the following, which gives you all the nice stuff about cleveref but also adds starred versions of its macros:
\makeatletter

% \cref and \cref*
\let\origcref\cref
\newcommand{\crefstar}[1]
{\begin{NoHyper}\origcref{#1}\end{NoHyper}}
\renewcommand{\cref}{\@ifstar{\crefstar}{\origcref}}

% \crefrange and \crefrange*
\let\origcrefrange\crefrange
\newcommand{\crefrangestar}[2]
{\begin{NoHyper}\origcrefrange{#1}{#2}\end{NoHyper}}
\renewcommand{\crefrange}
{\@ifstar{\crefrangestar}{\origcrefrange}}

% \Cref and \Cref*
\let\origCref\Cref
\newcommand{\Crefstar}[1]
{\begin{NoHyper}\origCref{#1}\end{NoHyper}}
\renewcommand{\Cref}
{\@ifstar{\Crefstar}{\origCref}}

% \Crefrange and \Crefrange*
\let\origCrefrange\Crefrange
\newcommand{\Crefrangestar}[2]
{\begin{NoHyper}\origCrefrange{#1}{#2}\end{NoHyper}}
\renewcommand{\Crefrange}
{\@ifstar{\Crefrangestar}{\origCrefrange}}

\makeatother
So there you go! That nearly beats \autoref!

Why nearly? Unfortunately, cleveref breaks some Springer journal document classes. The author also doesn't claim that it does or does not support item labels (he mentions that it may or may not, so it's uncertain). Finally, I don't like the default choices for some of the label formats. For example, you shouldn't ever start a sentence with an abbreviation, and the parentheses that go around equation numbers should be surrounded by \textup to keep them from looking silly in an italicized theorem environment. That's why I'm saying that by the 1.0 version (it was 0.6 since June of 2007), it should be a pretty awesome package... especially if the modifications above are built into the package.