1

I have a style (POSITION) that references a node by parameter

\documentclass{standalone}
\usepackage{tikz}
\usetikzlibrary
    {%
        positioning,
        shapes.geometric
    }
\tikzset
    {%
        POSITION/.style=
        {%
            below=0mm of #1.left corner,
            anchor=apex
        },
        TRIANGLE/.style=
        {%
            isosceles triangle,
            minimum width=30mm,
            line width=1mm,
            draw
        }
    }
\begin{document}
    \begin{tikzpicture}
        \path node[TRIANGLE](T1){};
        \path node
            [%
                TRIANGLE,
                POSITION={T1}
            ]   (T2){};
    \end{tikzpicture}
\end{document}

but aside from a node parameter (#1) I also need to be able to pass the node's anchor to POSITION style separately (as #2 parameter) so that left corner can be set as default value for the anchor's (#2) parameter (making it optional).

Following is a pseudo code of what I am looking for

POSITION/.style=
  {%
    below=0mm of #1.#2,
    anchor=apex
  }
POSITION/.default={#1}{left corner}

to make POSITION={T1} equal to POSITION={T1}{left corner} while accepting other anchor values (such as POSITION={T1}{right side}).

  • Please provide a proper minimal example we can compile. Fragments of improperly formatted code are not generally very useful. You want .style 2 args, however. – cfr Sep 9 '17 at 1:21
1
<whatever>/.style n args=2{<whatever's definition>},

or

<whatever>/.style 2 args={<whatever's definition>},

However, you need always to specify 2 arguments in this case. If that's not an option, use a separate key for the anchor specification.

Before you dismiss this suggestion an plough into the complications of optional arguments, you should read the accepted answer, at least, to Optional arguments in pgfkeys?. There is a great deal of sense in the approach supported there.

You can use a certain amount of trickery, if you really are sure that this is the right user interface. For example, I use something not entirely dissimilar to the following in chronos (though for somewhat different purposes).

\documentclass[border=10pt]{standalone}
\usepackage{tikz}
\usetikzlibrary{positioning,shapes.geometric}
\tikzset
{%
  POSITION/.style={%
    position aux/.expanded=#1.left corner.a,
  },
  position aux/.style args={#1.#2.#3}{%
    below=0pt of #1.#2, anchor=apex,
  },
  TRIANGLE/.style={%
    isosceles triangle,
    minimum width=30mm,
    line width=1mm,
    draw
  }
}
\begin{document}
\begin{tikzpicture}
  \path node [TRIANGLE] (T1) {};
  \path node [TRIANGLE, POSITION={T1}]   (T2) {};
  \path node [TRIANGLE, POSITION={T1.right corner}]   (T2) {};
\end{tikzpicture}
\end{document}

optional anchoring

  • @bp2017 See tex.stackexchange.com/questions/39834/…. In my opinion, the accepted answer there is right: if you are going to use keys, use keys. Don't try to treat them as dodgy pseudo-macros. – cfr Sep 9 '17 at 12:58
  • 1
    @bp2017 Please see edit above. But note that this is not really recommended as it violates much of the point of a key-value interface. At least, it certainly does so if used willy-nilly and it is not obvious that there's a sufficiently powerful interface reason for supporting an optional argument in this case. (Mark's code may be better as he is a PGF/TikZ guru.) – cfr Sep 9 '17 at 13:30
  • @bp2017 The idea, I think, is that a key-value interface is by its nature verbose and, therefore, transparent to the reader (and author!). So, if you want optional arguments etc., it is generally better to use the kind of thing which does such things i.e. a macro of some kind. However, it is less objectionable if your code is intended for purely personal use and you're sure you won't ever share it. – cfr Sep 9 '17 at 22:26
2

Provided the anchor argument is never going to contain a ., then the following may work:

\documentclass[varwidth,border=5]{standalone}
\usepackage{tikz}
\tikzset{%
  position/.style={
    .. position={#1.left corner.;}
  },
  .. position/.style args={#1.#2.#3;}{
    /utils/exec={[\#1 -> #1, \#2 -> #2]}
  }
}
\begin{document}
\ttfamily
\tikzset{position=T1}

\tikzset{position=T2.right side}
\end{document}

enter image description here

  • 1
    @bp2017 I think the \#1 -> #1 is just printing a hash, followed by a 1, followed by a space-hyphen-greater-than-sign-space, followed by the value of the first argument. Similarly for the version with #2. (See the output in the posted image.) /utils/exec is explained in the TikZ manual. If I remember more-or-less correctly, I think it just executes some code. So, in this case, it is executing the contents of the argument{[\#1 -> #1, \#2 -> #2]}, which will essentially put [\#1 -> #1, \#2 -> #2] into the input stream the TikZ/PGF parser is reading. However, I may be totally wrong. – cfr Sep 9 '17 at 22:31
  • @cfr you are correct in every respect. – Mark Wibrow Sep 11 '17 at 7:39
  • In fact the approach in this answer is pretty much identical to cfr's answer. The .. prefix is arbitrary and merely indicates an auxiliary key which isn't usually called directly. Doesn't matter what the prefix is, a suffix is just as good. – Mark Wibrow Sep 11 '17 at 7:46

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.