我正在尝试创建一个名为“my-environ”的逐字环境
\documentclass{article}
\usepackage{fancyvrb}
\DefineVerbatimEnvironment{myenviron}{Verbatim}{numbers=left,frame=lines,label=My Environ,labelposition=topline}
%\DefineVerbatimEnvironment{my-environ}{Verbatim}{numbers=left,frame=lines,label=My-Environ,labelposition=topline}
\begin{document}
\begin{myenviron}
Hello
\end{myenviron}
%\begin{my-environ}
%Hello
%\end{my-environ}
\end{document}
如果取消注释代码,您会发现它无法编译。我不必使用fancyvrb
,但我想要类似的功能。
答案1
在他的回答egreg 已经解释过,连字符-
在 verbatim 环境中有不同的 catcode。包从中fancyvrb
保存环境名称。有 catcode\begin{my-environ}
\FV@EnvironName
-
前逐字环境的 catcode 发生变化,通常为 12(其他)。然后在环境内部fancyvrb
查找\end{...}
并检查是否...
匹配\FV@EnvironName
。但-
现在 catcode 为 13(活动),并且由于 catcode 不同,字符串my-environ
不匹配-
,并且fancyvrb
无法看到环境的结尾。
该示例破解了 的宏,fancyvrb
以定义\FV@EnvironCheckName
存储my-environ
verbatim 环境的 catcode。由于\scantokens
、\everyeof
和 ,该破解需要 e-TeX\unexpanded
来获取未扩展的环境名称和 catcode,这些 catcode 在 verbatim 环境的 catcode 设置后处于活动状态。
\documentclass{article}
\usepackage{fancyvrb}
\DefineVerbatimEnvironment{my-environ}{Verbatim}{
numbers=left,
frame=lines,
label=My-Environ,
labelposition=topline,
}
\makeatletter
\renewcommand*{\VerbatimEnvironment}{%
\ifx\FV@EnvironName\relax
\xdef\FV@EnvironName{\@currenvir}%
\begingroup
\endlinechar=-1 %
\everyeof{\@nil\noexpand}%
\xdef\FV@EnvironCheckName{%
\expandafter
\FV@CatchUnexpanded\scantokens\expandafter{\@currenvir}%
}%
\endgroup
\fi
}
\def\FV@CatchUnexpanded#1\@nil{\unexpanded{#1}}
\begingroup
\catcode`\^^M=\active
\gdef\FancyVerbGetLine#1^^M{%
\@nil%
\FV@CheckEnd{#1}%
\ifx\@tempa\FV@EnvironCheckName% % True if end is found
\ifx\@tempb\FV@@@CheckEnd\else\FV@BadEndError\fi%
\let\next\FV@EndScanning%
\else%
\def\FV@Line{#1}%
\def\next{\FV@PreProcessLine\FV@GetLine}%
\fi%
\next%
}%
\endgroup
\makeatother
\begin{document}
\begin{my-environ}
Hello
\end{my-environ}
\end{document}
答案2
问题很微妙。一般来说,连字符可以出现在环境名称中,就像任何其他非特殊字符一样(实际上也包括一些特殊字符)。但是,在逐字环境中无法使用其中一些字符,因为逐字模式使它们积极的;latex.ltx
你会发现
\def\verbatim@nolig@list{\do\`\do\<\do\>\do\,\do\'\do\-}
并且列表中的字符`<,'-
被激活,以便 (La)TeX 不会产生通常的连字
?` !` << >> ,, `` '' -- ---
但是,您的环境的结尾verbatim
由细绳
\end{my-verbatim}
在设置上述活动字符之前构建fancyvrb
。字符串的含义是所有字符都具有类别代码 12;fancyvrb
一次加载一行并将其与结束字符串进行比较。但是,如果环境名称包含上述字符之一,则无法找到结束字符串。
也许可以破解宏以便允许使用这些字符,但最好只使用字母。