我想通过提供页码来引用文本的某个片段。我正在寻找一种灵活的方法:有时这将是单个页面,有时是一个页面范围,因此仅使用标签和 \pageref 是不够的。我发现有两个包可用于处理这个问题:varioref 和 cleveref。但是,我希望输出仅包含页码,仅此而已。我不知道如何使用这些包(或以其他方式)实现这一点。例如,这里我们可以看到 \vpagerefrange 输出的是“on pages 1-2”。相反,我希望只有数字,即只有“1-2”,而没有“on pages”。同样,这里我们可以看到 \cpagerefrange 产生了“第 1 至 3 页”,而我想要的只是“1-3”。
或者,我希望能够自定义显示的文本,例如使用“pp.”(如果是多页)或“p.”(如果是单页)而不是“on pages/on page”。
以下是 MWE:
\documentclass{article}
\usepackage{varioref}
\usepackage[english]{babel}
\begin{document}
\label{text1start}some text
\newpage
more text \label{text1stop}
\newpage
See \vpagerefrange{text1start}{text1stop}
\end{document}
它在第 3 页生成“参见第 1-2 页”;我想自定义这个结果,例如“参见第 1-2 页”。
答案1
在您已经找到的与您的问题相关的软件包中,我认为cleveref
显然是更合适的软件包。varioref
也可以产生范围,但其目的不同,它是根据标签和引用的相对位置产生上下文页面引用。
cleveref
\cpagerefrange
可以使用或 来处理范围\cpageref
。但是,\cpagerefrange
即使页面相同(如“1-1”),也始终会生成一个范围。并且\cpageref
只有在有两个以上的标签时才会生成一个范围。您可以cleveref
通过在 duplicity 中设置标签来使用一些小技巧。(您还必须处理与页面引用范围相关的长期错误,请参阅https://tex.stackexchange.com/a/620066/105447)。
\documentclass{article}
\usepackage[english]{babel}
\usepackage{cleveref}
\crefname{page}{p.}{pp.}
\Crefname{page}{p.}{pp.}
\crefrangeformat{page}{pp.~#3#1#4--#5#2#6}
\Crefrangeformat{page}{pp.~#3#1#4--#5#2#6}
% Fix for pending bug: https://tex.stackexchange.com/a/620066/105447
\makeatletter
\newcommand*{\@setcpagerefrange}[3]{%
\@@setcpagerefrange{#1}{#2}{cref}{#3}}
\newcommand*{\@setCpagerefrange}[3]{%
\@@setcpagerefrange{#1}{#2}{Cref}{#3}}
\newcommand*{\@setlabelcpagerefrange}[3]{%
\@@setcpagerefrange{#1}{#2}{labelcref}{#3}}
\makeatother
\begin{document}
\label{text1start}\label{text1startb}some text
\newpage
more text \label{text1stop}
\newpage
See \cpageref{text1start,text1startb,text1stop}
\end{document}
但这种滥用的尝试\cpageref
也是有问题的,因为如果标签所在的页面之间存在间隙,它就会失败,因为\cref
只有\cpageref
当中间值存在时,才会构建范围。因此,例如,如果您的标签位于第 1 页和第 3 页,您将得到“参见第 1 页和第 3 页”。
鉴于此,也许zref-clever
是一种合适的替代方案。它与引用具有总体相似的概念cleveref
(正如名称所暗示的那样),但它对范围的方法略有不同。与使用专门的范围命令(如\crefrange
和\cpagerefrange
)不同,范围是使用range
传递给的选项构建\zcref
的,从中我们可以受益于排序、压缩、任意数量的标签等,它将从极端构建一个范围(但如果是单个则不是这样,在这种情况下您会收到警告但预期的输出,并且根据配置,它还可以区分“对”)。在实践中:
\documentclass{article}
\usepackage[english]{babel}
\usepackage{zref-clever}
\zcLanguageSetup{english}{
type=page,
name-sg=p.,
Name-sg=p.,
name-pl=pp.,
Name-pl=pp.,
% these are defaults for page, but being explicit about your requirements.
rangesep = {\textendash} ,
rangetopair = false ,
}
\begin{document}
\section{Section 1}
\zlabel{text1start}some text
\newpage
more text \zlabel{text1stop}
\newpage
See \zcpageref[range]{text1start,text1stop} or
\zcref[page,range]{text1start,text1stop}.
% You can also omit the name on demand with the 'noname' option.
See \zcref[page,range,noname]{text1start,text1stop}.
\newpage
\section{Section 2}
% It will also work for labels in the same page.
\zlabel{text2start}some text
more text \zlabel{text2stop}
\newpage
See \zcpageref[range]{text2start,text2stop}.
\newpage
\section{Section 3}
% And also when the labels are not in contiguous pages.
\zlabel{text3start}some text
\newpage
mid page
\newpage
more text \zlabel{text3stop}
\newpage
See \zcpageref[range]{text3start,text3stop}.
\end{document}
关于标签放置的说明。您可能知道,在文本中的任意位置设置的标签将从设置它的最后一个文档对象中检索标签信息。页面引用将按预期工作,但如果您需要标签中的任何其他内容“属于设置它的位置”,您可以在hyperref
每个\phantomlabel
标签前使用 。
编辑:额外奖励,还可以使用refcount
标准标签来处理任务:
\documentclass{article}
\usepackage[english]{babel}
% 'refcount' is required by 'hyperref', if you are already using it, you don't
% need to load it.
\usepackage{refcount}
\ExplSyntaxOn
\NewDocumentCommand{\mypagerange}{mm}{
\exp_args:Nee \tl_if_eq:nnTF
{ \getpagerefnumber {#1} }
{ \getpagerefnumber {#2} }
{ p.~\pageref{#1} }
{ pp.~\pageref{#1}--\pageref{#2} }
}
\ExplSyntaxOff
\begin{document}
\section{Section 1}
\label{text1start}some text
\newpage
more text \label{text1stop}
\newpage
See \mypagerange{text1start}{text1stop}.
\newpage
\section{Section 2}
% It will also work for labels in the same page.
\label{text2start}some text
more text \label{text2stop}
\newpage
See \mypagerange{text2start}{text2stop}.
\newpage
\section{Section 3}
% And also when the labels are not in contiguous pages.
\label{text3start}some text
\newpage
mid page
\newpage
more text \label{text3stop}
\newpage
See \mypagerange{text3start}{text3stop}.
\end{document}