Take the 2-minute tour ×
TeX - LaTeX Stack Exchange is a question and answer site for users of TeX, LaTeX, ConTeXt, and related typesetting systems. It's 100% free, no registration required.

I'm using TikZ's \foreach iterator to create a series of nodes and then draw edges between them. First I iterate to create the nodes; then I iterate through the nodes to link them to each other. However, even though I use nearly identical iterators to create and link the nodes, the nodes just created by the first iterator are "unknown" to the second.

These iterators are defined inside a macro created with \newcommand, and involve the use of a style for the nodes, which is perhaps the source of the problem. I create the nodes with

\foreach \s [count=\i from 1][evaluate=\i as \n using \i+#7] in #2 {    
    \node[#4={\n}{\s}{black}] at(..,..){};}

where #2 is a list of labels, #4 is the style to be used, and #7 is the value after which to begin numbering the nodes, and then try to connect the nodes with

\foreach \i [remember=\i as \j (initially #1)] 
        [evaluate=\i as \n using \i+#7]
        [evaluate=\j as \m using \j+#7] in {1,...,#1} {             
    \draw[->,red](\n)--(\m);

where #1 is the number of nodes being created (the length of #2). But, while the set of values assumed by \n and \m in the second loop ought to be (as near as I can tell) and appears to be (if I simply print them out) the same, I get an error message:

Package pgf Error: No shape named 9 is known

where '9' is replaced by whatever 1+#7 is.

Have I missed some subtlety in the way arguments are evaluated? Is some "conversion" taking place that makes what appear to be the same name different? I notice for example that while I get, say, '9.0', etc., when I print out values for \n, the error message says '9' (without the decimal).


Please forgive the complexity of this MWE, it needs to coexist with some other code that requires this structure, and I wanted to make sure to preserve the idiosyncrasies that need to be retained in any solution.

\documentclass[]{scrartcl}
\usepackage{tikz}

\tikzset{                   
    actions/.style n args={3}{circle,draw=#3,inner sep=0pt,minimum size=7mm,label=center:$#2$,name=#1}
}

\begin{document}

\newcommand{\graphring}[7]{
    % Arguments
    % 1 =   Number of nodes
    % 2 =   List of labels for nodes (unused in example)
    % 3 =   Sense of sequence of nodes (1 or -1)
    % 4 =   Node style 
    % 5 =   Drawing scale factor
    % 6 =   Angular position for first node
    % 7 =   Number of previous nodes; added to each node number
    \foreach \s [count=\i from 1]   % \i = Index for positioning; \s = State for labeling
            [evaluate=\i as \angle using #6+(#3)*(\i-1)*(360/#1)]
            [evaluate=\i as \n using \i+#7] in #2 { % \n = Number/name for identification
        \node[#4={\n}{\s}{black}] at({#5*cos(\angle))},{#5*sin(\angle))}){};
    }
    \foreach \i [remember=\i as \j (initially #1)] 
            [evaluate=\i as \n using \i+#7]
            [evaluate=\j as \m using \j+#7] in {1,...,#1} {             
        \draw[->,red](\n)--(\m); % ERROR: Package pgf Error: No shape named <1+#7> is known
    }
}

\begin{center}
\begin{tikzpicture}[scale=3.0]
\graphring{8}{{e,r,r^2,r^3,r^4,r^5,r^6,r^7}}{-1}{actions}{1.0}{90}{0};
\graphring{8}{{f,fr,fr^2,fr^3,fr^4,fr^5,fr^6,fr^7}}{1}{actions}{2.0}{90}{8};
\end{tikzpicture}
\end{center}

\end{document} 
share|improve this question

2 Answers 2

up vote 10 down vote accepted

The first loop names your nodes 1.0, 2.0, and so on. You'll need to use evaluate=\i as \n using int(\i+#7) (and the equivalent for the other loops) to truncate the decimal part:

\documentclass[]{article}
\usepackage{tikz}

\tikzset{                   
    actions/.style n args={3}{circle,draw=#3,inner sep=0pt,minimum size=7mm,label=center:$#2$,name=#1}
}

\begin{document}

\newcommand{\graphring}[7]{
    % Arguments
    % 1 =   Number of nodes
    % 2 =   List of labels for nodes (unused in example)
    % 3 =   Sense of sequence of nodes (1 or -1)
    % 4 =   Node style 
    % 5 =   Drawing scale factor
    % 6 =   Angular position for first node
    % 7 =   Number of previous nodes; added to each node number
    \foreach \s [count=\i from 1]   % \i = Index for positioning; \s = State for labeling
            [evaluate=\i as \angle using #6+(#3)*(\i-1)*(360/#1)]
            [evaluate=\i as \n using int(\i+#7)] in #2 { % \n = Number/name for identification
        \node[#4={\n}{\s}{black}] at({#5*cos(\angle))},{#5*sin(\angle))}){};
    }
    \foreach \i [remember=\i as \j (initially #1)] 
            [evaluate=\i as \n using int(\i+#7)]
            [evaluate=\j as \m using int(\j+#7)] in {1,...,#1} {             
        \draw[->,red](\n)--(\m);
    }
}

\begin{center}
\begin{tikzpicture}[scale=3.0]
\graphring{8}{{e,r,r^2,r^3,r^4,r^5,r^6,r^7}}{-1}{actions}{1.0}{90}{0};
\graphring{8}{{f,fr,fr^2,fr^3,fr^4,fr^5,fr^6,fr^7}}{1}{actions}{2.0}{90}{8};
\end{tikzpicture}
\end{center}

\end{document} 
share|improve this answer
    
I'm embarrassed! I got as far as suspecting a "conversion" issue without taking the next step of "forcing" a uniform conversion myself. Thanks! –  raxacoricofallapatorius Jun 3 '12 at 22:12

You use \n and \m as node names but the nodes you define are not named. Here "shape" means "node". Note that node names have the format <name>.<anchor> where the .<anchor> part is optional. If you use the result of a normal math operation as node name, the integer part is used as name and the fractional part is taken as anchor. Numeric anchors are taken as degrees.

To fix this you need to use proper node names when creating and connecting the nodes. You use name to name the node and there the fractional part might be taken as actual node name, which fails afterwards because you can't refer to such a name later.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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