这是我用来隐藏图形的环境的简化版本,仅显示标题。
其中一个挑战是,我不仅想忽略\includegraphics
,还想忽略围绕各个图形排列的整个表格结构。同时,标签和子标签仍应可访问。为什么这很难?因为这会打印??
,因此\phantom
不会使其参数中的标签可访问:
\documentclass{article}
\begin{document}
\begin{figure}
\caption{Label}
\phantom{\label{label}}
\end{figure}
\ref{label}
\end{document}
\phantom
[有没有不存在该问题的版本?]
我想,这就是我解决问题的方法。但是,在这个例子中, 中的子标签tabularx
被称为 b,而 a 是正确的。(我将其与endfloat
和其他几个包结合在一起,因此很难用旧版本的代码完全重现相同的问题。使用 时,问题确实出现在我的大文档中endfloat
,但没有 时则不会出现。我不确定我如何在没有 的情况下将其简化为这个 MWE endfloat
。此外,问题不会出现在tabular
或中tabular*
,我碰巧在手稿修订之间从一个切换到另一个。)
那么,简而言之:使用时出了什么问题tabularx
?
收到关于多次定义标签的警告(aux
文件证实了这一点),我怀疑使用 tabularx 时,输入以某种方式被处理了两次。经过进一步调试,似乎\envlabels
只设置了一次(即\g@addto@macro
只执行了一次),也只执行了一次;但它的内容重复了:使用
\renewcommand{\label}[1]{
\typeout{This is printed once.}
\g@addto@macro\envlabels{
\typeout{But this is printed twice.}
\orgsubfloat{\label{####1}}}}
和
macro:->\orgsubfloat {\label {subfloat}}\orgsubfloat {\label{subfloat}}
怎么会这样呢?
这是我的(大大简化的)代码:
\documentclass{article}
\usepackage{newenviron}
\usepackage{tabularx}
\usepackage{subfig}
\makeatletter
\newenviron{hidecontent}{
\gdef\envlabels{}
\let\orgsubfloat=\subfloat
\renewcommand{\subfloat}[2][]{
\renewcommand{\label}[1]{
\g@addto@macro\envlabels{\orgsubfloat{\label{####1}}}}
##2}
\begin{figure}
\phantom{\envbody}
\envlabels
\end{figure}}{}
\begin{document}
Subfloat \subref{subfloat} is wrong, it should be (a).
\begin{hidecontent}
\begin{tabularx}{\linewidth}{l}
\subfloat{\label{subfloat}}
\end{tabularx}
\end{hidecontent}
\end{document}
答案1
广告问题 1:\label
内部发生的事件\phantom
无法访问
\label
放置在\phantom
s 内部的 s 无法访问的原因是:
该\label
命令确实会触发将信息写入辅助文件。
\protected@write
用于此目的。
\protected@write
确实会触发以\immediate
延迟方式而不是时尚方式写入内容。 这意味着: 当遇到写入指令时,不会立即写入内容,而是在处理构造过程中\write
发生相关命令的框并根据输出例程将其发送出/写入 .pdf 文件/.dvi 文件时写入内容。 (这样做是有原因的:例如,在构造框时通常不知道页码,但在输出例程准备页面时知道页码\shipout
。 诸如还将页码写入辅助文件之类的事情\label
,以便您可以\pageref
在连续的 latex 运行/再次编译文档时进行引用。)
所有\phantom
东西都放在一个盒子里,这个盒子永远不会运出,因为它只用于测量,然后创建另一个相同尺寸的空盒子。
因此,一种方法是重新定义\protected@write
以将其自己的调用添加到某些宏的定义中并在外部调用该宏\phantom
:
\documentclass{article}
\makeatletter
\newcommand\phantomWithDelayedWrites[1]{%
\begingroup
\gdef\CollectedCallsToProtected@write{}%
\long\def\protected@write##1##2##3{%
\g@addto@macro\CollectedCallsToProtected@write{\protected@write{##1}{##2}{##3}}%
}%
\phantom{#1}%
\expandafter\endgroup\CollectedCallsToProtected@write
}%
\makeatother
\begin{document}
\newcounter{mycounter}
\setcounter{mycounter}{9}
\begin{figure}
\caption{Label}%
A\phantomWithDelayedWrites{ Text Text \label{label} Text Text \stepcounter{mycounter}}B%
A Text Text Text Text B%
\end{figure}
Reference to figure 1 even while the correesponding \verb|\label|-command occured
inside \verb|phantom|: \ref{label}
By the way: Did you realize that counters etc get stepped inside \verb|\phantom|?
If this was not the case, then \verb|mycounter| would still have the value \verb|9|
but it has value {\csname verbatim@font\endcsname\selectfont\themycounter}.
\end{document}
顺便一提:
\specials
您可能会遇到将超链接和/或类似名称的目标放置到生成的输出文件中的问题。例如,当使用hyperref
-package,如果放置超链接的指令出现在 中,则超链接的目标将不会出现在 .pdf 文件中。\phantom
使用hyperref
,然后分段命令(如\caption
或)触发此类/目的地\section
的放置......\specials
我认为一个功能不是基于放置相等尺寸的空框,而是基于在生成的 .pdf 输出文件中完全无色且不可见的文本(可能具有不可复制粘贴的属性),这将是很好的:
如果有最新的软件可用,并且你的目标是生成 pdf 文件,那么你可以\phantom
通过 Heiko Oberdiek 的transparent
包。
在使用 transparent
包,相关文档至少需要编译两次。终端或 .log 文件中的警告消息将通知您有关此情况。
如果你还希望防止复制粘贴不可见的文本,你可以使用 Heiko Oberdiek 的accsupp
用于提供通过复制粘贴提供的替代文本的包。
\documentclass[12pt]{article}
\usepackage[unicode]{hyperref}
\usepackage{accsupp}[2007/11/14]
\usepackage{color}
\usepackage{transparent}
\usepackage{graphicx}
\parindent=0ex
\parskip=.66\baselineskip
\begin{document}
\textbf{Here inside the {\csname verbatim@font\endcsname\string\fbox} the
``non-phan\-to\-mi\-zed'' thing:}
Here the start:
\fbox{%
\parbox{4cm}{%
Some text. When you try to copy-paste, with the ``non-phan\-to\-mi\-zed'' thing the
pas\-ting-re\-sult may be nice and with the ``phantomized'' thing the pas\-ting-re\-sult
may be the advice not to do this.\\
\includegraphics[width=4cm]{example-image-a}%
}%
}
Here the end.
\textbf{Here inside the {\csname verbatim@font\endcsname\string\fbox} the
``phantomized'' thing:}
Here the start: %
\fbox{%
\begingroup
% Make the text inside the group transparent and thus invisible within the pdf-viewer:
\transparent{0.0}%
% Within AccSupp provide replacement-text when attempting to copy-paste the material:
\BeginAccSupp{method=pdfstringdef, space, unicode, ActualText={DO NOT COPY-PASTE THIS!}}%
%
\parbox{4cm}{%
Some text. When you try to copy-paste, with the ``non-phan\-to\-mi\-zed'' thing the
pas\-ting-re\-sult may be nice and with the ``phantomized'' thing the pas\-ting-re\-sult
may be the advice not to do this.\\
\includegraphics[width=4cm]{example-image-a}%
}%
%
\EndAccSupp{}%
\endgroup
}
Here the end.
\end{document}
\label
广告问题 2:在宏内收集调用时定义多个标签tabularx
为了调整单元格的宽度,tabularx
需要进行多次测试运行,在此期间,构成表格单元格内容的标记会被执行。
因此,tabularx
您的\g@addto@macro
指令也会被执行多次。
您需要确保您的\g@addto@macro
指令仅在最后一次运行中执行,而不是在测试运行期间执行。
怎么做? :
在测试运行中\@footnotetext
让其等于\TX@trial@ftn
(参见
tabularx 包,David Carlisle,2016/02/03,⟨http://mirrors.ctan.org/macros/latex/required/tools/tabularx.pdf⟩,第 5 节宏,代码第 119 行),因此您可以编写一个宏,通过检查定义在测试运行时进行测试\@footnotetext
:
\documentclass{article}
\usepackage{newenviron}
\usepackage{tabularx}
\makeatletter
\newcommand\DoIfNotTabularxTestRun{%
\ifx\@footnotetext\TX@trial@ftn\expandafter\@gobble\else\expandafter\@firstofone\fi
}%
\makeatother
\usepackage{subfig}
\makeatletter
\newenviron{hidecontent}{%
\gdef\envlabels{}%
\let\orgsubfloat=\subfloat
\renewcommand{\subfloat}[2][]{%
\begingroup %<-tabularx is a restricting scope on its own.
% but you may need this scope when using hidecontent's subfloat
% without additional environments. Otherise \subfloat's redefinition
% will remain effective even at the time of carrying out \envlabels
\renewcommand{\label}[1]{%
\DoIfNotTabularxTestRun{\myg@addto@macro\envlabels{\orgsubfloat{\protect\label{####1}}}}%
}%
##2%
\endgroup
}%
\begin{figure}%
\phantom{\envbody}%
\envlabels
\end{figure}%
}{}%
\makeatother
\begin{document}
Subfloat \subref{subfloat} should be (a). Is it?
\begin{hidecontent}
\begin{tabularx}{\linewidth}{l}
\subfloat{\label{subfloat}}
\end{tabularx}
\end{hidecontent}
\end{document}