下面是两个示例。第一个运行良好,没有错误也没有警告,但在尝试从后者构建文档时,我收到一堆错误。
在职的:
\documentclass[]{article}
\usepackage{environ}
\newsavebox{\DiscardedText}
\newcommand{\Slide}[1]{}
\newcommand{\SavedSlideText}{}
\newcommand\AddToSavedSlideText[1]{\xdef\SavedSlideText{\SavedSlideText#1\endgraf}}
\NewEnviron{GobbleExceptForSlide}{%
\renewcommand{\Slide}[1]{\AddToSavedSlideText{##1}}%
\savebox{\DiscardedText}{\BODY}%
\SavedSlideText%
}
\AtBeginDocument{\GobbleExceptForSlide}
\AtEndDocument{\endGobbleExceptForSlide}
\begin{document}
Should not show in output
\Slide{Should show in output}
\end{document}
但是,如果我将项目列放在 Slide 命令下方或其中,则它会在 \@savebox 完成 \end{document} 之前失败并结束段落:
\Slide{
Should show in output
\begin{itemize}
\item Item one
\item Iten two
\end{itemize}
}
我尝试用“newenvironment”替换“newcommand”,并做了相关更改,但还是无法让它工作。我有点生疏了……
更新
下面提供的答案确实解决了部分问题,但由于某种原因,在使用 Slide 之外的环境时它会中断。以下 tex 不会编译,因为 Slide 之外有一个 itemize 环境。
\documentclass{article}
\usepackage{environ}
\makeatletter
\newsavebox{\DiscardedText}
\newcommand{\Slide}[1]{}
\newcommand{\SavedSlideText}{}
\newcommand\AddToSavedSlideText[1]{\g@addto@macro\SavedSlideText{{#1}}}
\NewEnviron{GobbleExceptForSlide}{%
\renewcommand{\Slide}[1]{\AddToSavedSlideText{##1}}%
\savebox{\DiscardedText}{\BODY}%
\SavedSlideText%
}
\makeatother
\AtBeginDocument{\GobbleExceptForSlide}
\AtEndDocument{\endGobbleExceptForSlide}
\begin{document}
Should not show in output
\begin{itemize}
\item Item one
\item Iten two
\end{itemize}
\Slide{
Should show in output
\begin{itemize}
\item Item one
\item Iten two
\end{itemize}
}
\end{document}
答案1
根据修订后的 MWE 进行更新。
不幸的是,我不知道为什么会出现这个问题。但是,一种方法是按照以下方法消除缺少列表项的警告:如何使 itemize/enumerate/description 环境对缺失的 \item 元素具有鲁棒性?
代码:Suppress Missing Item Error
\documentclass{article}
\usepackage{environ}
%% Allow for lists to have no items.
%% https://tex.stackexchange.com/questions/86547/how-to-make-itemize-enumerate-description-environment-robust-to-missing-item-el
\makeatletter
\let\@oldnoitemerr\@noitemerr %Save the command definition
\newcommand\IgnoreMissingItemError{\let\@noitemerr\relax}
\newcommand\DontIgnoreMissingItemError{\let\@noitemerr\@oldnoitemerr}
\newsavebox{\DiscardedText}
\newcommand{\Slide}[1]{#1}
\newcommand{\SavedSlideText}{}
\newcommand\AddToSavedSlideText[1]{\g@addto@macro\SavedSlideText{{#1}}}
\NewEnviron{GobbleExceptForSlide}{%
\renewcommand{\Slide}[1]{\AddToSavedSlideText{##1}}%
\savebox{\DiscardedText}{\IgnoreMissingItemError\BODY}%
\SavedSlideText%
}
\makeatother
\AtBeginDocument{\GobbleExceptForSlide}
\AtEndDocument{\endGobbleExceptForSlide}
\begin{document}
Should not show in output
\begin{itemize}
\item Item one
\item Iten two
\end{itemize}
\Slide{
Should show in output
\begin{itemize}
\item Item one
\item Iten two
\end{itemize}
}
\end{document}
另一种方法是排版文档并保存\Slide
内容以便在文档末尾输出该内容。
代码:生成所有内容,以及Slide
最后的的内容
\documentclass{article}
\usepackage{environ}
\makeatletter
\newcommand{\Slide}[1]{#1}
\newcommand{\SavedSlideText}{}
\newcommand\AddToSavedSlideText[1]{\g@addto@macro\SavedSlideText{{#1}}}
\NewEnviron{GobbleExceptForSlide}{%
\renewcommand{\Slide}[1]{\AddToSavedSlideText{##1}##1}%
\BODY%
}
\makeatother
\AtBeginDocument{\GobbleExceptForSlide}
\AtEndDocument{\endGobbleExceptForSlide\clearpage\SavedSlideText}
\begin{document}
\section{foo}
Should not show in output
\begin{itemize}
\item Item one
\item Iten two
\end{itemize}
\Slide{
Should show in output
\begin{itemize}
\item Item one
\item Itenn two
\end{itemize}
}
\end{document}
在你之前的问题中有没有办法显示特定命令并隐藏其余命令,没有关于\Slide
宏将具有的内容类型的信息。因此,正如 David Carlisle 建议的那样,您需要使用来自如何保存字符串的运行列表,然后逐个处理它们保存内容:
代码:
\documentclass{article}
\usepackage{environ}
\makeatletter
\newsavebox{\DiscardedText}
\newcommand{\Slide}[1]{}
\newcommand{\SavedSlideText}{}
\newcommand\AddToSavedSlideText[1]{\g@addto@macro\SavedSlideText{{#1}}}
\NewEnviron{GobbleExceptForSlide}{%
\renewcommand{\Slide}[1]{\AddToSavedSlideText{##1}}%
\savebox{\DiscardedText}{\BODY}%
\SavedSlideText%
}
\makeatother
\AtBeginDocument{\GobbleExceptForSlide}
\AtEndDocument{\endGobbleExceptForSlide}
\begin{document}
Should not show in output
\Slide{
Should show in output
\begin{itemize}
\item Item one
\item Iten two
\end{itemize}
}
\end{document}