8

I'm trying to create references between two documents. Normally it works great, but I can't figure out why using siunitx inside a chapter name, causes build errors.

Simple example:

doc1.tex

\documentclass{book}
\usepackage{siunitx,xr-hyper,hyperref,lipsum}
\sisetup{detect-all=true}
\externaldocument{doc2}
\begin{document}
\chapter{Test \SI{1}{\GeV}}
\label{chap:test1}
\lipsum[1]
\ref{chap:test2}
\end{document}

doc2.tex

\documentclass{book}
\usepackage{siunitx,xr-hyper,hyperref,lipsum}
\externaldocument{doc1}
\begin{document}
\chapter{Test \SI{2}{\GeV}}
\label{chap:test2}
\lipsum[1]
\ref{chap:test1}
\end{document}

Build sequence

$ pdflatex doc1.tex
...(no errors)
$ pdflatex doc2.tex
! Undefined control sequence.
<argument> Test \SI {1}{\GeV 
                             }\relax 

I've narrowed it down to when externaldocument opens doc1.aux, it errors on the last line:\newlabel{chap:test1}{{1}{1}{Test \SI {1}{\GeV }\relax }{chapter.1}{}} properly.

Is there some way to make it parse the aux file properly?

9

Package xr-hyper expands the label contents. A better replacement for xr-hyper is zref-xr that also can import and export LaTeX labels:

\documentclass{book}
\usepackage{siunitx,hyperref,lipsum}

\usepackage{nameref,zref-xr}
\zxrsetup{toltxlabel}
\zexternaldocument*{doc1}

\begin{document}
\chapter{Test \SI{2}{\GeV}}
\label{chap:test2}
\lipsum[1]
\ref{chap:test1}, \nameref{chap:test1}
\end{document}

Package nameref should be loaded before \zexternaldocument, because it changes the internal reference format. hyperref loads nameref later in \begin{document}.

  • What exactly is it that zref-xr does differently in this regard? Because when using TeX4ht, \Configure{xr} with a custom Link command as per cvr.cc/?p=362 is apparently ignored. The link text is correct, though. – pazathoth Apr 10 '18 at 14:34
6

add

 \let\GeV\relax

to each document before the call to \externaldocument

and it should run without error.

3

nameref's \GetTitleString retrieves the sectional title and stores it in \@currentlabelname. You can override this before making the \label so that it doesn't include the macro contents from siunitx. The macro \updatelabelname{<new name>} below does this:

\makeatletter
\newcommand*{\updatelabelname}[1]{% For correcting \@currentlabelname, if needed
  \xdef\@currentlabelname{#1}}
\makeatother

Include the above in both documents and use

doc1.tex

\chapter{Test \texorpdfstring{\SI{1}{\GeV}}{1 GeV}}
\updatelabelname{Test 1 GeV}

doc2.tex

\chapter{Test \texorpdfstring{\SI{2}{\GeV}}{2 GeV}}
\updatelabelname{Test 2 GeV}

Also note the use of \texorpdfstring to correctly switch between TeX-related (like ToC) and PDF content (like bookmarks), in general.

  • Thanks for the insight on using \texorpdfstring. – h0tw1r3 Oct 17 '12 at 14:51

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.