14

I'm trying to adapt the solution provided in Different command definitions with and without optional argument to change the behavior of my new command. I'd like to use basic command to avoid some non basic packages.

I'm defining a command \mysign to produce my signature at the end of the document. But sometimes I need the date above and sometimes not. So I'd like to have an optional argument to insert it (for example\mysign[date]).

Also, sometimes I need to insert some personal ID and I'd like to have a second optional argument, but independent with the first one.

So, the result would be something like this:

  • \mysign only the signature
  • \mysign[date] the signature with date
  • \mysign[id] the signature with ID
  • \mysign[date, id] full signature

The problem is that \@ifnextchar[ is working only for one option. I can not adjust to work only with second option.

Any idea?

Sigur
  • 37,330
  • Would a key=value approach be valid for you? – Gonzalo Medina Jul 08 '13 at 22:27
  • @GonzaloMedina, thanks, but I have no idea what you are asking. Probably yes since I simply would like to turn on/off the date and ID on my signature. – Sigur Jul 08 '13 at 22:28
  • 1
    I mean \mysign produces signature; \mysign[date=<value>] produces signature+date; \mysign[id=<value>] gives signature+id; \mysign[date=<value>,id=<value>] gives signature+date+id. – Gonzalo Medina Jul 08 '13 at 22:31
  • Great! It'll be very useful for me. – Sigur Jul 08 '13 at 22:32
  • Doing with only one optional argument requires knowing the format of the ID, so that it's distinguishable from the date. – egreg Jul 08 '13 at 22:59
  • @egreg, in fact, the ID is an image and I'd like to insert it with \includegraphics. – Sigur Jul 08 '13 at 23:06

5 Answers5

8

A key=value approach

\documentclass{article}
\usepackage{graphicx}
\usepackage{xkeyval}

\makeatletter
\def\SigurId{}
\define@key{sigur}{date}{\def\SigurDate{#1}}
\define@boolkey{sigur}{id}{
  \ifKV@sigur@id
    \def\SigurId{\includegraphics[height=1.2ex,width=2cm]{example-image-a}}%
  \else
  \fi%
}

\makeatother
\newcommand\mysig[1][]{%
  \begingroup
    \setkeys{sigur}{date={},id=false}
    \setkeys{sigur}{#1}
    Sigur~\SigurDate\unskip~\SigurId\unskip
  \endgroup
}

\begin{document}

\mysig 

\mysig[date={\today}]

\mysig[id=true]

\mysig[date=\today,id=true]

\end{document}

enter image description here

Gonzalo Medina
  • 505,128
6

From the comments to the answer of Gonzalo Medina I conclude that the optional argument ID is constant and rather a flag. Then LaTeX also knows an optional star as syntax element. The following example defines \mysign without the need of further packages the following way:

  • If a star follows, then the signature ID is set.
  • If an optional argument follows, then the date is set.
  • If the optional argument is empty, then \today is used as date.

The example file:

\documentclass{article}
\usepackage{graphicx}

\makeatletter
\newcommand*{\SetId}{%
  % tabular is only used for vertical centering
  % and ghostscript's example tiger.eps is the dummy
  % for the real scanned signature
  \begin{tabular}{@{}c@{}}%
    \includegraphics[height=2em,trim=0 50mm 0 0,clip]{tiger}%
  \end{tabular}%
}
\newcommand*{\mysign}{%
  \@ifstar{%
    \let\@DoId=\SetId
    \@mysign
  }{%
    \let\@DoId=\relax
    \@mysign
  }%
}
\newcommand*{\@mysign}[1][\relax]{%
  Signature%
  \def\@mysign@relax{\relax}%
  \def\@mysign@date{#1}%
  \ifx\@mysign@date\@mysign@relax
  \else
    , %
    \ifx\@mysign@date\@empty
      \today
    \else
      #1%
    \fi
  \fi
  \ifx\@DoId\relax
  \else
    , %   
    \@DoId
  \fi
}
\makeatother

\begin{document}
\renewcommand*{\arraystretch}{2}
\begin{tabular}{ll}
\verb|\mysign| & \mysign \\
\verb|\mysign*| & \mysign* \\
\verb|\mysign[]| & \mysign[] \\
\verb|\mysign[2001-02-03]| & \mysign[2001-02-03] \\
\verb|\mysign*[]| & \mysign*[] \\
\verb|\mysign*[2001-02-03]| & \mysign*[2001-02-03] \\
\end{tabular}
\end{document}

Result

Moriambar
  • 11,466
Heiko Oberdiek
  • 271,626
4

Another solution based again on a key-based interface: it exploits pgfkeys.

The code:

\documentclass[a4paper,11pt]{article}
\usepackage{tikz}
\usepackage{mwe}

% key definition
\newif\ifbaseline
\pgfkeys{/signature/.cd, baseline/.is if=baseline}
\pgfkeys{/signature/.cd,
  date/.initial={},
  date/.get=\signdate,
  date/.store in=\signdate,
  id/.initial={},
  id/.get=\id,
  id/.store in=\id,
}

% Basic command
\newcommand{\signature}[2][]{
\pgfkeys{signature/.cd,
  date={},
  id={},
  baseline=false,
  #1}
#2\space\signdate\space%
\ifbaseline
 \tikz[baseline=-0.5ex]\node[inner sep=0pt]{\id};
\else
 \id
\fi%
}

\begin{document}
\signature{Sigur}

\signature[date=\today]{Sigur}

\signature[id={\includegraphics[width=2em,height=2em]{example-image}}]{Sigur}

\signature[baseline,id={\includegraphics[width=2em,height=2em]{example-image}}]{Sigur}

\signature[baseline,
  id={\includegraphics[width=2em,height=2em]{example-image}},
  date={June 28, 2013}]{Sigur}

\signature[id={\includegraphics[width=2em,height=2em]{example-image}},
  date={June 28, 2013}]{Sigur}
\end{document}

TikZ is not really needed, actually it can be loaded pgfkeys in its place, but then I enjoyed the possibility to put the picture aligned on the baseline.

The result:

enter image description here

  • the twoopt package provides \newcommand, \renewcommand and \providecommand variants, that all accept two optional arguments. – wasteofspace Jul 09 '13 at 10:22
  • 1
    @wasteofspace: what if they are three or six? With key-based approaches it's just matter of defining new keys. Please, also consider that there's the xparse package able to define commands with more optional arguments, but I really believe that a key-based approach is the best. – Claudio Fiandrino Jul 09 '13 at 10:28
  • 1
    This is really the only right approach. – Ryan Reich Aug 20 '13 at 15:49
2

The poor man's solution:

\newcommand\mysig[3][Sigur]{#2 #1 #3}

Example:

\documentclass{article}

\newcommand\mysig[3][Sigur]{#2 #1 #3}

\begin{document}

\mysig{date}{id}

\mysig{date}

\mysig{}{id}

\mysig

\end{document}

MWE

Fran
  • 80,769
0

what about doing something like:

\usepackage{ifthen}
\newcommand{\mysign}[2]{%
    \ifthenelse{\equal{#1}{}}{}{#1\\}%
    SIGNATURE CODE%
    \ifthenelse{\equal{#2}{}}{}{\\#2}}

and then just invoke with the fields you don't want to use blank

i.e. \mysign{date}{} fot just date, etc...

John C
  • 173