5

I have some coordinates (say A, B, C).

Now I make sth. like this: \foreach \P in {A,B,C} \draw[fill=pink] (\P) circle[radius=2.5pt];

If I would have said \foreach \P in {A,B,C,X} \draw[fill=pink] (\P) circle[radius=2.5pt];

I would have got the error No shape named 'X' is known.

So my question is: How could I have sth. like the symbolic code

\ifcoordinateexist 
\draw[fill=pink]  (\P) circle[radius=2.5pt];
\else % nothing
\fi

I there a simple solution, maybe with TikZ-tools?

enter image description here

\documentclass[border=2mm, tikz]{standalone}
\usepackage{tikz}
\begin{document}

\begin{tikzpicture}[] \coordinatelabel=A at (0,0); \coordinatelabel=B at (2,3); \coordinatelabel=C at (1,1);

% Will work: \foreach \P in {A,B,C} \draw[fill=pink] (\P) circle[radius=2.5pt];

%% Will not work: %\foreach \P in {A,B,C,X} \draw[fill=pink] (\P) circle[radius=2.5pt]; % ---------> No shape named `X' is known. \end{tikzpicture} \end{document}

cis
  • 8,073
  • 1
  • 16
  • 45

2 Answers2

4

I found a solution here: https://tex.stackexchange.com/a/85531/46023

\documentclass[border=2mm, tikz]{standalone}
\usepackage{tikz}
\begin{document}

\makeatletter \long\def\ifcoorddefined#1#2#3{% @ifundefined{pgf@sh@ns@#1}{#3}{#2}% } \makeatother

\begin{tikzpicture}[] \coordinatelabel=A at (0,0); \coordinatelabel=B at (2,3); \coordinatelabel=C at (1,1);

\foreach \P in {A,B,C, X, Y, L, M}{ \ifcoorddefined{\P}{ \draw[fill=pink] (\P) circle[radius=2pt]; }{} } \end{tikzpicture}

\end{document}

enter image description here

muzimuzhi Z
  • 26,474
cis
  • 8,073
  • 1
  • 16
  • 45
  • 1
    +1 some comments: i) coordinate is a kind of specialized nodes, so naming the \ifXXX with \ifNodeDefined is better. ii) tikz nodes are defined globally (also mentioned in Martin Scharrer's original answer), so if there is a node X defined in previous tikzpicture(s), then this test would fail. – muzimuzhi Z Dec 16 '20 at 14:45
  • Ok, thx. ..... ;) – cis Dec 17 '20 at 19:10
  • @ muzimuzhi Z If you want, you could create an else-function and post it as an answer. That could be interesting. – cis Dec 19 '20 at 11:04
  • I'm wondering how to assign a distinct count to every tikzpicture which be used to assign a distinct internal macro to every node. This will take some time since I'm not familiar with the node implementations yet. – muzimuzhi Z Dec 19 '20 at 16:47
  • I added a missing empty argument to use of \ifcoorddefined. – muzimuzhi Z Dec 20 '20 at 22:34
1

As pointed in my previous comment,

tikz nodes are defined globally (also mentioned in Martin Scharrer's original answer), so if there is a node X defined in previous tikzpicture(s), then this test (the \ifcoorddefined in this answer) would fail.

Here is an enhanced tester \ifNodeDefined{<node name>}{<true>}{<false>} which can test whether the given node is defined in the current pgfpicure, an environment internally used by tikzpicture.

\documentclass{article}
\usepackage{tikz}

\makeatletter \long\def\ifcoorddefined#1#2#3{% @ifundefined{pgf@sh@ns@#1}{#3}{#2}% }

\def\ifNodeDefined#1{% @ifundefined{pgf@sh@ns@#1}{@secondoftwo}{% \expandafter\ifx\csname pgf@sh@pi@#1\endcsname\pgfpictureid \expandafter@firstoftwo \else \expandafter@secondoftwo \fi}% } \makeatother

\begin{document}

\begin{tikzpicture} \coordinate[label=X] (X) at (1,0); \coordinate[label=Y] (Y) at (0,1); \end{tikzpicture} \qquad \begin{tikzpicture}[baseline=0pt] \coordinate[label=A] (A) at (0,0); \coordinate[label=B] (B) at (2,3); \coordinate[label=C] (C) at (1,1);

\foreach \P in {A,B,C, X, Y, L, M}{ \ifcoorddefined{\P} {\draw[fill=pink] (\P) circle[radius=2pt];} {} } \node[anchor=north] at (1,-.5) {old tester}; \end{tikzpicture} \qquad \begin{tikzpicture}[baseline=0pt] \coordinate[label=A] (A) at (0,0); \coordinate[label=B] (B) at (2,3); \coordinate[label=C] (C) at (1,1);

\foreach \P in {A,B,C, X, Y, L, M}{ \ifNodeDefined{\P} {\draw[fill=pink] (\P) circle[radius=2pt];} {} } \node[anchor=north] at (1,-.5) {new tester}; \end{tikzpicture}

\end{document}

enter image description here

muzimuzhi Z
  • 26,474