hyperref
hyperref copied to clipboard
nameref: not working for float labels defined via \caption{...\label{...}}
The manuals of the longtable and xltabular packages specify that labels for tables should be defined in the form \caption{...\label{...}}. This seems not to work with nameref. For a MWE, see https://github.com/Ri-Ga/keyvaltable/issues/2#issuecomment-716180030.
well nameref basically doesn't work with captions at all. It contains a patch for \LT@c@ption but this only catches the title at the end, so yes the label must be currently outside.
I don't see an easy way to extend the nameref patch (and I would be wary to do it anyway, imho patching external packages isn't the right way to handle this). But you could perhaps ask the caption author. He seemed to have extended standard captions to work with nameref, so he could perhaps improve the longtable caption too.
Sorry the comment about standard captions was nonsense, my local version of nameref is faulty.
Though I personally don't like the syntax where a label is placed into the argument of \section, \caption and the like it is the recommended solution (I think even in Lamport's book) for solving spacing and processing problems with the label in certain circumstances. So arguably it would be nice if that syntax is not broken by nameref making it, for example, incompatible with longtable.Where to best solve that is, of course, an open question.
Getting nameref to work for a label only requires to define \@currentlabelname suitably, where "suitably" means that the text should be so that it can be writtten to aux, and commands like a \label command are removed. This can be done with \NR@gettitle , with \GetTitleString directly (it is used by \NR@gettitle, or even with \text_purify:n. (Thinking about it: text_purify would remove robust commands, so it is not the best idea here).
The problem with longtable is that standard pretocmd/apptocmd-patches don't work here: As the caption is using \multicolumn prepending code gives \omit errors, and appending is too late if the label is in the argument.
Imho the best would be if longtable would change its caption command to define \@currentlabelname. And even better would be if more commands would set \@currentlabelname on their own, then nameref wouldn't have to patch them.
\documentclass{article}
\usepackage{nameref}
\begin{document}
\makeatletter
\NR@gettitle{some text with Grüße and some label\label{foo}}%
some text even with Grüße and some label\label{foo}
This is the reference:
\nameref{foo}
\ExplSyntaxOn
\tl_set:Nx\@currentlabelname{\text_purify:n{Some~other~text~with~Grüße~and~~some~label\label{blub}}}
\ExplSyntaxOff
\label{blub}
\nameref{blub}
\GetTitleString{gettitlestring~\label{bar}}%
\let\@currentlabelname\GetTitleStringResult\label{bar}
\nameref{bar}
\end{document}
@FrankMittelbach Well yes, but shouldn't we be thinking like ConTeXt and have the label as an argument to something?
@josephwright my comment this is purely about existing (or in this case not existing) 2e functionality/syntax (not any future interface that may exist one day). One can, of course, take the position that nameref doesn't support that historic syntax and longtable requires it -> so the two don't work together. @davidcarlisle any comments?
@FrankMittelbach it is easy to add the extra code to save the nameref data to longtable's caption I should probably aim to add this in longtable 4.14 (currently in a branch in the latex2e git)
something like ths (from @u-fischer )
\AtBeginDocument{%
\@ifundefined{GetTitleString}%
{\let\LT@set@currentlabelname\@gobble}
{\newcommand\LT@set@currentlabelname[1]{%
\GetTitleString{#1}%
\let\@currentlabelname\GetTitleStringResult}}}
\def\LT@makecaption#1#2#3{%
\LT@mcol\LT@cols c{\hbox to\z@{\hss\parbox[t]\LTcapwidth{%
\LT@set@currentlabelname{#3}%
\sbox\@tempboxa{#1{#2: }#3}%
\ifdim\wd\@tempboxa>\hsize
#1{#2: }#3%
\else
\hbox to\hsize{\hfil\box\@tempboxa\hfil}%
\fi
\endgraf\vskip\baselineskip}%
\hss}}\LT@set@currentlabelname{#3}%
}
@davidcarlisle well not completly easy, as I missed the optional argument, so \caption[abc]{long} should store the abc, which it doesn't yet.
@u-fischer sure, that's just details:-)
The harder part are usual issues of then checking we don't break caption or ltcaption or other packages that are adjusting the caption behaviour here.
The harder part are usual issues of then checking we don't break
captionorltcaptionor other packages that are adjusting the caption behaviour here.
true, but this suggest that that new longtable version sitting in some branch for a long time should be soon moved to develop so that there are several months in which any adjustments necessary could be sorted well before the spring release, no?
@FrankMittelbach yes I hope to move lt 4.14 to tools-dev before end of year