是否可以使用独立包嵌套文件?我有类似以下内容:
在 A.tex 中:
\documentclass{article}
\usepackage{standalone}
\begin{document}
\input{B}
\end{document}
B. 特克斯:
\documentclass{standalone}
\begin{document}
\begin{table}
\input{C}
\end{table}
\end{document}
C.tex
\documentclass{standalone}
\begin{document}
\begin{tabular}{ l l r r }
A & B & C & D
\end{tabular}
\end{document}
A 和 C 编译正常,但在编译 B.tex 时出现以下错误:
! LaTeX Error: Not in outer par mode.
并从那里抱怨。
我尝试做的事情(A.tex 包含 B.tex 包含 C.tex)可行吗?使用浮点数可行吗?
答案1
是的,你可以嵌套standalone
文件,但是,与任何其他\input
包含standalone
文件的文档一样,你需要加载standalone
包裹在这种情况下也是如此。
另一个问题是,由于使用了 used 模式,您无法在普通文件中使用浮点数table
和环境。您需要使用 class 选项将其关闭,或者重新定义环境使其不再是浮点数。figure
standalone
preview
preview=false
table
% B.tex
\documentclass{standalone}
\usepackage{standalone}
\renewenvironment{table}{}{}% Ignore `table` environment in standalone mode.
\begin{document}
\begin{table}
\input{C}
\end{table}
\end{document}
如果你有\caption
你应该使用:
\makeatletter
\renewenvironment{table}{\def\@captype{table}}{}
\makeatother
否则你会得到一个错误。
更新 2011/12/21
我现在发布了standalone
v1.0,它默认重新定义浮点数以在standalone
文件内部工作。float
有关更多详细信息,请参阅手册中的选项。另请参阅是否可以将图形环境与独立包一起使用?
答案2
虽然这不使用standalone
包,我希望它会令您感兴趣。
我经常使用自己的技巧来制作可以单独编译的独立文档。我在知道之前就想出了这个技巧standalone
,我还没有解决的唯一缺点是它在存在子文件夹的情况下表现不佳。
文件a.tex
\input{include.sty}
在文档的最顶部使用(定义如下),并直接使用\begin{xdocument}
(注意x
),而\end{xdocument}
无需任何前言。
\input{include.sty}
\masterdocumenttrue
\begin{xdocument}
\input{b}
\end{xdocument}
\masterdocumenttrue
让您知道在命令行上传递给 LaTeX 的文件是否是“主”文档,而不是子文档,因此您可以通过将目录和参考书目等内容括在内来有条件地包含它们\ifmasterdocument …\fi
。
文件b.tex
同样的事情,但是\masterdocumenttrue
这里没有。
\input{include.sty}
\begin{xdocument}
\begin{table}
\input{c}
\end{table}
\end{xdocument}
文件c.tex
\input{include.sty}
\begin{xdocument}
\begin{tabular}{ l l r r }
A & B & C & D
\end{tabular}
\end{xdocument}
文件preamble.sty
此文件包含所有文件使用的 pramble。
\documentclass{article}
%\usepackage{foo}
%\def\mycommand{bar}
一步步include.sty
此文件仅包含“主”文档(通过命令行传递给 LaTeX 的文档)的序言,在运行\begin{document}
第一个文档时插入,并且如果您的 s 正确嵌套,则在第一个文档关闭时插入(因此是最后一个),并且它们应该是。\begin{xdocument}
\end{document}
xdocument
\end{xdocument}
xdocument
由于我们没有使用 LaTeX 的\usepackage
,所以我们需要@
自己更改 的 catcode:
\makeatletter
如果宏\nesteddocumentlevel
未定义,那么它是第一次include.sty
被包含,所以它会完成它的工作,但其余时间不会执行:
\ifx\nesteddocumentlevel\undefined
\def\nesteddocumentlevel{0}
我们避免使用额外的计数器(只有 255 个),通过提供增加任何宏的命令,将其放在临时计数器中只是为了增加它,然后返回到宏中:
\def\addtomacrocounter#1#2{%
\bgroup%
\@tempcnta=#1%
\advance\@tempcnta #2%
\expandafter\xdef\noexpand#1{\the\@tempcnta}%
\egroup%
}
构建一个易于使用的宏\ifdocumentlevel{level}{if-equal}{if-different}
来检查当前包含的深度:
\def\ifdocumentlevel#1#2#3{
\edef\testnesteddocumentlevel{#1}
\ifx\nesteddocumentlevel\testnesteddocumentlevel#2\else#3\fi%
}
搭建xdocument
环境:
\newenvironment{xdocument}{
它增加了包含深度伪计数器:
\addtomacrocounter{\nesteddocumentlevel}{1}
如果我们在顶层文档中,插入一个\begin{document}
\ifdocumentlevel{1}{
\document% = \begin{document}
如果我们有一个名为的文件main-header.tex
,它将被包含在通过命令行传递给 LaTeX 的文档的开头,也就是b.tex
在你编译时在 的内容之前b.tex
:
\IfFileExists{main-header.tex}{\input{main-header.tex}}{}
}{}
如果我们有一个名为的文件every-header.tex
,它将被包含在每个(子)文档的开头,也就是在编译时在b.tex
和的内容之前:c.tex
b.tex
\IfFileExists{every-header.tex}{\input{every-header.tex}}{}
}{
当运行 时\end{xdocument}
,我们定义一个\maybeenddocument
宏,它将被\expandafter
编辑,并且可能输出\end{document}
,并包含各种页脚。
如果我们有一个名为的文件every-footer.tex
,它将被包含在每个(子)文档的末尾,也就是在编译时在b.tex
和的内容之后:c.tex
b.tex
\IfFileExists{every-footer.tex}{\input{every-footer.tex}}{}
\ifdocumentlevel{1}{
If we have a file named `main-footer.tex`, it will be included at the end of the document passed on the command-line to LaTeX, that is after `b.tex`'s content when you compile `b.tex`
\IfFileExists{main-footer.tex}{\input{main-footer.tex}}{}
当我们处于顶层文档时,我们将输出\end{document}
:
\def\maybeenddocument{\enddocument}
}{
但其余时间则不然:
\def\maybeenddocument{}
}
弹出一层包含:
\addtomacrocounter{\nesteddocumentlevel}{-1}
并将可能的放在 的\end{document}
最后一段代码之后\end{xdocument}
。如果我们将它放得更早,它会抱怨不匹配的{
,因为它们的匹配}
将在 之后\end{document}
,即处于不确定状态。
\expandafter\maybeenddocument%
}
include.sty
首次包含时,我们会包含序言。preamble.sty
应包含 \documentclass{…} 和 \begin{document} 之间的所有内容,但不包含 \begin{document} 本身。
\input{preamble.sty}
并创建masterdocument
条件。我们需要用 和 来转义它的名称\csname
,\endcsname
否则 TeX 会认为它是一个真正的\if…
,将它与 匹配\fi
,后者属于\ifx\nesteddocumentlevel\undefined
此文件顶部的 ,而 反过来将没有匹配项\fi
\expandafter\newif\csname ifmasterdocument\endcsname\masterdocumentfalse
include.sty
首次包含时代码运行结束:
\fi
并恢复的行为@
:
\makeatother
完整代码include.sty
\makeatletter
\ifx\nesteddocumentlevel\undefined
\def\nesteddocumentlevel{0}
\def\addtomacrocounter#1#2{%
\bgroup\@tempcnta=#1%
\advance\@tempcnta #2%
\expandafter\xdef\noexpand#1{\the\@tempcnta}%
\egroup}
\def\ifdocumentlevel#1#2#3{
\edef\testnesteddocumentlevel{#1}
\ifx\nesteddocumentlevel\testnesteddocumentlevel#2\else#3\fi%
}
\newenvironment{xdocument}{
\addtomacrocounter{\nesteddocumentlevel}{1}
\ifdocumentlevel{1}{
\document% = \begin{document}
\IfFileExists{main-header.tex}{\input{main-header.tex}}{}
}{}
\IfFileExists{every-header.tex}{\input{every-header.tex}}{}
}{
\IfFileExists{every-footer.tex}{\input{every-footer.tex}}{}
\ifdocumentlevel{1}{
\IfFileExists{main-footer.tex}{\input{main-footer.tex}}{}
\def\maybeenddocument{\enddocument}
}{
\def\maybeenddocument{}
}
\addtomacrocounter{\nesteddocumentlevel}{-1}
\expandafter\maybeenddocument%
}
\input{preamble.sty}
\expandafter\newif\csname ifmasterdocument\endcsname\masterdocumentfalse
\fi
\makeatother