
Es scheint unmöglich zu sein, \rowcolor
ein mit definiertes Makro einzuschließen \NewDocumentCommand
, während mit alles in Ordnung ist \newcommand
. Kann man das beheben?
\documentclass{article}
\usepackage[table]{xcolor}
\usepackage{xparse}
\NewDocumentCommand{\rowI}{}{
\rowcolor{blue}
}
%\newcommand{\rowI}{
% \rowcolor{green}
%}
\begin{document}
\begin{tabular}{lll}
\rowI 1 & 2 & 3 \\
1 & 2 & 3 \\
\end{tabular}
\end{document}
Da der Fehler nur bei den Ursachen auftritt, \NewDocumentCommand
gehe ich davon aus, xparse
dass er das Problem verursacht und nicht \rowcolor
sich selbst …
Antwort1
Die Definition von \rowcolor
in colortbl.sty
ist
\def\rowcolor{%
\noalign{\ifnum0=`}\fi
\global\let\CT@do@color\CT@@do@color
\@ifnextchar[\CT@rowa\CT@rowb}
Wir sehen also, dass es mit beginnt \noalign
. Wenn TeX eine Ausrichtung vornimmt (mit dem primitiven \halign
, wie es bei der Fall ist tabular
) und ein gescannt hat, \cr
das eine Zeile beendet (einschließlich des durch die Tabellenpräambel generierten), erweitert es das nächste Token, um zu sehen, ob \omit
oder \noalign
kommt. So funktioniert \hline
das optionale Argument für \\
oder . TeX erweitert weiterhin Token, bis es entweder / oder ein anderes nicht erweiterbares Token \multicolumn
findet .\noalign
\omit
Sie müssen wissen, dass \NewDocumentCommand
die e-TeX-Funktion namens verwendet wird \protected
. Ein mit dem Präfix definiertes Makro \protected
verhält sich hinsichtlich des obigen Scan-Mechanismus so, als wäre es ein nicht erweiterbares Token: Es wird \relax
vorerst als gleichwertig zu betrachtet, aber nach Abschluss dieser vorläufigen Suche normal erweitert.
(Dasselbe Verhalten tritt bei \protected
Makros in einem auf \edef
.)
Also,niemalsdefinieren mit \NewDocumentCommand
Makros, die (am Anfang ihres Ersetzungstextes) Dinge enthalten, diemussan erster Stelle in einer Ausrichtungszelle stehen, wie beispielsweise \multicolumn
, \hline
, \cline
(dasselbe gilt für die Regelerstellungsbefehle von booktabs
) oder \rowcolor
von colortbl
.
Dieselbe Einschränkung wie oben gilt für Befehle, die mit \newcommand
einem optionalen Argument definiert sind, da sie verzögert erweitert werden, was die Suche nach \omit
/ unterbrechen würde \noalign
.
Verwenden Sie \newcommand
(ohne optionale Argumente) oder, wenn Sie wirklich ein optionales Argument benötigen, \DeclareExpandableDocumentCommand
von xparse
(lesen Sie in diesem Fall jedoch die Dokumentation zu den Einschränkungen, z. B. wenn Sie nach einem optionalen Argument ein obligatorisches Argument benötigen).