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.
\documentclass{article} 
\usepackage{tikz}
\usetikzlibrary{chains}
\begin{document}
\begin{tikzpicture}[start chain=circle placed {at=(\tikzchaincount*30:1.5)},regular/.style={draw,circle,inner sep=0,minimum size=4mm}]
\foreach \i in {0,...,11}
  \node [on chain, regular] (\i) {\i};
\foreach \i [evaluate=\i as \ni using {int(mod(\i+1,12))}] \i in {0,3,6,9}
  {\draw [->] (\i) to [bend right] node[auto] {$p_b$} (\ni); }
\foreach \i [evaluate=\i as \ni using {int(Mod(\i-1,12))}] \i in {0,3,6,9}
  {\draw [->] (\i) to [bend right] node[auto] {$q_b$} (\ni); }
\foreach \i [evaluate=\i as \ni using {int(mod(\i+1,12))}] \i in {1,2,4,5,7,8,10,11}
  {\draw [->] (\i) to [bend right] node[auto] {$p_g$} (\ni); }
\foreach \i [evaluate=\i as \ni using {int(Mod(\i-1,12))}] \i in {1,2,4,5,7,8,10,11}
  {\draw [->] (\i) to [bend right] node[auto] {$q_g$} (\ni); }
\end{tikzpicture}
\end{document}

gave me

enter image description here

Although I have used node[auto] and there is certainly enough room to layout all the on-the-arrow node labels, they still crowd into a mess. I am aware that I have the option of using node[auto,above] or node[auto,below] to fine-tune the position, but that would make the code lengthy. Is there a simple way to lay out those labels beautifully?

share|improve this question
    
The nodes are placed on inner side. You need to swap them or use auto=right. The problem with auto is that it snaps to the main anchors (multiples of 45). You will need a more sophisticated node setup for such small distances. –  Qrrbrbirlbel Oct 29 '13 at 18:59

4 Answers 4

up vote 5 down vote accepted

Quite similar to the other answers, but with one or two less keystrokes.

\documentclass[border=0.125cm]{standalone}

\usepackage{tikz}
\usetikzlibrary{topaths}

\begin{document}

\begin{tikzpicture}

\foreach \n in {0,...,11}
    \node [draw, circle] at (\n*30+30:2.5) (n-\n) {\n};

\foreach \n [evaluate={\m=int(mod(11+\n, 12)); \p=int(mod(\n+1,3)); \q=int(mod(\n,3)); }] in {0,...,11}{
    \draw [->] (n-\m) to [bend right] node [anchor=\n*30+210] {$P_\ifodd\p b\else g\fi$} (n-\n);
    \draw [<-] (n-\m) to [bend left]  node [anchor=\n*30+30]  {$P_\ifodd\q b\else g\fi$} (n-\n);
}

\end{tikzpicture}

\end{document}

enter image description here

share|improve this answer
    
Really nice code! –  wdg Oct 30 '13 at 3:12

Two problems:

  1. The auto option places the nodes by default to the left, you will need to use auto=right (or the swap option which swaps the default side).
  2. The auto option snaps to the main compass anchors east, north east, north, …, south and south east.

You want to use circle nodes so that anchors are placed in a circle around the node.
You want to use text depth=+0pt or similar solution to hide the different depths of the subscripts.
And you want to use another auto anchor/angle calculator. This is what this answer has to offer.

By the way, you might be interested in the nodes around center key for the placement of nodes in a chain. One might also add the edge nodes via the join style but that’s for another question.

Code

\documentclass[tikz]{standalone}
\usetikzlibrary{chains}
\pgfmathparse{atan2(0,1)}% the CVS version swaps the arguments so I define new atan
                         % functions that have the order of arguments in their name
\ifdim\pgfmathresult pt=0pt % atan2(y, x)
  \tikzset{declare function={atanXY(\x,\y)=atan2(\y,\x);atanYX(\y,\x)=atan2(\y,\x);}}
\else                       % atan2(x, y)
  \tikzset{declare function={atanXY(\x,\y)=atan2(\x,\y);atanYX(\y,\x)=atan2(\x,\y);}}
