\ nameref usando texto 'não expandido'?
Suponha que eu defina um comando personalizado da \exerciseseguinte maneira.
\newcounter{exercise}
\newcommand\exercise{%
\refstepcounter{exercise}%
\section*{Exercise \theexercise}%
}
Agora, no exemplo a seguir, quero usar \namerefdo hyperrefpacote.
\exercise\label{ex:first}
foo
\exercise\label{ex:second}
see \nameref{ex:first}
\exercise\label{ex:third}
bar
Isso produz "consulte o Exercício 2" em vez de "consulte o Exercício 1". Parece que o texto 'não expandido' é usado, expandindo para o valor do contador atual. Como posso ter certeza de que \nameref{ex:first}produz o "Exercício 1"?
(Claro, eu poderia apenas usar Exercise~\ref{ex:first}, mas isso é mais sujeito a erros. E, no futuro, posso querer substituir "exercício" por "problema" sem ter que localizar e substituir todas as ocorrências em meu documento.)
Exemplo completo:
\documentclass{article}
\usepackage{hyperref}
\newcounter{exercise}
\newcommand\exercise{%
\refstepcounter{exercise}%
\section*{Exercise \theexercise}%
}
\begin{document}
\exercise\label{ex:first}
foo
\exercise\label{ex:second}
see \nameref{ex:first}
\exercise\label{ex:third}
bar
\end{document}
Respostas
Na verdade, você precisa passar a expansão de \theexercise, porque hyperrefnão faz isso para o título.
\documentclass{article}
\usepackage{hyperref}
\newcounter{exercise}
\newcommand\exercise{%
\par % just in case
\refstepcounter{exercise}%
\begingroup\edef\x{\endgroup
\noexpand\section*{\unexpanded{Exercise} \theexercise}%
}\x
}
\begin{document}
\exercise\label{ex:first}
foo
\exercise\label{ex:second}
see \nameref{ex:first}
\exercise\label{ex:third}
bar
\end{document}
Este é o conteúdo (resumido) do .auxarquivo:
\newlabel{ex:first}{{1}{1}{Exercise 1}{section*.1}{}}
\newlabel{ex:second}{{2}{1}{Exercise 2}{section*.2}{}}
\newlabel{ex:third}{{3}{1}{Exercise 3}{section*.3}{}}
Era
\newlabel{ex:first}{{1}{1}{Exercise \theexercise }{section*.1}{}}
\newlabel{ex:second}{{2}{1}{Exercise \theexercise }{section*.2}{}}
\newlabel{ex:third}{{3}{1}{Exercise \theexercise }{section*.3}{}}
com o seu código.
Nota. Porque \unexpanded{Exercise}? No caso particular é obviamente desnecessário, mas seria para o alemão “Übung”.
Você pode usar em seu clevereflugar.
\documentclass{article}
\usepackage{hyperref}
\usepackage[nameinlink]{cleveref}
\newcounter{exercise}
\newcommand\exercise{%
\par % just in case
\refstepcounter{exercise}%
\section*{Exercise \theexercise}
}
\crefname{exercise}{Exercise}{Exercises}
\begin{document}
\exercise\label{ex:first}
foo
\exercise\label{ex:second}
see \cref{ex:first}
\exercise\label{ex:third}
bar
\end{document}
A saída é a mesma em ambos os casos.
Podemos evitar o \edef\x{\endgrouptruque? Sim, claro.
\documentclass{article}
%\usepackage{xparse} % not needed for LaTeX 2020-10-01 or later
\usepackage{hyperref}
\usepackage[nameinlink]{cleveref}
\ExplSyntaxOn
\NewDocumentCommand{\exercise}{}
{
\gooz_exercise:ne { \exercisename } { \theexercise }
}
\cs_new_protected:Nn \gooz_exercise:nn
{
\par % just in case
\refstepcounter{exercise}
\section*{#1~#2}
}
\cs_generate_variant:Nn \gooz_exercise:nn { ne }
\ExplSyntaxOff
\newcommand{\exercisename}{Exercise}
\newcounter{exercise}
\crefname{exercise}{\exercisename}{\exercisename s}
\begin{document}
\exercise\label{ex:first}
foo
\exercise\label{ex:second}
see \cref{ex:first} or \nameref{ex:first}
\exercise\label{ex:third}
bar
\end{document}
Observe que cleverefnão é necessário, apenas remova as chamadas relevantes se preferir \nameref.