[Tex/LaTex] Cross-referencing between local files with \href

cross-referencingexternal fileshyperrefxr

I am struggling with the creation of cross-references between different files. What I want to do is the following. I want to create two separate documents (books). One of the documents (doc1) will include exercises, and the other document (doc2) will provide the solutions to these exercises. What I want is to create a link after each exercise in doc1 that would say something like: "the solution is here", and when you click on "here", it opens doc2 and takes you to the solution of the exercise.

Similarly, in doc2 there would be a header for each exercise solution stating "this is the solution to exercise x", and when you click on x, it would take you back to doc1 right at the beginning of the exercise.

I looked at many related topics on this forum, and with what I found I thought at first I could do the job with a combination of the hyperref and xr-hyper packages. I tried with something like this:

doc1:

\documentclass[11pt,a4paper,fleqn]{book}
\usepackage{xr-hyper}
\externaldocument[doc2-]{doc2}
\usepackage{hyperref} 
\usepackage[nopar]{lipsum} 

\begin{document}

\lipsum[1-6]
\\ \\
This is exercise 1 \label{ex1} \\
\lipsum[1-6] \\
Solution is \href{doc2.pdf#correx1}{\textbf{here}}.
\\ \\
This is exercise 2 \label{ex2} \\
\lipsum[1-6] \\
Solution is \href{doc2.pdf#correx2}{\textbf{here}}.
\\ \\
\lipsum[1-6]

\end{document} 

and doc2:

\documentclass[11pt,a4paper,fleqn]{book}
\usepackage{xr-hyper}
\externaldocument[doc1-]{doc1}
\usepackage{hyperref}
\usepackage[nopar]{lipsum}

\begin{document}

\lipsum[1-6]
\\ \\
This is the solution to exercise \href{doc1.pdf#ex1}{1} \label{correx1} \\
\lipsum[1-6]
\\ \\
This is the solution to exercise \href{doc1.pdf#ex2}{2} \label{correx2} \\
\lipsum[1-6]
\\ \\
\lipsum[1-6]

\end{document} 

In a sense, it works: the hyperlinks are created, and they do open the other document. However, when clicking on the link, it does not lead to the \ref-erenced label, but rather to some random spot of the document. This ruins the whole thing.

Would you have any suggestion?

Best Answer

This is simply a proof of concept and needs to be refined, but it works as required and illustrates the relevant methods.

You should create a new, empty directory, and then save the following three files under that one directort, with the names specified below.


Contents of file CommonMacros.tex:

\newcommand*{\SolutionBook}{SoluBook.pdf}
\newcommand*{\ExerciseBook}{MainBook.pdf}

\newcommand*{\exercisename}[1]{Exercise~#1.}
\newcommand*{\exercisecategory}{exercise}
\newcommand*{\solutionname}[1]{Solution of Exercise~#1.}
\newcommand*{\solutioncategory}{solution}

% In the following two commands, #1 stands for the part that is to be made
% clickable:
\newcommand*{\seeexercisephrase}[1]{See exercise #1.}
\newcommand*{\seesolutionphrase}[1]{See solution #1.}
\newcommand*{\herename}{here}

\newcommand*{\exesolubreak}{%
    \addpenalty{-200}%
    \addvspace{\bigskipamount}%
}

\newcounter{exercise}[section]
\renewcommand*{\theexercise}{\thesection.\arabic{exercise}}
\newenvironment*{exercise}{%
    \exesolubreak
    \noindent
    \refstepcounter{exercise}%
    \hyperdef{\exercisecategory}{\theHexercise}%
        {\textbf{\exercisename{\theexercise}}}%
    \nobreak\quad
    \ignorespaces
}{%
    \par
    \nobreak\smallskip
    \begingroup
        \footnotesize
        \noindent
        \seesolutionphrase{%
            \hyperref{\SolutionBook}{\solutioncategory}{\theHexercise}%
                {\herename}%
        }%
        \par
    \endgroup
    \addvspace{\bigskipamount}%
}

% In a real-life example, the two books would "communicate" through some sort 
% of auxiliary file; here, we assume that each solution correspond to the 
% exercise with the same number.
\newcounter{solution}[section]
\renewcommand*{\thesolution}{\thesection.\arabic{solution}}
\newenvironment*{solution}{%
    \exesolubreak
    \noindent
    \refstepcounter{solution}%
    \hyperdef{\solutioncategory}{\theHsolution}%
        {\textbf{\solutionname{\thesolution}}}%
    \nobreak\quad
    \ignorespaces
}{%
    \par
    \nobreak\smallskip
    \begingroup
        \footnotesize
        \noindent
        \seeexercisephrase{%
            \hyperref{\ExerciseBook}{\exercisecategory}{\theHsolution}%
                {\herename}%
        }%
        \par
    \endgroup
    \addvspace{\bigskipamount}%
}

Contents of file MainBook.tex:

% My standard header for TeX.SX answers:
\documentclass[a4paper]{article} % To avoid confusion, let us explicitly 
                                 % declare the paper format.

\usepackage[T1]{fontenc}         % Not always necessary, but recommended.
% End of standard header.  What follows pertains to the problem at hand.

\usepackage{hyperref}
\usepackage{lipsum}

\input{CommonMacros}



\begin{document}

\section{Some argument}

\lipsum[1-2]

\begin{exercise}
    \lipsum*[\arabic{exercise}]
\end{exercise}

\lipsum[3]

\begin{exercise}
    \lipsum*[\arabic{exercise}]
\end{exercise}

\lipsum[4-6]

\begin{exercise}
    \lipsum*[\arabic{exercise}]
\end{exercise}

\lipsum[7-8]

\begin{exercise}
    \lipsum*[\arabic{exercise}]
\end{exercise}

\lipsum[9]

\begin{exercise}
    \lipsum*[\arabic{exercise}]
\end{exercise}



\section{Another argument}

\lipsum[10]

\begin{exercise}
    \lipsum*[1\arabic{exercise}]
\end{exercise}

\lipsum[11-12]

\begin{exercise}
    \lipsum*[1\arabic{exercise}]
\end{exercise}

\lipsum[13]

\begin{exercise}
    \lipsum*[1\arabic{exercise}]
\end{exercise}

\lipsum[14]

\begin{exercise}
    \lipsum*[1\arabic{exercise}]
\end{exercise}

\lipsum[15-16]

\begin{exercise}
    \lipsum*[1\arabic{exercise}]
\end{exercise}

\end{document}

Contents of file SoluBook.tex:

% My standard header for TeX.SX answers:
\documentclass[a4paper]{article} % To avoid confusion, let us explicitly 
                                 % declare the paper format.

\usepackage[T1]{fontenc}         % Not always necessary, but recommended.
% End of standard header.  What follows pertains to the problem at hand.

\usepackage{hyperref}
\usepackage{lipsum}

\input{CommonMacros}



\begin{document}

\section{Some argument}

\begin{solution}
    \lipsum*[\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[\arabic{solution}]
\end{solution}



\section{Another argument}

\begin{solution}
    \lipsum*[1\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[1\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[1\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[1\arabic{solution}]
\end{solution}

\begin{solution}
    \lipsum*[1\arabic{solution}]
\end{solution}

\end{document}

Now, compile the files MainBook.tex and SoluBook.tex. Ignore warnings about duplicate destinations, they are absolutely normal since more than one exercise/solution winds up on the same page. The resulting two files MainBook.pdf and SoluBook.pdf should exhibit the requested behavior.