XeTeX 的注释

XeTeX 的注释

red考虑以下 MWE。我想为带框的物体 ( )赋予颜色 ( ) Hello。不幸的是,它不能按预期工作,就好像带框的物体被屏蔽了一样。如何去除这样的屏蔽?

\documentclass{article}
\usepackage{xcolor}

\newsavebox\MyBox
\savebox\MyBox{Hello}

\begin{document}
\textcolor{red}{\usebox\MyBox}
\end{document}

答案1

\savebox使用来定义\sbox,后者在 LaTeX 中定义为:

\long\def\sbox#1#2{\setbox#1\hbox{%
  \color@setgroup#2\color@endgroup}}

当包加载时,的文本参数\sbox被包装在一个组\color@setgroup和中:\color@endgroupcolor

\def\color@setgroup{\begingroup\set@color}
\let\color@begingroup\begingroup
\def\color@endgroup{\endgraf\endgroup}

另外,在构建框时设置当前处于活动状态的颜色。这是故意的,因为其他属性(如字体)也是固定的。框内容在或\color@setgroup中不会改变,字体系列或大小也无法更改。\textit\textbf

颜色通常通过特殊来实现,那么以下定义会有所帮助:

\makeatletter
\newcommand{\sboxcolorless}[2]{%
  \setbox#1\hbox{\color@begingroup#2\color@endgroup}%
}
\makeatother

将参数放入一个组中非常重要,这里\color@begingroup\color@endgroup,因为#2可以包含\color命令,这些命令会自动重置颜色组。如果缺少明确的组里面 \hbox,重置颜色特殊会泄漏外部\hbox声明\setbox

\documentclass{article}
\usepackage{xcolor}

\newsavebox\MyBoxA
\savebox\MyBoxA{Hello}

\makeatletter
\newcommand{\sboxcolorless}[2]{%
  \setbox#1\hbox{\color@begingroup#2\color@endgroup}%
}
\makeatother

\newsavebox\MyBoxB
\sboxcolorless\MyBoxB{Hello}

\begin{document}
  \textcolor{red}{Red \usebox\MyBoxA\ red \usebox\MyBoxB\ red.}
\end{document}

结果

但是,这个技巧取决于颜色的实现。LuaTeX 有一个属性的概念,其中颜色可以更接近字体属性的实现。包luacolor实现了这一点。然后,元素、字符在创建时会归因于当前颜色。在框中重复使用不会改变这一点。因此,使用包的luacolor示例看起来会有所不同,两个“Hello”都是黑色的:

使用 luacolor 的结果

如果您想要更多的可移植性和灵活性,可以使用宏,其中对固定属性的控制更大:

\documentclass{article}
\usepackage{xcolor}

\newcommand*{\Hello}{%
  \begingroup
    \fontfamily\rmdefault % roman font, no non-serif or typewriter
    \upshape % no italics, small caps
    % but series (bold) or font size are flexible
    Hello% 
  \endgroup
}

\begin{document}
  \textcolor{red}{Red \Hello\ \textbf{bold \Hello} \textit{italics \Hello}}
\end{document}

结果宏

这也适用于所有颜色实现。

XeTeX 的注释

XeTeX 的颜色驱动程序xetex.def通过 很晚才定义颜色命令\AtBeginDocument。这意味着颜色命令是不是在前导码中完全可操作。例如,\textcolor{blue}{...}如果在前导码中设置了框,框内也将不起作用。如果在 `\begin{document} 之后保存框,则框将像其他驱动程序的情况一样工作。

\documentclass{article}
\usepackage{xcolor}

\newsavebox\MyBox
\savebox\MyBox{Hello \textcolor{blue}{World}!}

\begin{document}
  \textcolor{red}{Red \usebox\MyBox\ Red}

  \savebox\MyBox{Hello \textcolor{blue}{World}!}

  \textcolor{red}{Red \usebox\MyBox\ Red}
\end{document}

结果 XeTeX

这种“奇怪”行为背后的原因是xetex.def想要允许用户通过禁用堆栈颜色实现(在某些极少数情况下可能需要)\noXeTeXcolorstack

在序言中启用颜色的解决方法:

\makeatletter
\check@for@XeTeX@colorstack
\let\check@for@XeTeX@colorstack\relax
\makeatother

答案2

据我了解,当 LaTeX 使用 创建一个框时\savebox,该框是在那一刻创建的,并且任何颜色都已被分配;所以当你 时\usebox,当前颜色不会产生任何效果。

一个选项是最初用颜色定义框:

\savebox\MyBox{\textcolor{red}{Hello}}

另一个更灵活的解决方案是定义一个命令,在发出命令时动态构建框:

\documentclass{article}
\usepackage{xcolor}
\def\makecolbox#1#2{%
    \hbox{\textcolor{#1}{#2}}%
}
\begin{document}
\makecolbox{red}{Hello}
\makecolbox{green}{Goodbye}
\makecolbox{black}{Whatever}
\end{document}

如果框的内容相同,则可以消除#2,然后以这种方式对文本进行硬编码。

答案3

这里有一个蒂克兹解决方案。我定义了两个宏:

  • \savecolorablebox{boxname}{content}定义并保存一个可着色的框。

  • \usecoloredbox[color]{boxname}使用并给盒子上色。

在此处输入图片描述

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{fadings}
\newcommand\savecolorablebox[2]{
  \expandafter\newsavebox\csname#1\endcsname
  \expandafter\savebox\csname#1\endcsname{\textcolor{white}{#2}}
  \begin{tikzfadingfrompicture}[name=#1]
    \node[text=transparent!0,fill=transparent!100]{\expandafter\usebox\csname#1\endcsname};
  \end{tikzfadingfrompicture}
}
\newcommand\usecoloredbox[2][black]{%
  \bgroup%
  \pgfmathsetmacro\myw{width("\expandafter\usebox\csname#2\endcsname")}%
  \pgfmathsetmacro\myh{height("\expandafter\usebox\csname#2\endcsname")}%
  \pgfmathsetmacro\myd{depth("\expandafter\usebox\csname#2\endcsname")}%
  \begin{tikzpicture}[baseline=-1 * \myh pt / 2 + \myd pt / 2]
    \fill[path fading=#2,fit fading=false,fill=#1]
    (-1 * \myw pt / 2, -1 * \myh pt / 2 - 1 * \myd pt / 2)
    rectangle (\myw pt / 2,\myh pt /2 + \myd pt / 2);
  \end{tikzpicture}%
  \egroup%
}
\begin{document}
\savecolorablebox{MyBox}{Hello}
test \usecoloredbox[orange]{MyBox} test \usecoloredbox[blue]{MyBox}
\savecolorablebox{MyBox2}{Hello gg}
test \usecoloredbox[cyan]{MyBox2} test \usecoloredbox[green]{MyBox2}
\savecolorablebox{MyBox3}{$x=\frac{a}{b}$}
test \usecoloredbox[cyan]{MyBox3} test \usecoloredbox[red]{MyBox3}
\end{document}

相关内容