3

I have the following three automaton :enter image description here

I want to put them in boxes and add some link, such that I can get something like this:enter image description here

Here is my code :

\documentclass{standalone}
\usepackage{etex}
\usepackage[version=0.96]{pgf}
\usepackage{tikz}
\usetikzlibrary{calc,arrows,shapes,snakes,automata,backgrounds,petri}
\begin{document}
\begin{tikzpicture}[->,node distance=1.3cm,>=stealth',bend angle=20,auto]
  \tikzstyle{place}=[circle,thick,draw=blue!75,fill=blue!20,minimum size=10mm]
  \tikzstyle{red place}=[place,draw=red!75,fill=red!20]
  \tikzstyle{every label}=[red]

  \begin{scope}[local bounding box=scope1,every node/.style={scale=.4}]
% First net
    \node [initial, place] (l0)  {$l0$};
    \node [place] (l1) [xshift=2cm,yshift=-4cm]{$l1$};
    \node [place] (l2) [xshift=-2cm,yshift=-4cm]{$l2$};

    \path (l0) edge [in=30, out=60,loop] node{$eq0$} (l0)
           edge [in=150, out=120,loop] node[above]{$set0$} (l0)
           edge [bend left] node{$set1$} (l1)
           edge [bend right] node[left]{$set2$} (l2)
      (l1) edge [in=60, out=30,loop] node[above]{$set1$} (l1)
           edge [in=-60, out=-30,loop] node[below]{$eq1$} (l1)
           edge [bend left] node[right]{$set0$} (l0)
           edge [bend right] node[above]{$set2$} (l2)
      (l2) edge [in=120, out=150,loop] node[above]{$set2$} (l2)
           edge [in=240, out=210,loop] node[below]{$eq2$} (l2)
           edge [bend right] node[left]{$set0$} (l0)
           edge [bend right] node[below]{$set1$} (l1);
  \end{scope}

  \begin{scope}[shift={($(scope1.east)+(3cm,0)$)},every node/.style={scale=.4}]
% First net
    \node [initial, place] (l1)  {idle};
    \node [place] (l2) [right of=l1,xshift=3cm,label=above:$x\le k$]{req};
    \node [place] (l3)  [below of=l2,yshift=-3cm] {wait};
    \node [place] (l4) [left of=l3,xshift=-3cm]                       {cs};

    \path (l1) edge node[align=center, pos=0.5]{$try\quad reset\{x\}$ } (l2)
          (l2) edge node[align=center, pos=0.5, swap]{$set$ \\ $reset\{x\}$} (l3)
          (l3) edge node[align=center, pos=0.5]{$enter\quad x > k$} (l4)
               edge [bend right] node[align=center, pos=0.5, swap]{$retry$ \\ $reset\{x\}$} (l2)
          (l4) edge node[align=center,pos=0.5]{$exit$} (l1);
  \end{scope}

  \begin{scope}[shift={($(scope1.west)+(-3cm,0)$)},every node/.style={scale=.4}]
% First net
    \node [initial, place] (l1)  {idle};
    \node [place] (l2) [right of=l1,xshift=3cm,label=above:$x\le k$]{req};
    \node [place] (l3)  [below of=l2,yshift=-3cm] {wait};
    \node [place] (l4) [left of=l3,xshift=-3cm]                       {cs};

    \path (l1) edge node[align=center, pos=0.5]{$try\quad reset\{x\}$ } (l2)
          (l2) edge node[align=center, pos=0.5, swap]{$set$ \\ $reset\{x\}$} (l3)
          (l3) edge node[align=center, pos=0.5]{$enter\quad x > k$} (l4)
               edge [bend right] node[align=center, pos=0.5, swap]{$retry$ \\ $reset\{x\}$} (l2)
         (l4) edge node[align=center,pos=0.5]{$exit$} (l1);
  \end{scope}

  \begin{pgfonlayer}{background}
    \filldraw [line width=4mm,join=round,black!10]
     ([yshift=0.5cm]l3  -| l3.east)  rectangle (l4.south  -| l1.west);
  \end{pgfonlayer}


\end{tikzpicture}
\end{document}

I am trying to put these automaton in rectangles and to align them but I could not figure out an efficient way to do it. Any helps would be great.

Many thanks

Torbjørn T.
  • 206,688
Mr. D
  • 397
  • When posting code, could you please make complete examples, so that we can copy-paste and compile the code without making modifications? (Finding the right libraries, defining missing styles (e.g. initial) etc.) – Torbjørn T. Jun 29 '15 at 12:56
  • you can just put this code in a file.tex and then add \input{file} to your main .tex file. initial is just to say which stat is the initial state of the automaton... – Mr. D Jun 29 '15 at 13:36
  • No you can't, you'll get an error saying that \usepackage can only be used in the preamble. To make it into a proper minimal working example, you only would have needed to add a documentclass and document environment, as I did in my edit. It's the automata library that defines the initial style, and if you're not familiar with it, it's a bit hard to guess. – Torbjørn T. Jun 29 '15 at 13:40
  • well you are right – Mr. D Jun 29 '15 at 13:43

1 Answers1

4

Here is one suggestion. Instead of using scopes and shifting those around, I place one of the lower nodes of the two automata on the sides relative to the closest of the lower nodes on the center one. The rectangles are drawn afterwards with the help of the fit library.

Other remarks:

enter image description here

\documentclass[border=3mm]{standalone}
\usepackage{etex}
\usepackage[version=0.96]{pgf}
\usepackage{tikz}
\usetikzlibrary{calc,arrows,shapes,snakes,automata,backgrounds,petri,positioning,fit}

\tikzset{
    ncbar angle/.initial=90,
    ncbar/.style={
        to path=(\tikztostart)
        -- ($(\tikztostart)!#1!\pgfkeysvalueof{/tikz/ncbar angle}:(\tikztotarget)$)
        -- ($(\tikztotarget)!($(\tikztostart)!#1!\pgfkeysvalueof{/tikz/ncbar angle}:(\tikztotarget)$)!\pgfkeysvalueof{/tikz/ncbar angle}:(\tikztostart)$)
        -- (\tikztotarget)
    },
    ncbar/.default=0.5cm,
}
\begin{document}
\begin{tikzpicture}[->,node distance=1.3cm,>=stealth',bend angle=20,auto,
   place/.style={circle,thick,draw=blue!75,fill=blue!20,minimum size=10mm},
   red place/.style={place,draw=red!75,fill=red!20}
   every label/.style={red},
   every node/.style={scale=.4},
   dots/.style={fill=black,circle,inner sep=2pt}]


    \node [initial, place] (l0)  {$l0$};
    \node [place,below=of l0,xshift=2cm] (l1) {$l1$};
    \node [place,below=of l0,xshift=-2cm] (l2) {$l2$};

    \path (l0) edge [in=30, out=60,loop] node{eq0} (l0)
           edge [in=150, out=120,loop] node[above]{set0} (l0)
           edge [bend left] node{set1} (l1)
           edge [bend right] node[left]{set2} (l2)
      (l1) edge [in=60, out=30,loop] node[above]{set1} (l1)
           edge [in=-60, out=-30,loop] node[below]{eq1} (l1)
           edge [bend left] node[right]{set0} (l0)
           edge [bend right] node[above]{set2} (l2)
      (l2) edge [in=120, out=150,loop] node[above]{set2} (l2)
           edge [in=240, out=210,loop] node[below]{eq2} (l2)
           edge [bend right] node[left]{set0} (l0)
           edge [bend right] node[below]{set1} (l1);


    \node [place] (l2-3)  [left=1.8cm of l2] {wait};
    \node [place] (l2-2) [above=of l2-3,label=above:$x\le k$]{req};
    \node [place] (l2-4) [left=of l2-3]                       {cs};
    \node [initial, place, left=of l2-2] (l2-1)  {idle};


    \path (l2-1) edge node[align=center, pos=0.5]{try reset$\{x\}$ } (l2-2)
          (l2-2) edge node[align=center, pos=0.5, swap]{set \\ reset$\{x\}$} (l2-3)
          (l2-3) edge node[align=center, pos=0.5]{enter $x > k$} (l2-4)
               edge [bend right] node[align=center, pos=0.5, swap]{retry \\ reset$\{x\}$} (l2-2)
          (l2-4) edge node[align=center,pos=0.5]{exit} (l2-1);



   \node [place] (l3-4) [right=1.8cm of l1]                      {cs};
   \node [initial, place,above=of l3-4] (l3-1)  {idle};
   \node [place] (l3-2) [right=of l3-1,label=above:$x\le k$]{req};
   \node [place] (l3-3)  [right=of l3-4] {wait};


    \path (l3-1) edge node[align=center, pos=0.5]{try reset $\{x\}$ } (l3-2)
          (l3-2) edge node[align=center, pos=0.5, swap]{set \\ reset$\{x\}$} (l3-3)
          (l3-3) edge node[align=center, pos=0.5]{enter $x > k$} (l3-4)
               edge [bend right] node[align=center, pos=0.5, swap]{retry \\ reset$\{x\}$} (l3-2)
         (l3-4) edge node[align=center,pos=0.5]{exit} (l3-1);


  \begin{pgfonlayer}{background}
    \filldraw [line width=4mm,join=round,black!10]
     ([yshift=0.5cm]l2-3  -| l2-3.east)  rectangle (l2-4.south  -| l2-1.west);
  \end{pgfonlayer}

\node [inner sep=3.2cm, draw, fit=(l0)(l1)(l2)] (rec1) {};
\node [inner sep=3.2cm, inner xsep=3.8cm, draw, fit=(l2-1)(l2-2)(l2-3)(l2-4)] (rec2) {};
\node [inner sep=3.2cm, ,inner xsep=3.8cm, draw, fit=(l3-1)(l3-2)(l3-3)(l3-4)] (rec3) {};

\node [dots,label=-90:sync1] (sync1) at ($(rec2.north west)!0.3!(rec2.north east)$) {};
\node [dots,label=-90:set1] (set1) at ($(rec2.north west)!0.7!(rec2.north east)$) {};
\node [dots,label=-90:sync3] (sync3) at ($(rec3.north west)!0.7!(rec3.north east)$) {};
\node [dots,label=-90:sync3] (set3) at ($(rec3.north west)!0.3!(rec3.north east)$) {};
\node [dots,label=-90:get1] (get1) at ($(rec1.north west)!0.2!(rec1.north east)$) {};
\node [dots,label=-90:get3] (get2) at ($(rec1.north west)!0.8!(rec1.north east)$) {};
\node [dots,label=-90:sync] (sync) at ($(rec1.north west)!0.5!(rec1.north east)$) {};

\node (a1) [coordinate,label=90:$a_1$] at ([yshift=1cm]sync) {};

\draw [-] (sync1) |- (a1) -- (sync);
\draw [-] (sync3) |- (a1);
\draw [-] (set1) to[ncbar] (get1);
\draw [-] (set3) to[ncbar=-0.5cm] (get2);

\end{tikzpicture}
\end{document}
Torbjørn T.
  • 206,688