4

I have created a new command whose argument can be a new call to the same command. How can I then reset the values of the pgfkeys in the nested call to their default values, so that they don't have the values that were set in the first call of the command? Specifically, the width of the overlaid image becomes 2cm instead of 6cm, which is the default, because the width was set to 2cm in the parent command call. I know I could use \pgfkeys{/icon/.cd,overlay,width,#1) to reset \width, but then it becomes empty, and not the default value.

\documentclass{article}
\usepackage{tikz}
\usepackage{etoolbox}
\usepackage{overpic}

\pgfkeys{
    /icon/.cd,
    width/.store in = \width,
    width/.default = ,
    overlay/.store in = \overlay,
    overlay/.default = ,
    width,overlay,
}

\newcommand\icondefaults[1]{%
    \pgfkeys{/icon/.cd,#1}%
    \pgfkeys{
        width/.default = \width,
    }%
}
\newcommand{\icon}[2][]{%
    {%
        \pgfkeys{/icon/.cd,overlay,#1}% "overlay" to prevent infinite loop of overlays
        \def\options{}%
        \ifdefvoid{\width}{}{\edef\options{width=\width,\options}}%
        \ifdefvoid{\overlay}{%
            \edef\graphic{\noexpand\includegraphics[\options]{#2}}%
        }{%
            \edef\temp{\noexpand\begin{overpic}[\options]{#2}}%
            \def\graphic{\temp\put(0,0){\overlay}\end{overpic}}%
        }%
        \graphic%
    }%
}%

\begin{document}

\icondefaults{width=6cm}
\icon{example-image} % Image gets default width 6cm
\icon[width=2cm,overlay={\icon{example-image-overlay}}]{example-image} % Image gets width 2cm, but the overlaid image also gets width 2cm
\icon{example-image} % Image gets default width 6cm

\end{document}

By the way, sorry for all the %. I haven't understood when they are need and not yet.

1

I was able to find a solution to the problem. The following code works like a charm. Hopefully it will be a help to someone sometime :)

\documentclass{article}
\usepackage{tikz}
\usepackage{etoolbox}
\usepackage{overpic}

\pgfkeys{
    /icon/.cd,
    width/.initial,
    overlay/.initial,
    overlay/.store in=\iconoverlay,
    set defaults/.unknown/.code={\pgfkeys{/icon/\pgfkeyscurrentname/.default=#1}}
}
\newcommand\icondefaults[1]{%
    \pgfkeys{/icon/set defaults/.cd, #1}%
}
\newcommand\ifkeyempty[3]{%
    \pgfkeysgetvalue{#1}{\keyvalue}%
    \ifempty{\keyvalue}{#2}{#3}%
}
\newcommand\ifempty[3]{%
    \def\novalue{\pgfkeysnovalue}%
    \def\empty{}%
    \ifboolexpr{test {\ifdefequal{#1}{\empty}} or test {\ifdefequal{#1}{\novalue}}}{#2}{#3}%
}
\newcommand{\icon}[2][]{%
    {%
        \pgfkeys{/icon/.cd,width,overlay,#1}% Reset to default values
        \def\options{}%
        \ifkeyempty{/icon/width}{}{\edef\options{width=\pgfkeysvalueof{/icon/width},\options}}%
        \ifempty{\iconoverlay}{%
            \edef\graphic{\noexpand\includegraphics[\options]{#2}}%
        }{%
            \edef\overlay{\noexpand\begin{overpic}[\options]{#2}}%
            \def\graphic{\overlay\put(0,0){\iconoverlay}\end{overpic}}%
        }%
        \graphic%
    }%
}%

\begin{document}

\icondefaults{width=6cm}
\icon{example-image} % Image gets default width 6cm
\icon[width=2cm,overlay={\icon{example-image-overlay}}]{example-image} % Image gets width 2cm, while the overlaid image gets default width 6cm
\icon{example-image} % Image gets default width 6cm

\end{document}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.