class Graph
Graph models directed graphs and subgraphs and outputs in graphviz’s dot format.
Attributes
Global attributes for edges in this graph.
A parent graph, if any. Only used for subgraphs.
Global attributes for this graph.
The name of the graph. Optional for graphs and subgraphs. Prefix the name of a subgraph with “cluster” for subgraph that is boxed.
Global attributes for nodes in this graph.
Shortcut method to create a new colorscheme Attribute instance. If passed n, name must match one of the brewer color scheme names and it will generate accessors for each fillcolor as well as push the colorscheme onto the node_attribs.
An array of subgraphs.
Public Class Methods
# File lib/graph.rb, line 309 def self.escape_label s s = s.to_s.gsub(/\n/, '\n').gsub(/\"/, '\\\"') if s[0] == ?< and s[-1] == ?> then s else "\"#{s}\"" end end
Creates a new graph object. Optional name and parent graph are available. Also takes an optional block for DSL-like use.
# File lib/graph.rb, line 139 def initialize name = nil, graph = nil, &block @name = name @graph = graph graph << self if graph @nodes_order = [] @nodes = Hash.new { |h,k| @nodes_order << k; h[k] = Node.new self, k } @edges_order = [] @edges = Hash.new { |h,k| h[k] = Hash.new { |h2, k2| @edges_order << [k, k2] h2[k2] = Edge.new self, self[k], self[k2] } } @graph_attribs = [] @node_attribs = [] @edge_attribs = [] @subgraphs = [] self.scheme = graph.scheme if graph node_attribs << scheme if scheme instance_eval(&block) if block end
Public Instance Methods
Push a subgraph into the current graph. Sets the subgraph’s graph to self.
# File lib/graph.rb, line 166 def << subgraph subgraphs << subgraph subgraph.graph = self end
Access a node by name
# File lib/graph.rb, line 174 def [] name nodes[name] end
Shortcut method for creating an arrowhead attribute.
# File lib/graph.rb, line 181 def arrowhead shape raise ArgumentError, "Bad arrow shape: #{shape}" unless shape =~ ARROW_RE Attribute.new "arrowhead = #{shape}" end
Shortcut method for creating an arrowsize attribute.
# File lib/graph.rb, line 197 def arrowsize size Attribute.new "arrowsize = #{size}" end
Shortcut method for creating an arrowtail attribute.
# File lib/graph.rb, line 189 def arrowtail shape raise ArgumentError, "Bad arrow shape: #{shape}" unless shape =~ ARROW_RE Attribute.new "arrowtail = #{shape}" end
Shortcut method to create a new fillcolor Attribute instance.
# File lib/graph.rb, line 283 def bgcolor n Attribute.new "bgcolor = %p" % [n] end
Shortcut method to set the global node attributes to use boxes.
# File lib/graph.rb, line 204 def boxes node_attribs << shape("box") end
Shortcut method to create a clustered subgraph in the current graph. Use with the top-level digraph method in block form for a graph DSL.
# File lib/graph.rb, line 397 def cluster name, &block subgraph "cluster_#{name}", &block end
Shortcut method to create a new color Attribute instance.
# File lib/graph.rb, line 211 def color color Attribute.new "color = #{color}" end
Shortcut method to create and set the graph to use a colorscheme.
# File lib/graph.rb, line 226 def colorscheme name, n = nil self.scheme = Attribute.new "colorscheme = %p" % ["#{name}#{n}"] max = COLOR_SCHEME_MAX[name.to_sym] node_attribs << scheme if max scheme end
Shortcut method to rotate and use boxes. Helps compact when there is lots of long text nodes.
# File lib/graph.rb, line 353 def compact! rotate boxes end
Deletes a node from the graph
# File lib/graph.rb, line 403 def delete_node node_name nodes.delete node_name nodes_order.delete node_name edges_order.each do |(a, b)| edges[a].delete b if b == node_name edges.delete a if a == node_name edges.delete a if edges[a].empty? end edges_order.delete_if { |ary| ary.include? node_name } end
Define one or more edges.
edge "a", "b", "c", ...
is equivalent to:
edge "a", "b" edge "b", "c" ...
# File lib/graph.rb, line 252 def edge(*names) last = nil names.each_cons(2) do |from, to| last = self[from][to] end last end
Shortcut method to create a new fillcolor Attribute instance.
# File lib/graph.rb, line 276 def fillcolor n Attribute.new "fillcolor = %p" % [n] end
Shortcut method to create a new font Attribute instance. You can pass in both the name and an optional font size.
# File lib/graph.rb, line 291 def font name Attribute.new "fontname = %p" % [name] end
Shortcut method to create a new fontcolor Attribute instance.
# File lib/graph.rb, line 298 def fontcolor name Attribute.new "fontcolor = %p" % [name] end
Shortcut method to create a new fontsize Attribute instance.
# File lib/graph.rb, line 305 def fontsize size Attribute.new "fontsize = #{size}" end
Creates a new Graph whose edges point the other direction.
# File lib/graph.rb, line 263 def invert result = self.class.new edges.each do |from, h| h.each do |to, edge| result[to][from] end end result end
Shortcut method to set the graph’s label. Usually used with subgraphs.
# File lib/graph.rb, line 321 def label name graph_attribs << "label = #{Graph.escape_label name}" end
Access a node by name, supplying an optional label
# File lib/graph.rb, line 328 def node name, label = nil n = nodes[name] n.label label if label n end
Shortcut method to specify the orientation of the graph. Defaults to the graphviz default “TB”.
# File lib/graph.rb, line 338 def orient dir = "TB" graph_attribs << "rankdir = #{dir}" end
Shortcut method to specify the orientation of the graph. Defaults to “LR”.
# File lib/graph.rb, line 345 def rotate dir = "LR" orient dir end
Saves out both a dot file to path and an image for the specified type. Specify type as nil to skip exporting an image. Specify cmd as the command name like “neato” to use a command other than “dot”.
# File lib/graph.rb, line 363 def save path, type = nil, cmd = "dot" File.open "#{path}.dot", "w" do |f| f.puts self.to_s end system "#{cmd} -T#{type} #{path}.dot > #{path}.#{type}" if type end
Shortcut method to create a new shape Attribute instance.
# File lib/graph.rb, line 373 def shape shape Attribute.new "shape = %p" % [shape] end
Shortcut method to create a new style Attribute instance.
# File lib/graph.rb, line 380 def style name Attribute.new "style = %p" % [name] end
Shortcut method to create a subgraph in the current graph. Use with the top-level digraph method in block form for a graph DSL.
# File lib/graph.rb, line 388 def subgraph name = nil, &block Graph.new name, self, &block end
Outputs a graphviz graph.
# File lib/graph.rb, line 419 def to_s result = [] type = graph ? "subgraph " : "digraph " type = "%s%p" % [type, name] if name and !name.empty? result << type result << " {" graph_attribs.each do |line| result << " #{line};" end unless node_attribs.empty? then result << " node [ #{node_attribs.join(", ")} ];" end unless edge_attribs.empty? then result << " edge [ #{edge_attribs.join(", ")} ];" end subgraphs.each do |line| result << " #{line};" end nodes_order.each do |name| node = nodes[name] result << " #{node};" if graph or node.attributes? or node.orphan? end edges_order.uniq.each do |(from, to)| edge = edges[from][to] result << " #{edge};" end result << " }" result.join "\n" end