我现有如下代码,自定义了weizil,weizic,weizir三个环境,如何把这个三个环境合成一个新定义环境,然后给出选项l,c,r,根据l,c,r的不同选择对应的环境?
\documentclass{ctexart}
\newenvironment{weizil}[1][]
{\begin{flushleft}
\begin{minipage}{#1\textwidth}
}{\end{minipage}\end{flushleft}}
\newenvironment{weizic}[1][]
{\begin{center}
\begin{minipage}{#1\textwidth}
}{\end{minipage}\end{center}}
\newenvironment{weizir}[1][]
{\begin{flushright}
\begin{minipage}{#1\textwidth}
}{\end{minipage}\end{flushright}}
\begin{document}
\begin{weizil}[0.5]
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizil}
\begin{weizic}[0.6]
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizic}
\begin{weizir}[0.55]
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizir}
\end{document}
第一个参数是 []
,第二个是 {}
。
\documentclass{ctexart}
\usepackage{xparse}
\newenvironment{weizil}[1][]
{\begin{flushleft}
\begin{minipage}{#1\textwidth}
}{\end{minipage}\end{flushleft}}
\newenvironment{weizic}[1][]
{\begin{center}
\begin{minipage}{#1\textwidth}
}{\end{minipage}\end{center}}
\newenvironment{weizir}[1][]
{\begin{flushright}
\begin{minipage}{#1\textwidth}
}{\end{minipage}\end{flushright}}
\ExplSyntaxOn
\NewDocumentEnvironment { test } { O{c} m }
{
\tl_if_eq:NNTF { #1 } { l }
{
\begin{weizil}[#2]
}
{
\tl_if_eq:NNTF { #1 } { c }
{
\begin{weizic}[#2]
}
{
\begin{weizir}[#2]
}
}
}
{
\tl_if_eq:NNTF { #1 } { l }
{
\end{weizil}
}
{
\tl_if_eq:NNTF { #1 } { c }
{
\end{weizic}
}
{
\end{weizir}
}
}
}
\ExplSyntaxOff
\begin{document}
\begin{test}[c]{0.5}
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{test}
\end{document}
这里再给出几种方法。
由于使用 \begin{<env>}
时,LaTeX 将会(在该命令执行的最末尾)展开 \csname <env>\endcsname
;
使用 \end{<env>}
,将会展开 \csname end<env>\endcsname
,我们可以在 \<env>
中定义 \end<env>
。
\newcommand\weizi[2][c]{%
\strcase{#1}
{{c}{\def\endweizi{\end{minipage}\end{center}}%
\begin{center}}
{l}{\def\endweizi{\end{minipage}\end{flushleft}}%
\begin{flushleft}}
{r}{\def\endweizi{\end{minipage}\end{flushright}}%
\begin{flushright}}}
{}
{\def\endweizi{\end{minipage}\end{center}}%
\begin{center}}%
\begin{minipage}{#2\textwidth}}
也就是根据相应的可选参数,定义对应的 \end<env>
。这里的 \strcase
对应于 LaTeX3 的 \str_case_e:nnTF
。
% \strcase := LaTeX3 \str_case_e:nnTF
\expandafter\let\expandafter\strcase\csname str_case_e:nnTF\endcsname
使用方式为:
\begin{weizi}[c]{0.5}
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
这样的定义是可以嵌套使用的,因为每一对 \begin ... \end
都放在一个组中。
另一种方式涉及到 center
、flushleft
、flushright
环境的实现。这三个环境都是使用 trivlist
环境实现的,它们的 \end<...>
都是 \endtrivlist
。(具体细节可以在 source2e.pdf 中找到。)
因此实际上可以写得更加简单,不论 c
、l
、r
,\endweizi
都可以定义为 \def\endweizi{\endminipage\endtrivlist}
。
包装成一个环境就是:
\newenvironment{weizi}[2][c]
{\strcase{#1}
{{c}{\center}
{l}{\flushleft}
{r}{\flushright}}
{}
{\center}
\minipage{#2\textwidth}}
{\endminipage\endtrivlist}
使用方式是完全相同的。
另一个就是使用 cmd
(xparse
),我们可以方便的使用可选参数:
\DeclareDocumentEnvironment {weizi} { !D(){} !O{c} !D(){#1} }
{\strcase{#2}
{{c}{\center}
{l}{\flushleft}
{r}{\flushright}}
{}
{\center}
\minipage{#3\textwidth}}
{\endminipage\endtrivlist}
这样,
\begin{weizi}
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}(0.5)
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}[c]
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}[c](0.5)
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}(0.5)[c]
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
都是可以的。
汇总:
\documentclass{ctexart}
% \strcase := LaTeX3 \str_case_e:nnTF
\expandafter\let\expandafter\strcase\csname str_case_e:nnTF\endcsname
\begin{document}
\newenvironment{weizi}[2][c]
{\strcase{#1}
{{c}{\center}
{l}{\flushleft}
{r}{\flushright}}
{}
{\center}
\minipage{#2\textwidth}}
{\endminipage\endtrivlist}
\begin{weizi}[c]{0.5}
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\renewcommand\weizi[2][c]{%
\strcase{#1}
{{c}{\def\endweizi{\end{minipage}\end{center}}%
\begin{center}}
{l}{\def\endweizi{\end{minipage}\end{flushleft}}%
\begin{flushleft}}
{r}{\def\endweizi{\end{minipage}\end{flushright}}%
\begin{flushright}}}
{}
{\def\endweizi{\end{minipage}\end{center}}%
\begin{center}}%
\begin{minipage}{#2\textwidth}}
\begin{weizi}[c]{0.5}
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\DeclareDocumentEnvironment {weizi} { !D(){} !O{c} !D(){#1} }
{\strcase{#2}
{{c}{\center}
{l}{\flushleft}
{r}{\flushright}}
{}
{\center}
\minipage{#3\textwidth}}
{\endminipage\endtrivlist}
\begin{weizi}
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}(0.5)
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}[c]
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}[c](0.5)
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\begin{weizi}(0.5)[c]
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
文字文字文字文字文字文字文字文字文字文字文字文字文字文字文字
\end{weizi}
\end{document}
感谢大佬指点,我去试试