19

Is there a way to add the usage of a table/reference in the caption of the reference/table in LaTeX?

For example:

\begin{table}
    \begin{tabular}{ll}
    \textbf{Name} & \textbf{Description} \\
        Foo & bar \\
        Foo & bar
    \end{tabular}
    \caption{Nice Table. Used on pages [2,3,4].}
    \label{tab:table}
\end{table}

I would like the "Used on pages[2,3,4]." to appear automatically and linked to the correct reference, to all the locations in the document that use \ref{tab:table}.

Anyone knows a package that takes care of this?

migrated from stackoverflow.com Apr 5 '11 at 8:18

This question came from our site for professional and enthusiast programmers.

  • Welcome to TeX.sx! Your question was migrated here from another stackexchange site. Please register on this site, too, and make sure that both accounts are associated with each other, otherwise you won't be able to comment on or accept answers or edit your question. – doncherry Sep 4 '11 at 10:31
16

I want to provide two solutions. The first works without using the package hyperref. The second answer supports hyperlinks.

\documentclass{article}
\usepackage{etoolbox,xstring,xspace}
\makeatletter
\let\origref\ref
\renewcommand*\ref[1]{%
  \origref{#1}\xlabel{#1}}
\def\xlabel#1{%
   \ifcsdef{siteref@doc@#1}{}{\csgdef{siteref@doc@#1}{,}}%
    \@bsphack%
       \csxdef{siteref@doc@#1}{\csuse{siteref@doc@#1},\thepage}%
         \protected@write\@auxout{}%
        {\string\SiteRef{siteref@#1}{\csuse{siteref@doc@#1}}}%
     \@esphack%
}

\newrobustcmd*\SiteRef[2]{\csgdef{#1}{#2}}

\newrobustcmd*\xref[1]{%
\ifcsundef{siteref@#1}{%
     \@latex@warning@no@line{Label `#1' not defined}
     }{%
       [\StrGobbleLeft{\csuse{siteref@#1}}{2}]\xspace%
   }%
}
\makeatother
\usepackage{lipsum}
\begin{document}
\ref{tab:table}
\lipsum[1]
\begin{table}[!ht]
    \begin{tabular}{ll}
    \textbf{Name} & \textbf{Description} \\
        Foo & bar \\
        Foo & bar
    \end{tabular}
    \caption{Nice Table. Used on pages \xref{tab:table}.}
    \label{tab:table}
\end{table}

\lipsum
\ref{tab:table}
\end{document}

Modifications to work with hyperref

\documentclass{article}
\usepackage{etoolbox,xstring,xspace}
\usepackage[colorlinks=true]{hyperref}
\makeatletter

\AtBeginDocument{%
\let\origref\ref
\renewcommand*\ref[1]{%
  \origref{#1}\xlabel{#1}}
}
\newrobustcmd*\xlabel[1]{%
   \ifcsdef{siteref@doc@#1}{}{\csgdef{siteref@doc@#1}{,}}%
    \@bsphack%
    \begingroup
       \csxdef{siteref@doc@#1}{\csuse{siteref@doc@#1},\thepage}%
         \protected@write\@auxout{}%
        {\string\SiteRef{siteref@#1}{\csuse{siteref@doc@#1}}}%
     \endgroup
     \@esphack%
}

\newrobustcmd*\SiteRef[2]{\csgdef{#1}{#2}}

\newrobustcmd*\xref[1]{%
\ifcsundef{siteref@#1}{%
     \@latex@warning@no@line{Label `#1' not defined}
     }{%
    \begingroup
      \StrGobbleLeft{\csuse{siteref@#1}}{2}[\@tempa]\relax%
      \def\@tempb{}%
      \@tempcnta=0\relax%
      \@tempcntb=\@ne\relax%
      \def\do##1{\advance\@tempcnta\@ne}%
      \expandafter\docsvlist\expandafter{\@tempa}%
       \def\do##1{%
         \ifnum\@tempcntb=\@tempcnta\relax%
            \hyperpage{##1}%
         \else
            \hyperpage{##1},%
          \fi%
          \advance\@tempcntb\@ne
       }%
       [\expandafter\docsvlist\expandafter{\@tempa}]\xspace%
    \endgroup
   }%
}
\makeatother

\usepackage{lipsum}
\begin{document}
\ref{tab:table}
\lipsum[1]
\begin{table}[!ht]
    \begin{tabular}{ll}
    \textbf{Name} & \textbf{Description} \\
        Foo & bar \\
        Foo & bar
    \end{tabular}
    \caption{Nice Table. Used on pages \xref{tab:table}.}
    \label{tab:table}
\end{table}

\lipsum
\ref{tab:table}
\end{document}

The package crossreference defines the command \xref too. So if you are load the package you have to rename the command \xref.

  • 2
    Awesome answer! However, when I tried it, if I reference something on the page more than once, the same page number will be written out more than once. Is it somehow possible to only print the page number only once? – jaye1234 Jan 9 '13 at 10:44
  • Could you give this older answer of you a quick workover and remove the "Edit" headlines. They should be avoided in general, as they make the answer less readable and normally not required due to the existance of the edit history. – Martin Scharrer Jun 3 '13 at 21:19
  • @MartinScharrer: I did -- I hope it's ok now. – Marco Daniel Jun 3 '13 at 21:22
  • @MarcoDaniel: The "Few minutes ago ..." part still doesn't read good. ;-) Please also state here if this \xref does the same or is simply (and more likely) a macro name collision. In the latter case I wouldn't start the answer with it. – Martin Scharrer Jun 3 '13 at 21:27
2

You can get page numbers by putting labels where the table is used and adding \pageref{..}, but \pageref is "fragile", so must be preceded with a \protect, e.g.,

Table \ref{tab:table}\label{tabuse:table} used here...

then in the caption:

\caption{Nice Table. Used on page \protect\pageref{tabuse:table}.}

A dirty trick for articles is to enter an empty ToC line:

\caption[]{Nice Table. Used on page \pageref{tabuse:table}.}

Your Answer

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