使用命令\AtBeginDocument
和\AtEndDocument
documentclassstandalone
会产生意想不到的效果。
我有以下三个文件。
% main.tex
\documentclass{scrartcl}
\usepackage[subpreambles]{standalone}
\AtBeginDocument{begin main \\}
\AtEndDocument{end main \\}
\begin{document}%
before
\input{sub1}
between
\input{sub2}
after
\end{document}
和
% sub1.tex
\documentclass{standalone}
\AtBeginDocument{begin sub1 \\}
\AtEndDocument{end sub1 \\}
\begin{document}%
\end{document}
sub2.tex
sub1.tex
除了数字之外,看起来都一样。编译main.tex
后会生成一个按如下顺序排列文本片段的文档。(我在这里插入了一些缩进,只是为了指出结构。)
begin sub1
begin sub2
begin main
before
between
after
end main
end sub1
end sub2
但我预料到这一点。
begin main
before
begin sub1
end sub1
between
end sub2
begin sub2
after
end main
我怎样才能获得第二个结果?
答案1
我相信有更好的方法可以做到这一点,但我的方法是在加载子前言期间修补\AtBeginDocument
和宏,以便它们将其参数附加到临时宏中。然后我修补(或更具体地说)宏以在文档主体中使用临时宏。我使用\AtEndDocument
input
\@iinput
etoolbox
包,但您可以按照自己的意愿进行操作。为了在加载子前言时完成修补,我直接写入文件\jobname.sta
。我的修补\@iinput
不是特别强大,需要您使用\input{sub1.tex}
而不是`\input{sub1}。
顺便说一下,如果您在子文件中加载任何依赖于并在应该扩展的位置扩展的包,则这种对\AtBeginDocument
和\AtEndDocument
宏的修补将造成严重破坏。\AtBeginDocument
\AtEndDocument
% main.tex
\documentclass{scrartcl}
\usepackage{etoolbox}
\usepackage[subpreambles]{standalone}
\AtBeginDocument{begin main \\}
\AtEndDocument{end main \\}
\makeatletter
\pretocmd{\@iinput}{\csuse{AtBeginDocument#1}}{}{}
\apptocmd{\@iinput}{\csuse{AtEndDocument#1}}{}{}
{\@makeother\#%
\AtBeginDocument{\immediate\write\sa@out{\unexpanded{%
\renewcommand{\subpreamble}[1]{%
\expandafter\def\csname AtBeginDocument#1\endcsname{}%
\expandafter\def\csname AtEndDocument#1\endcsname{}%
\renewcommand{\AtBeginDocument}[1]{\expandafter\apptocmd\expandafter{\csname AtBeginDocument#1\endcsname}{##1}{}{}}
\renewcommand{\AtEndDocument}[1]{\expandafter\apptocmd\expandafter{\csname AtEndDocument#1\endcsname}{##1}{}{}}
}
}}}
}
\makeatother
\setlength{\parindent}{0pt}
\begin{document}%
before
\input{sub1.tex}
between
\input{sub2.tex}
after
\end{document}
答案2
因为有人给出了一个棘手的答案(+1),所以我并不介意建议一个简单的答案,这可能有用,也可能没用,这取决于你真的希望发生在‘边缘’或子文件附近。
\documentclass{scrartcl}
\parindent 0pt
\usepackage[subpreambles]{standalone}
\AtBeginDocument{main.tex: begin main\par}
\AtEndDocument{main.tex: end main\par}
\usepackage{xparse}
\NewDocumentCommand{\myinput}{omo}
{\IfNoValueTF{#3}%
{\IfNoValueTF{#1}%
{\input{#2}}%
{#1\par\input{#2}}}%
{\IfNoValueTF{#1}%
{\input{#2}\par#3\par}%
{#1\par\input{#2}\par#3\par}}%
}
\begin{document}%
before
\myinput{sub1}
between
\myinput[sub1: before (no after)]{sub1}
between
\myinput{sub1}[sub1: after (no before) ]
between
\myinput[sub2: before]{sub2}[sub2: after]
\end{document}
\At<etc.>
然后从子文件中删除所有参数:
% sub1.tex
\documentclass{standalone}
% \AtBeginDocument{begin sub1 \\}
% \AtEndDocument{end sub1 \\}
\begin{document}%
sub1 -- main text
\end{document}
和
% sub1.tex
\documentclass{standalone}
% \AtBeginDocument{begin sub2 \\}
% \AtEndDocument{end sub2 \\}
\begin{document}%
sub2 -- main text
\end{document}