I am totally new to LaTeX (use it for 2 days), so I am sorry if this has already been asked, but I spent the last 6 hours searching for a solution, but to no avail. (I stumbled upon a package xpeek which might be able to do what I want (or maybe not), but the documentation was way to complex for me to get anything out of it.)
I am using the ansmath package to write some formulas. I want to introduce a new command for formating my matrix variables. My first attempt was:
\newcommand{\mtrx}[1]{\boldsymbol{#1}}
which looks fine, except when I use subscripting. In this case, my lower indices are too far away to look nice. E.g. $\mtrx{P}_{\mu\nu}$
Because P is in italics, the space between the P and the subscript is disturbingly large. Using $\mtrx{P\!}_{\mu\nu}$
looks fine, but I get into trouble when using a superscript too: In $\mtrx{P\!}_{\mu\nu}^{*}$
, the * is way too close, and in $\mtrx{P}_{\mu\nu}^{*}$
the space between P and \mu
is too large.
So, my desired behaviour is to write my macro \mtrx
in a way, that it has a look at the tokens after the macro. If there is a subscript present, it inserts a \!
after the #1
. If there is a subscript and a superscript, it inserts a \;
in the superscript. If there is no subscript nothing is changed.
I tried a bit with
\makeatletter
\newcommand{\mtrx}[1]{%
\@ifnextchar_{\boldsymbol{#1}\!}{\boldsymbol{#1}}}
\makeatother
but was not able to detect if there is also a superscript present - or at all how to read past the first character after the macro. I guess, this should somehow be possible with \@car
and \@cdr
, but I have no real clue on how to use them.
Any help is appreciated. Thank you for your time.
[EDIT]
Ok, finally I found a solution. I stumbled upon a version of \@ifnextchar
which removes the character in case of a match here. I have no clue how it works, but it works.
By using it to remove the _
and ^
characters, I was able to call some other macros turning A_{B}
into something like \@mtrx@sub{A}{B}
.
Just in case, someone is searching for a similar problem, here is my solution.
\removeifnextchar
is taken from the link above and acts similar to\@ifnextchar
, except it removes the character on match.\mtrx
only formates its argument into bold face and calls\@mtrx@chk
to check for sub- and superscripts\@mtrx@chk
peeks the next character using\removeifnextchar
and calls\@mtrxsub
or\@mtrx@sup
, respectively, or returns its argument in case the next character is neither_
nor^
.\@mtrx@sub
and\@mtrx@sup
take 2 arguments each, attach them in subscript or superscript fashion and call\@mtrx@chk
again with this new argument in order to evaluate the next sub- or superscript.
Maybe this is not the best solution, but I am really glad that I finally found it. Anyway, in order to learn from this, please feel free to comment and/or improve.
\makeatletter
\newcommand{\removeifnextchar}[3]{%
\begingroup
\ltx@LocToksA{\endgroup#2}%
\ltx@LocToksB{\endgroup#3}%
\ltx@ifnextchar{#1}{%
\def\next{\the\ltx@LocToksA}%
\afterassignment\next
\let\scratch= %
}{%
\the\ltx@LocToksB
}%
}
\newcommand{\mtrx}[1]{
\ensuremath
\@mtrx@chk{\boldsymbol{#1}}
}
\def\@mtrx@chk#1{%
\removeifnextchar{_} %
{\@mtrx@sub{#1}}
{ \removeifnextchar{^} %
{\@mtrx@sup{#1}}
{#1}
}
}
\def\@mtrx@sub#1#2{%
\@mtrx@chk{#1_{\!#2}}
}
\def\@mtrx@sup#1#2{%
\@mtrx@chk{#1^{\:#2}}
}
\makeatother
A
instead ofP
. But if you really want to, you could use a macro with 2 arguments like so :\boldsymbol{#1}_{\!#2}
. I think it is a little bit awkward, but maybe it can help.