Class: MiniMindmap::Mindmap

Inherits:
Object
  • Object
show all
Defined in:
lib/mini_mindmap.rb

Constant Summary collapse

@@compiles_meta =
{
  basic: {
    id: "basic",
    description: "basic expression",
    syntax: /^(\*+)\s+([^\s]*[^\[\]]*)\s*(\[.*\])*\s*(\/\/.*)*\s*$/,
    processor: "basic_processor",
  },
  annotation: {
    id: "annotation",
    description: "annotation expression",
    syntax: /^\s*\/\/.*\s*/,
    processor: "annotation_processor",
  }
}

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(name, dsl, output = {}, config = {}) {|_self| ... } ⇒ Mindmap

Returns a new instance of Mindmap.

Yields:

  • (_self)

Yield Parameters:



27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
# File 'lib/mini_mindmap.rb', line 27

def initialize(name, dsl,output={},config={})

  @name = name
  @dsl = dsl
  @config =  {
    rankdir: 'LR', # "TB", "LR", "BT", "RL", 分别对应于从上到下,从左到右,从下到上和从右到左绘制的有向图
    node: {},
    edge: {}
  }.deep_merge(config)
  @output = {
    dir: Dir.home,
    format: "png"
  }.deep_merge(output) 

  yield(self) if block_given?
end

Instance Attribute Details

#configObject

Returns the value of attribute config.



44
45
46
# File 'lib/mini_mindmap.rb', line 44

def config
  @config
end

#declaresObject

Returns the value of attribute declares.



44
45
46
# File 'lib/mini_mindmap.rb', line 44

def declares
  @declares
end

#dslObject

Returns the value of attribute dsl.



44
45
46
# File 'lib/mini_mindmap.rb', line 44

def dsl
  @dsl
end

#nameObject

Returns the value of attribute name.



44
45
46
# File 'lib/mini_mindmap.rb', line 44

def name
  @name
end

#nodesObject

Returns the value of attribute nodes.



44
45
46
# File 'lib/mini_mindmap.rb', line 44

def nodes
  @nodes
end

#outputObject

Returns the value of attribute output.



44
45
46
# File 'lib/mini_mindmap.rb', line 44

def output
  @output
end

Class Method Details

.compiles_metaObject



23
24
25
# File 'lib/mini_mindmap.rb', line 23

def self.compiles_meta
  @@compiles_meta
end

Instance Method Details

#basic_processorObject



68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
# File 'lib/mini_mindmap.rb', line 68

def basic_processor
  declares = [];
  nodes = []
  stack = []
  dsl = @dsl.split("\n")
  dsl.each_with_index do |code, current_index|

    if not code.strip.empty?
      current_id = current_index
      current = self.compile(code)
      if not current
        next
      end
      current.unshift(current_id)
      # [id, type_id, level, content, config]


      current_declare = "node#{current_id}[label=\"#{current[3]}\"]";
      declares.push(current_declare)

      unless stack.empty?
        top = stack.pop
        if current[2] > top[2]
          node_line = "node#{top[0]} -> node#{current[0]}"
          if current.length >=5
            node_line += " #{current[4]}"
          end
          nodes << node_line 
          stack.push(top)
        else
          while (current[2] <= top[2]) and (not stack.empty?)
            top = stack.pop
          end
          if current[2] > top[2]
            node_line = "node#{top[0]} -> node#{current[0]}"
            if current.length >=5
              node_line += " #{current[4]}"
            end
            nodes << node_line 
            stack.push top
          end
          
        end
      end
      stack.push(current)
    end
  end
  @declares = declares
  @nodes = nodes
end

#compile(code) ⇒ Object



46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
# File 'lib/mini_mindmap.rb', line 46

def compile(code)
  # TODO  增加拓展语法支持 label等自定义
  case code.strip
  when @@compiles_meta[:basic][:syntax]
    level_prefix = $1
    content = $2
    config = $3
    level = level_prefix.length
    node = [@@compiles_meta[:basic][:id],level, content]

    if config
      node.push(config)
    end
  
    return node
  when @@compiles_meta[:annotation][:syntax]
    # pass annotation  
  else
    # rest pass
  end
end

#exportObject



151
152
153
154
155
156
157
# File 'lib/mini_mindmap.rb', line 151

def export
  self.run_tasks
  export = self.export_cmd

  puts("[command]: #{export}")
  `#{export}`
end

#export_cmdObject



143
144
145
146
147
148
149
# File 'lib/mini_mindmap.rb', line 143

def export_cmd
  output_dir = @output[:dir]
  output_file = File.join(output_dir, "#{@name}.#{@output[:format]}")

  output_dotfile = File.join(output_dir, "#{@name}.dot")
  "dot #{output_dotfile} -T #{@output[:format]} -o #{output_file}"
end

#nodes_to_docObject



129
130
131
132
133
134
135
# File 'lib/mini_mindmap.rb', line 129

def nodes_to_doc
  output_dir = File.absolute_path(@output[:dir])
  FileUtils::mkdir_p output_dir
  output_file = File.join(output_dir, "#{@name}.dot")

  File.open("#{output_file}", "w") { |f| f.write(package_nodes) }
end

#package_nodesObject



123
124
125
126
127
# File 'lib/mini_mindmap.rb', line 123

def package_nodes
  node_config = @config[:node].map {|k,v| "#{k}=\"#{v}\""}.join(",")
  edge_config = @config[:edge].map {|k,v| "#{k}=\"#{v}\""}.join(",")
  "digraph \"#{@name}\" {\nrankdir = #{@config[:rankdir]};\nnode [#{node_config}];\nedge [#{edge_config}];\n#{@declares.join("\n")}\n#{@nodes.join("\n")}\n}"
end

#processorObject



119
120
121
# File 'lib/mini_mindmap.rb', line 119

def processor
  self.send @@compiles_meta[:basic][:processor]  
end

#run_tasksObject



137
138
139
140
141
# File 'lib/mini_mindmap.rb', line 137

def run_tasks
  self.processor
  self.package_nodes
  self.nodes_to_doc
end