为什么在 lettrine 中采用这种数学模式

为什么在 lettrine 中采用这种数学模式

尝试使用莱特林使用 Georg Duffner 的 EB Garamond 字体在 XeLaTeX 中进行打包,结果如下:

! Bad USV code (-2411)

反复试验表明,问题出在 lettrine.sty 中的这两行:

\smash{\llap{\mbox{\L@ante}\raisebox{\L@lraise}{\usebox{\L@lbox}}%
       \hskip \the\L@Findent}}

在原始 lettrine.sty 文件中,这些行包含在内$ $,因此在数学模式下排版。我删除了$ $,问题就消失了。

问:鉴于这两行代码与数学无关,为什么它们应该处于数学模式?

答案1

显然,作者lettrine认为这只\smash在数学模式下有效。在数学模式之外使用它时会出现问题,因为它不会像预期的那样开始一个段落。然而,定义中的代码\@lettrine

\def\@lettrine[#1]#2#3{%
  \setcounter{L@lines}{\theDefaultLines}%
  <...omitted code...>
  \noindent\leavevmode
  \parshape=\L@parshape
  $\smash{\llap{\mbox{\L@ante}\raisebox{\L@lraise}{\usebox{\L@lbox}}%
          \hskip \the\L@Findent}}$%
  \usebox{\L@tbox}}

并且\noindent已经使 TeX 切换到水平模式(并且 是\leavevmode多余的)。我们可以看到 的参数中没有使用数学模式材料\smash

因此,删除 ; 没有任何风险$,但最好停止寻找\parshape可能导致\smash过早扩展的其他规范。因此,我建议使用以下补丁:

\usepackage{lettrine}
\usepackage{etoolbox}
\makeatletter
\patchcmd{\@lettrine}{$}{\relax}{}{}
\patchcmd{\@lettrine}{$}{}{}{}
\makeatother

也就是说,将第一个更改$\relax并删除第二个$

如果宏在软件包修订版中发生更改,则补丁不应执行任何操作\@lettrine(前提是它不会注入$同一宏的其他地方)。

相关内容