Neue Befehle
Ein neuer Befehl wird definiert über% \newcommand{cmd}[narg]{command definition} \newcommand{\figureref}[1]{(Abbildung \ref{#1})}% |
Dabei sind bis zu 9 Argumente (narg) möglich. Diese werden abgerufen über #1, …, #9.
Wie man mehr als 9 Argumente übegeben kann ist in der englischen FAQ erklärt:http://www.tex.ac.uk/cgi-bin/texfaq2html?label=moren9. Eine solche Anzahl von Argumenten ist jedoch nicht zu empfehlen. Besser ist es eine key=value Syntax zu verwenden.
Ist ein Befehl schon definiert löst ein \newcommand
einen Fehler aus.
zur Definition gibt es noch weitere Befehle, jeweils mit der gleichen Syntax:
\renewcommand
: definiert ein bestehenden Befehl um. Löst einen Fehler aus falls der Befehl noch nicht exisiter.\providecommand
: definiert einen Befehl unabhängig davon ob er schon existierte oder nicht.\DeclareRobustCommand
: wie\newcommand
, definiert allerdings einenrobusten Befehl.
Lange und kurze Befehle
Lange Befehle, dass sind alle die mit den vorgestellten Befehle \newcommand
, \renewcommand
, \providecommand
usw. erzeugt werden erlauben Paragraphenumbrüche in den Argumenten.
\newcommand* \renewcommand* \providecommand* ... |
die dann kurze Befehle erzeugen, die dann keine Paragraphenumbrüche in den Argumenten erlauben.
Intern sind die langen Befehl als \long\def
definiert und die kurzen nur als \def
Optionale Argumente
Die Syntax für einen Befehl mit optionalem Argument ist wie folgt\newcommand{cmd}[narg][default]{command definition} |
In diesem Fall hat das Optionale Argument die Nummer #1 und wird durch den default Wert ersetzt wenn der optionale Parameter nicht genutzt wird.
Im Falle von\newcommand{\foobar}[1][2]{#1} |
\foobar[3]
was dann “3” ausgibt.
Mehrfache optionale Argumente
Für die Lösung gibt es mehrere Pakete. Zum einen das optparams Paket welches die folgende Syntax bietet\long\def\test@[#1][#2][#3][#4]{% (#1) (#2) (#3) (#4) } \newcommand{\test}{% \optparams{\test@}{[one][two][three][four]}% } |
\test[this] % ergibt "(this) (two) (three) (four)" \test[this][is] % ergibt "(this) (is) (three) (four)" \test[this][is][a]% ergibt "(this) (is) (a) (four)" \test[this][is][a][test]% ergibt "(this) (is) (a) (test)" |
\long\def\test@[#1][#2][#3][#4]#5{% (#1) (#2) (#3) (#4) #5 } \newcommand{\test}{% \optparams{\test@}{[one][two][three][four]}% } |
Allerdings muss bei dieser Methode der erste Befehl über ein \def definiert werden da ein \newcommand diese Syntax nicht versteht.
Zum Anderen gibt es das wesentlich mächtigere Paket xargs welches eine sehr flexible Lösung bietet.
In diesem Paket werden die Befehle
\newcommandx \renewcommandx \providecommandx \DeclareRobustCommandx \CheckCommandx \newenvironmentx \renewenvironmentx |
definiert, welche sich durch die vordefiniertem jeweils durch das angehangene x unterscheiden und eine etwas andere Syntax bieten:
\newcommandx*{command}[number][list]{definition} % zum Vergleich \newcommand*{command}[number]{definition} |
Die Definition eines Befehls unterscheidet sich somit in der Definition von list. Das folgende Beispiel definiert zwei optionale Argumente
\newcommandx*\coord[3][1=1, 3=n]{(#2_{#1},\ldots,#2_{#3})} $\coord{x}$ % (x1, . . . , xn) $\coord[0]{y}$ % (y0, . . . , yn) $\coord{z}[m]$ % (z1, . . . , zm) $\coord[0]{t}[m]$ % (t0, . . . , tm) |
Der ‘value’ Wert bei der Liste gibt dabei den Standardwert an.
Um ein optionales Argument zu übergehen, also nicht anzugeben, aber das darauffolgende anzugeben muss man der Liste den Wert “usedefault” hinzufügen. Das Beispiel sieht dann wie folgt aus
\newcommandx*\coord[3][2=1,3=n,usedefault]{(#2_{#1},\ldots,#2_{#3})} $\coord{x}$ % (1x, . . . , 1n) $\coord{y}[0]$ % (0y, . . . , 0n) $\coord{z}[][m]$ % (1z, . . . , 1m) $\coord{t}[0][m]$ % (0t, . . . , 0m) |
Verschachtelte Befehle
Möchte man einen Befehl definieren, der einen weiteren Befehl umdefiniert benötigt man je nach Tiefer der Verschachtelung vorgestellte Raouten (#). Hier ein Beispiel:\newcommand\TextZwischenAnfangUndEnde[1]{Anfang \ldots #1 \ldots Ende} \newcommand\NeuerAnfangUndEnde[2]{% \renewcommand\TextZwischenAnfangUndEnde[1]{#1 \ldots ##1 \ldots #2}% } |
Mit der Voreingestellten Definition von \TextZwischenAnfangUndEnde
erhält man dann die Ausgabe
Benutzt man nun den Befehl zum Umdefinieren
\NeuerAnfangUndEnde{Es war einmal}{Sie lebten gluecklich bis an ihr Lebensende} \TextZwischenAnfangUndEnde{Das Maerchen} |
so erhält man
Befehle mit *
Vielleicht nicht die optimale, aber eine Möglichkeit diesen Unterschied abzufangen bietet der Befehl\@ifnextchar
mit der folgenden Notation
\newcommand{\fancy}{\@ifnextchar*{Befehl mit *}{Befehl ohne *} sonstiges} |
Umgebungen
Umgebungen werden definiert über\newenvironment{cmd}[narg]{begin definition}{end definition} \renewenvironment{cmd}[narg]{begin definition}{end definition} % Erste Argument optional \newenvironment{cmd}[narg][optional]{begin definition}{end definition} |
\begin{}
und \end{}
definieren. Stattdessen benötigt man die äquivalenten normalen Befehle. Hier ein Beispiel
% \newenvironment{myquote}[1]{\small\begin{quote}}{\end{quote}} % funktioniert nicht! \newenvironment{myquote}[1]{\small\quote}{\endquote} % funktioniert |
Protect, Fragile und Robust
Angeleht an einen Text aus der englische FAQ: LaTeX definiert Befehle deren Daten später nocheinmal eingelesen werden. Diese Daten können dann Argumetne von anderen Befehlen sein. Dies kann z.B. vorkommen bei Inhaltsverzeichnissen die aus aux Dateien wieder eingelesen werden und Daten die in den Kopf und Fusszeilen landen. Diese Befehle werden bei ihrer Ausführung und damit dem Speichern der Werte direkt expandiert. Manchmal erzeugt das einen Fehler wenn die Daten später nochmal eingelesen werden. Dies kann verhindert werden indem man ein\protect
vor einen Befehl stellt:
\protect\somecommand |
Fragile Befehle sind dann solche die in ungültigem TeX Code beim Speichern resultieren, wohingegen Robuste Befehle in gültigen Code beim Speichern expandieren.
Also
funktioniert bei mir ohne Probleme. Zwar macht die Angabe eines Parameters keinen Sinn, wenn es sich nur um eine einfach, kleine quote-Umgebungserweiterung handeln soll. Davon abgesehen kann ich ohne Fehler beim Kompilieren
\begin{myquote}
ein kleines Zitat
\end{myquote}
in mein Dokument einbauen…
Davon abgesehen möchte ich dir auch mal kurz für deine LaTeX-Tipps im Allgemeinen danken. Die haben mir schon oft geholfen 🙂
LG,
Dominik