Graphvizでステートチャート図

Graphvizでステートチャート図を書く。

Graphvizでステートチャート図

digraph sample {
  graph [fontname = "monospace", fontsize = 10, rankdir = TD, compound = true];
  node  [fontname = "monospace", fontsize = 10];
  edge  [fontname = "monospace", fontsize = 10];

  // node
  node  [shape = circle];
  start [height = 0.3, width = 0.3, style = filled, fillcolor = black, label = ""];
  end   [height = 0.3, width = 0.3, style = filled, fillcolor = black, label = "", peripheries = 2];

  node   [shape = record];
  state1 [label = "{\<\<State\>\>\n状態1|entry/入場時アクション\ldo/繰り返しアクション\lexit/退場時アクション\lイベント名/内部遷移アクション\l}"];
  state4 [label = "{\<\<State\>\>\n状態4|}"];

  node   [shape = box];
  folk   [height = 0.01, style = filled, fillcolor = black, label = ""];
  join   [height = 0.01, style = filled, fillcolor = black, label = ""];

  // sub state
  subgraph cluster_sub_state {
    label = "サブ状態";

    // node
    node      [shape = circle];
    sub_start [height = 0.3, width = 0.3, style = filled, fillcolor = black, label = ""];
    sub_end   [height = 0.3, width = 0.3, style = filled, fillcolor = black, label = "", peripheries = 2];

    node   [shape = record];
    state2 [label = "{\<\<State\>\>\n状態2|}"];
    state3 [label = "{\<\<State\>\>\n状態3|}"];

    // edge
    sub_start -> state2;
    state2    -> state3;
    state3    -> state2;
    state2    -> sub_end;

    // rank
    {rank = same; state2; state3}

  }

  // edge
  edge [arrowhead = vee];
  start  -> state1;
  state1 -> folk   [label = "イベント[ガード条件]/アクション"];
  folk   -> state2 [lhead = cluster_sub_state];
  folk   -> state4;
  state3 -> join   [ltail = cluster_sub_state]; 
  state4 -> state4 [label = "自己遷移"];
  state4 -> join;
  join   -> end;

  // rank
}