\fi
\makeatletter
\let\tikz@auto@anchor@orig      \tikz@auto@anchor
\let\tikz@auto@anchor@prime@orig\tikz@auto@anchor@prime
\tikzset{
  Auto/.code=\pgfkeysalso{/tikz/auto=#1}%
    \let\tikz@auto@anchor      \tikz@Auto@anchor
    \let\tikz@auto@anchor@prime\tikz@Auto@anchor@prime,
  auto/.prefix code=\let\tikz@auto@anchor      \tikz@Auto@anchor@orig
                    \let\tikz@auto@anchor@prime\tikz@Auto@anchor@prime@orig}
\def\tikz@Auto@anchor{%
  \pgfmathatanXY@{\pgf@sys@tonumber\pgf@x}{\pgf@sys@tonumber\pgf@y}%
  \pgfutil@tempdima=\pgfmathresult pt\relax
  \advance\pgfutil@tempdima-90pt\relax
  \edef\tikz@anchor{\pgf@sys@tonumber\pgfutil@tempdima}}
\def\tikz@Auto@anchor@prime{%
  \pgfmathatanXY@{\pgf@sys@tonumber\pgf@x}{\pgf@sys@tonumber\pgf@y}%
  \pgfutil@tempdima=\pgfmathresult pt\relax
  \advance\pgfutil@tempdima90pt\relax
  \edef\tikz@anchor{\pgf@sys@tonumber\pgfutil@tempdima}}
\begin{document}
\begin{tikzpicture}[Auto=right,
  start chain=circle placed {at=(\tikzchaincount*30:1.5)},
  regular/.style={draw,circle,inner sep=+0pt,minimum size=+4mm}]
\foreach \i in {0,...,11} \node [on chain, regular] (\i) {\i};
\tikzset{text depth=+0pt, shape=circle, inner sep=+2pt}
\foreach \i [evaluate=\i as \ni using {int(mod(\i+1,12))}] \i in {0,3,6,9}
  {\draw [->] (\i) to [bend right] node {$p_b$} (\ni); }
\foreach \i [evaluate=\i as \ni using {int(Mod(\i-1,12))}] \i in {0,3,6,9}
  {\draw [->] (\i) to [bend right] node {$q_b$} (\ni); }
\foreach \i [evaluate=\i as \ni using {int(mod(\i+1,12))}] \i in {1,2,4,5,7,8,10,11}
  {\draw [->] (\i) to [bend right] node {$p_g$} (\ni); }
\foreach \i [evaluate=\i as \ni using {int(Mod(\i-1,12))}] \i in {1,2,4,5,7,8,10,11}
  {\draw [->] (\i) to [bend right] node {$q_g$} (\ni); }
\end{tikzpicture}
\end{document}

Output

enter image description here

share|improve this answer

With PSTricks just for fun as usual!

\documentclass[pstricks,border=12pt,12pt]{standalone}
\usepackage{pst-node,pst-plot}

\makeatletter
% Get Label
\def\GL#1#2{\pst@mod{#2}{3}\rem\ifcase\rem $#1_b$ \or $#1_g$ \or $#1_g$\fi}
\makeatother

\begin{document}
\begin{pspicture}[radius=12pt,arcangle=30,arrows=<-](-3,-3)(3,3)
    \curvepnodes[plotpoints=13]{0}{360}{2.5 t 30 add PtoC}{P}
    \multido{\i=0+1}{\Pnodecount}{\Cnodeput(P\i){A\i}{\i}}
    \Cnodeput(P\Pnodecount){A\Pnodecount}{}
    \multido{\ix=0+1,\iy=1+1}{\Pnodecount}
    {
        \ncarc{A\iy}{A\ix}\naput{\GL{p}{\ix}}
        \ncarc{A\ix}{A\iy}\naput{\GL{q}{\iy}}
    }
\end{pspicture}
\end{document}

enter image description here

Just another option

\documentclass[pstricks,border=12pt,12pt]{standalone}
\usepackage{pst-node,pst-plot}

\makeatletter
% Get Label
\def\GL#1#2{\pst@mod{#2}{3}\rem\ifcase\rem $#1_b$ \or $#1_g$ \or $#1_g$\fi}
% Angle unit operator
\def\angleunit#1{\degrees[#1]\pstVerb{/angleunit {\pst@angleunit} bind def}}
\makeatother

\begin{document}
\begin{pspicture}[radius=12pt,arcangle=30,arrows=<-](-3,-3)(3,3)
    \angleunit{12}
    \curvepnodes[plotpoints=13]{0}{12}{2.5 t 1 add angleunit PtoC}{P}
    \multido{\i=0+1}{\Pnodecount}{\Cnodeput(P\i){A\i}{\i}}
    \Cnodeput(P\Pnodecount){A\Pnodecount}{}
    \multido{\ix=0+1,\iy=1+1}{\Pnodecount}
    {
        \ncarc{A\iy}{A\ix}\naput{\GL{p}{\ix}}
        \ncarc{A\ix}{A\iy}\naput{\GL{q}{\iy}}
    }
\end{pspicture}
\end{document}

The difference is

\angleunit{12}
\curvepnodes[plotpoints=13]{0}{12}{2.5 t 1 add angleunit PtoC}{P}

where

\makeatletter
\def\angleunit#1{\degrees[#1]\pstVerb{/angleunit {\pst@angleunit} bind def}}
\makeatother

is defined in the preamble.

The simplest one

\documentclass[pstricks,border=12pt,12pt]{standalone}
\usepackage{pst-node,pst-plot}

\makeatletter
% Get Label
\def\GL#1#2{\pst@mod{#2}{3}\rem\ifodd\rem $#1_b$ \else $#1_g$ \fi}
\makeatother

\begin{document}
\begin{pspicture}[radius=12pt,arcangle=30,arrows=<-](-3,-3)(3,3)
    \multido{\i=0+1}{12}{\Cnodeput(!2.5 \i\space 1 add 30 mul PtoC){A\i}{\i}}
    \Cnodeput(A0){A12}{}% auxiliary node
    \multido{\ix=0+1,\iy=1+1}{12}
    {
        \ncarc{A\iy}{A\ix}\naput{\GL{p}{\iy}}
        \ncarc{A\ix}{A\iy}\naput{\GL{q}{\numexpr\ix+2}}
    }
\end{pspicture}
\end{document}

No more significant edit in the future!

share|improve this answer
    
Elegant and short! The only thing is that I think it should be plotpoints=13 to get all the circle with numbers. –  Svend Tveskæg Oct 29 '13 at 19:22
    
check the labels... –  percusse Oct 29 '13 at 19:23
    
@percusse In the question I see labels 0 to 11 so 12 would seem okay, but the output 'only' shows 0 to 10. (Am I missing something obvious?) [I assumed this was a note for me; am I right?] –  Svend Tveskæg Oct 29 '13 at 19:32
1  
@SvendTveskæg there is no alphabetical progression but a pattern modulo three –  percusse Oct 29 '13 at 19:33

Some coordinate calculations are also useful.

\documentclass[tikz]{standalone}
\usetikzlibrary{chains,calc}
\begin{document}
\begin{tikzpicture}[start chain=circle placed {at=(\tikzchaincount*30:1.5)},
                    regular/.style={draw,circle,inner sep=0,minimum size=4mm}]
\foreach \i in {0,...,11}
\node [on chain, regular] (\i) {\i};
\foreach \i [evaluate=\i as \ni using {int(mod(\i+1,12))},
           evaluate=\i as \pi using {int(Mod(\i-1,12))}] \i in {0,...,11}
{
\draw [->] (\i) to [bend right] (\ni);
\draw [->] (\i) to [bend right] (\pi); 
\node[] at ($($(\i)!0.5!(\pi)$)!1!90:(\pi)$) {\pgfmathparse{Mod(\i,3)==0?"$q_b$":"$p_g$"}\pgfmathresult};
\node[] at ($($(\i)!0.5!(\ni)$)!1!90:(\ni)$) {\pgfmathparse{Mod(\i,3)==0?"$p_b$":"$q_g$"}\pgfmathresult};
}

\end{tikzpicture}
\end{document}

enter image description here

share|improve this answer
    
There is \pgfmathprint, you know? :) –  Qrrbrbirlbel Oct 29 '13 at 19:29

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.