bash-visual 1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,60 @@
1
+ require 'font'
2
+
3
+ class Builder
4
+
5
+ def initialize (font = Font.new)
6
+ @default_font = font
7
+ end
8
+
9
+ def clear
10
+ set_position(0, 0) + "\e[2J"
11
+ end
12
+
13
+ def erase_to_end_line
14
+ "\e[K"
15
+ end
16
+
17
+ def restore_position
18
+ "\e[u"
19
+ end
20
+
21
+ def save_position
22
+ "\e[s"
23
+ end
24
+
25
+ def set_position (x, y)
26
+ "\e[#{y.to_i};#{x.to_i}H"
27
+ end
28
+
29
+ def move_position(offset_x, offset_y)
30
+ bash = ''
31
+ if (offset_y > 0)
32
+ bash << "\e[#{offset_y}B"
33
+ else
34
+ bash << "\e[#{offset_y.abs}A"
35
+ end
36
+ if (offset_x > 0)
37
+ bash << "\e[#{offset_x}C"
38
+ else
39
+ bash << "\e[#{offset_x.abs}D"
40
+ end
41
+ bash
42
+ end
43
+
44
+ def write_to_position (x, y, text, font = @default_font)
45
+ bash = ''
46
+ bash << save_position()
47
+ bash << move_position(x, y)
48
+ bash << write(text, font)
49
+ bash << restore_position()
50
+ bash
51
+ end
52
+
53
+ def write (text, font = @default_font)
54
+ font.to_bash + text + Font::RESET
55
+ end
56
+
57
+ def write_ln (text, font = @default_font)
58
+ font.to_bash + text << "\n" << Font::RESET
59
+ end
60
+ end
@@ -0,0 +1,143 @@
1
+ # coding: utf-8
2
+ $:.unshift(File.dirname(__FILE__))
3
+ require 'font'
4
+ require 'builder'
5
+
6
+ class Console
7
+ @@mutex = Mutex.new
8
+
9
+ OUTPUT_STRING = 0
10
+ OUTPUT_WITHOUT_BLOCK = 1
11
+ OUPUT_WITH_BLOCK = 2
12
+ # see: http://en.wikipedia.org/wiki/Box-drawing_characters
13
+ BORDER_UTF = ["\u250C","\u2500","\u2510",
14
+ "\u2502", "\u2502",
15
+ "\u2514","\u2500","\u2518"]
16
+
17
+ BORDER_UTF_ROUND = ["\u256D","\u2500","\u256E",
18
+ "\u2502", "\u2502",
19
+ "\u2570","\u2500","\u256F"]
20
+
21
+ BORDER_UTF_DOUBLE = ["\u2554","\u2550","\u2557",
22
+ "\u2551", "\u2551",
23
+ "\u255A","\u2550","\u255D"]
24
+
25
+ attr_reader :current_x, :current_y, :font;
26
+
27
+ def initialize (font = Font.new, way_outnput = OUTPUT_WITHOUT_BLOCK, builder = Builder.new)
28
+ @current_x = 0
29
+ @current_y = 0
30
+ @font = font
31
+ @way_output = way_outnput
32
+ @builder = builder
33
+ end
34
+
35
+ def position= coord
36
+ @current_x , @current_y = *coord
37
+ print @builder.set_position(@current_x, @current_y)
38
+ end
39
+
40
+ def move_position(offset_x, offset_y)
41
+ @current_x += offset_x
42
+ @current_y += offset_y
43
+ print @builder.move_position(offset_x, offset_y)
44
+ end
45
+
46
+ # Записать что-то в определенной позиции, а потом вернуться на текущую
47
+ # Если необходимо сохранить позицию после записи - используйте связку
48
+ # move_position/position= и write
49
+ def write_to_position (x, y, text, font = @font)
50
+ print @builder.write_to_position(x, y, text, font)
51
+ end
52
+
53
+ def write (text, font = @font)
54
+ print @builder.write(text, font)
55
+ end
56
+
57
+ def write_ln (text, font = @font)
58
+ print @builder.write_ln(text, font)
59
+ end
60
+
61
+ def erase_to_end_line
62
+ print @builder.erase_to_end_line
63
+ end
64
+
65
+ def draw_rectangle(x, y, width, height, font = nil)
66
+ bash = ''
67
+ bash << @builder.save_position()
68
+ bash << @builder.set_position(x,y)
69
+ height.times do
70
+ bash << @builder.write(' ' * width, font)
71
+ bash << @builder.move_position(-width, 1)
72
+ end
73
+ bash << @builder.restore_position()
74
+ print @builder.write(bash, font)
75
+ end
76
+
77
+ def draw_border(x, y, width, height, font = nil, border = BORDER_UTF)
78
+ raise 'width,height must be great than 1' if (width < 2 or height < 2)
79
+
80
+ bash = ''
81
+ bash << @builder.save_position()
82
+ bash << @builder.set_position(x,y)
83
+
84
+ bash << @builder.write(border[0] + border[1] * (width - 2) + border[2], font)
85
+ (height - 2).times do
86
+ bash << @builder.move_position(-width, 1)
87
+ bash << @builder.write(border[3] + ' ' * (width - 2) + border[4], font)
88
+ end
89
+ bash << @builder.move_position(-width, 1)
90
+ bash << @builder.write(border[5] + border[6] * (width - 2) + border[7], font)
91
+
92
+ bash << @builder.restore_position()
93
+ print @builder.write(bash, font)
94
+ end
95
+
96
+ def draw_window(x, y, width, height, text = '', font = nil, border = BORDER_UTF_DOUBLE, text_wrap = ["\u2561","\u255E"])
97
+ raise 'width,height must be great than 2' if (width < 3 or height < 3)
98
+
99
+ text = text.slice(0, width - 2)
100
+ if text.size < (width - 3) && (text_wrap.instance_of? Array)
101
+ text = text_wrap[0] + text + text_wrap[1]
102
+ end
103
+ text = text.center(width - 2, border[1])
104
+ bash = ''
105
+ bash << @builder.save_position()
106
+ bash << @builder.set_position(x,y)
107
+
108
+ bash << @builder.write(border[0] + text + border[2], font)
109
+ (height - 2).times do
110
+ bash << @builder.move_position(-width, 1)
111
+ bash << @builder.write(border[3] + ' ' * (width - 2) + border[4], font)
112
+ end
113
+ bash << @builder.move_position(-width, 1)
114
+ bash << @builder.write(border[5] + border[6] * (width - 2) + border[7], font)
115
+
116
+ bash << @builder.restore_position()
117
+ print @builder.write(bash, font)
118
+ end
119
+
120
+ # Clear the screen and move to (0,0)
121
+ def clear
122
+ @current_x = 0
123
+ @current_y = 0
124
+ print @builder.clear
125
+ end
126
+
127
+ def font= font
128
+ @font = font
129
+ end
130
+
131
+ private
132
+ def print string
133
+
134
+ return string if OUTPUT_STRING == @way_output
135
+
136
+ if OUPUT_WITH_BLOCK == @way_output
137
+ @@mutex.synchronize {super}
138
+ else
139
+ super
140
+ end
141
+ end
142
+
143
+ end
data/lib/bash/font.rb ADDED
@@ -0,0 +1,91 @@
1
+
2
+ class Font
3
+ BLACK = 0
4
+ RED = 1
5
+ GREEN = 2
6
+ BROWN = 3
7
+ BLUE = 4
8
+ MAGENTA = 5
9
+ CYAN = 6
10
+ LIGHT_GRAY = 7
11
+
12
+ GRAY = 10
13
+ LIGHT_RED = 11
14
+ LIGHT_GREEN = 12
15
+ YELLOW = 13
16
+ LIGHT_BLUE = 14
17
+ LIGHT_MAGENTA = 15
18
+ LIGHT_CYAN = 16
19
+ WHITE = 17
20
+
21
+ RESET = "\e[0m"
22
+
23
+ #types font
24
+ STD = 0
25
+ BOLD = 1
26
+ UNDERLINE = 2
27
+ BLINK = 4
28
+
29
+ attr_reader :font, :foreground, :background
30
+
31
+ def initialize (font = STD, foreground = WHITE, background = nil)
32
+ raise "not found color #{foreground}" unless (0..7).cover? foreground or (10..17).cover? foreground
33
+ @font, @foreground, @background = font, foreground, background
34
+
35
+ @bash_command = ''
36
+
37
+ @string = "<type=%s, foreground=%s, background=%s>" % [@font, @foreground, @background]
38
+ if font == STD
39
+ if foreground and foreground < 10
40
+ @bash_command << "\e[3#{foreground}m"
41
+ else
42
+ @bash_command << "\e[9#{foreground-10}m"
43
+ end
44
+ end
45
+
46
+ if font & BOLD != 0
47
+ if foreground < 10
48
+ @bash_command << "\e[1;3#{foreground}m"
49
+ else
50
+ @bash_command << "\e[1;9#{foreground-10}m"
51
+ end
52
+ end
53
+
54
+ if font & UNDERLINE != 0
55
+ if foreground < 10
56
+ @bash_command << "\e[4;3#{foreground}m"
57
+ else
58
+ @bash_command << "\e[4;9#{foreground-10}m"
59
+ end
60
+ end
61
+
62
+ if background.instance_of? Fixnum
63
+ if background < 10
64
+ @bash_command << "\e[4#{background}m"
65
+ else
66
+ @bash_command << "\e[10#{background-10}m"
67
+ end
68
+ end
69
+
70
+ end
71
+
72
+ def to_bash
73
+ @bash_command
74
+ end
75
+
76
+ def to_s
77
+ @string
78
+ end
79
+
80
+ class << self
81
+ def rand_color (exclude_color = nil)
82
+ color = rand(14)
83
+ color += 1 if color == exclude_color
84
+ color = 0 if color > 14
85
+ color += 3 if color > 7
86
+ color
87
+ end
88
+ end
89
+
90
+
91
+ end
@@ -0,0 +1,12 @@
1
+ $:.unshift(File.dirname(__FILE__))
2
+ class RandomText
3
+ @@text = File.open(File.dirname(__FILE__)+'/utf') { |file| file.read }
4
+ class << self
5
+ def get
6
+ aText = @@text.split(' ')
7
+ len = Random.new.rand(1...70)
8
+ max = Random.new.rand(0...aText.size-len)
9
+ aText[max, len].join(' ')
10
+ end
11
+ end
12
+ end
data/lib/example1.rb ADDED
@@ -0,0 +1,86 @@
1
+ # coding: utf-8
2
+ $:.unshift(File.dirname(__FILE__))
3
+
4
+ require 'bash/console'
5
+ require 'bash/font'
6
+ require 'scroll'
7
+ require 'vertical_scroll'
8
+ require 'horizontal_scroll'
9
+ require 'common/random_text'
10
+
11
+
12
+ def join_all
13
+ main = Thread.main
14
+ current = Thread.current
15
+ all = Thread.list
16
+ all.each {|t| t.join unless t == current or t == main}
17
+ end
18
+
19
+ default_font = Font.new(Font::STD, Font::LIGHT_BLUE)
20
+
21
+
22
+ console = Console.new(default_font)
23
+ console.clear()
24
+
25
+ window_font = Font.new(Font::STD, Font::WHITE, Font::BLUE)
26
+
27
+
28
+ font_scroll = Font.new(Font::STD, Font::YELLOW)
29
+
30
+ scroll = VerticalScroll.new(
31
+ coordinates: [41, 1],
32
+ window_size: [80, 28],
33
+ message_block_size: 23,
34
+ font: font_scroll,
35
+ separator: "\u2508",
36
+ start: Scroll::ENDING,
37
+ adapt_size_message: true,
38
+ prefix: ->{ Time.now.strftime('%H-%M-%S:%3N') << " " }
39
+ )
40
+
41
+
42
+ console.draw_window(4, 31, 122, 6, 'Example List', window_font, Console::BORDER_UTF_DOUBLE)
43
+
44
+ scroll2 = HorizontalScroll.new(
45
+ coordinates: [4, 31],
46
+ window_size: [120, 4],
47
+ message_block_size: 10,
48
+ font: font_scroll,
49
+ separator: true,
50
+ start: Scroll::BEGINNING
51
+ )
52
+
53
+ 1.upto(28) { |y|
54
+ if (10..20).include? y
55
+ console.write_to_position(121, y, "\u2503")
56
+ else
57
+ console.write_to_position(121, y, "\u2502")
58
+ end
59
+
60
+ }
61
+
62
+ Thread.new do
63
+ 1000.times do
64
+ font = Font.new(Font::BOLD, rand(7), nil)
65
+ x = rand(40)
66
+ y = rand(30)
67
+ console.write_to_position(x, y, '.', font)
68
+
69
+ font = Font.new(Font::STD, Font::rand_color(window_font.background), window_font.background)
70
+ scroll.add(RandomText::get(), font)
71
+ scroll2.add(RandomText::get(), font)
72
+
73
+ sleep(0.7)
74
+ end
75
+ end
76
+ Thread.new do
77
+ 1000.times do
78
+ font = Font.new(Font::STD, window_font.foreground, window_font.background)
79
+ scroll2.add(RandomText::get(), font)
80
+
81
+ sleep(0.3)
82
+ end
83
+ end
84
+
85
+
86
+ join_all
@@ -0,0 +1,69 @@
1
+ require 'scroll'
2
+
3
+ class HorizontalScroll < Scroll
4
+
5
+ DEFAULT_SEPARATOR = "\u2502"
6
+
7
+ def initialize options
8
+ super
9
+ @message_block_width = @message_block_size
10
+
11
+ @separator =
12
+ if @separator == true; DEFAULT_SEPARATOR
13
+ elsif @separator.instance_of? String; @separator[0]
14
+ else nil
15
+ end
16
+ end
17
+
18
+ def get_x_position available_area_width, message_width = 0
19
+ if (@start == BEGINNING)
20
+ @x + (@area_width - available_area_width)
21
+ else
22
+ @x + available_area_width - message_width
23
+ end
24
+ end
25
+
26
+ def print_message message, font, available_area
27
+
28
+ available_area_width, available_area_height = available_area
29
+ avail_width = @message_block_width > available_area_width ? available_area_width : @message_block_width
30
+
31
+
32
+ (available_area_height - message.size).times {
33
+ message << ''
34
+ }
35
+
36
+ if @adapt_size_message
37
+ message_width = rows_wrap! message, available_area_width
38
+ else
39
+ rows_wrap! message, avail_width
40
+ message_width = avail_width
41
+ end
42
+
43
+ message = message.slice(0, available_area_height) if message.size > available_area_height
44
+
45
+ message.map! do |row|
46
+ row.strip.ljust(message_width)
47
+ end
48
+
49
+ if @separator and @separator.size.nonzero?
50
+ if @adapt_size_message
51
+ if message_width < available_area_width
52
+ message.map! do |row|
53
+ row << @separator
54
+ end
55
+ message_width += 1
56
+ end
57
+ else
58
+ message.each do |row|
59
+ row[message_width-1] = @separator
60
+ end
61
+ end
62
+ end
63
+
64
+ write(get_x_position(available_area_width, message_width), @y, message, font)
65
+
66
+ [available_area_width - message_width, available_area_height]
67
+ end
68
+
69
+ end
data/lib/main.rb ADDED
@@ -0,0 +1,71 @@
1
+ ####!> coding:
2
+ $:.unshift(File.dirname(__FILE__))
3
+ print "\u2580"
4
+ exit
5
+ 255.downto(0) { |i|
6
+ puts i.chr
7
+ }
8
+
9
+ exit
10
+ require 'bash/console'
11
+ require 'bash/font'
12
+ require 'scroll'
13
+
14
+ font = Font.new(Font::STD, Font::LIGHT_BLUE)
15
+
16
+ #
17
+ console = Console.new(font)
18
+ console.clear()
19
+ #console.write_ln('+' << '-' * 59 << '+')
20
+ #console.write_ln(("| %9s " % 'Thread') * 5 << '|')
21
+ #console.write_ln('+' << '-' * 59 << '+')
22
+
23
+ #####console.draw_rectangle(1, 1, 100, 40, Font::get(Font::STD, Font::STD, nil))
24
+
25
+ font_scroll = Font.new(Font::STD, Font::YELLOW, Font::BLACK)
26
+
27
+ font_scroll1 = Font.new(Font::STD, Font::LIGHT_GREEN, Font::BLACK)
28
+
29
+
30
+ scroll = Scroll.new(
31
+ coordinates: [100, 3],
32
+ size: [80, 20],
33
+ message_block_size: [80, 3],
34
+ message_crop?: true,
35
+ message_keep: 0,
36
+ type: Scroll::VERTICAL,
37
+ font: font_scroll,
38
+ separator: ' ',
39
+ start: Scroll::BEGINNING
40
+ # prefix: ->{ Time.now.strftime('%H-%M-%S:%3N') << "\n" }
41
+ )
42
+
43
+ at_exit do |unusedlocal|
44
+ #console.clear()
45
+ end
46
+
47
+ #Thread.new {
48
+ #
49
+ # scroll.add(gets())
50
+ #}
51
+
52
+ generator = ->(count){
53
+ value = ''
54
+ 25.times {value << (65 + rand(25)).chr}
55
+ value
56
+ }
57
+
58
+ 100000.times {
59
+ font = Font.new(Font::BOLD, rand(7), nil)
60
+ x = rand(100)
61
+ y = rand(40)
62
+ console.write_to_position(x, y, '.', font)
63
+ #
64
+ #scroll.add("\n01234" * 4, font_scroll2)
65
+
66
+ #scroll.add(generator.(50).to_s, font_scroll1)
67
+
68
+ scroll.add('' << '[]' * rand(40) << "\n1111\n1221")
69
+
70
+ sleep(0.4)
71
+ }
data/lib/scroll.rb ADDED
@@ -0,0 +1,120 @@
1
+ $:.unshift(File.dirname(__FILE__))
2
+
3
+ require 'console'
4
+
5
+ class Scroll
6
+
7
+ FORWARD = 1
8
+ BACKWARD = -1
9
+
10
+ BEGINNING = false
11
+ ENDING = true
12
+
13
+ attr_accessor :console
14
+
15
+ def initialize(options)
16
+
17
+ @x, @y = options[:coordinates]
18
+ @x = @x.to_i
19
+ @y = @y.to_i
20
+
21
+ raise ':window_size isn\'t array' unless options[:window_size].instance_of? Array
22
+ raise 'size :window_size must be great than 1' if options[:window_size].size < 2
23
+
24
+ @area_width, @area_height = options[:window_size]
25
+ @area_width = @area_width.to_i
26
+ @area_height = @area_height.to_i
27
+
28
+ @message_block_size = options[:message_block_size] ? options[:message_block_size].to_i : 1
29
+ @message_block_size = 1 if @message_block_size < 1
30
+
31
+ @prefix = options[:prefix] ? options[:prefix] : nil
32
+
33
+ @adapt_size_message = options[:adapt_size_message] ? options[:adapt_size_message] : false
34
+
35
+ @is_wrap = true
36
+ @start = options[:start] ? ENDING : BEGINNING
37
+ @separator = options[:separator] ? options[:separator] : false
38
+ @font = options[:font] ? options[:font] : nil
39
+
40
+ @stack = []
41
+ @console = Console.new @font,Console::OUTPUT_STRING
42
+ @mutex = Mutex.new
43
+ end
44
+
45
+ def scroll(positions = 1, direction = @direction * positions)
46
+
47
+ end
48
+
49
+ def add (message, font = @font)
50
+
51
+ if @stack.size.zero?
52
+ print @console.draw_rectangle(@x + 1, @y + 1, @area_width, @area_height, font)
53
+ end
54
+
55
+ @stack << {
56
+ message: prefix() << message.to_s,
57
+ font: font
58
+ }
59
+
60
+ redraw()
61
+ #@stack.slice!(-index, index)
62
+ end
63
+
64
+ def prefix= (prefix)
65
+ @prefix = prefix
66
+ end
67
+
68
+ def prefix
69
+ if (defined? @prefix.call)
70
+ @prefix[].to_s
71
+ else
72
+ ''
73
+ end
74
+ end
75
+
76
+ private
77
+
78
+ def redraw
79
+ avail_area = [@area_width, @area_height]
80
+ @stack.reverse.each do |item|
81
+
82
+ message = item[:message].dup.lines.to_a
83
+ font = item[:font]
84
+ unless font.background
85
+ font = Font.new font.font, font.foreground, @font.background
86
+ end
87
+
88
+ avail_area = print_message(message, font, avail_area)
89
+ # выходим если закончилось место в области
90
+ return nil if avail_area[0] <= 0 or avail_area[1] <= 0
91
+ end
92
+ end
93
+
94
+ # сделать переносы в массиве строк
95
+ def rows_wrap! arr, max_len
96
+ max_used_len = 1
97
+ arr.each_with_index do |row, i|
98
+ len = row.size
99
+ max_used_len = len if len > max_used_len
100
+ next if len <= max_len
101
+ tail = row.slice!(max_len, len-max_len)
102
+ arr.insert(i+1, tail)
103
+ end
104
+ max_used_len
105
+ end
106
+
107
+ def write (x, y, message, font)
108
+
109
+
110
+ string = ''
111
+ message.each_with_index { |text, i|
112
+ string << @console.write_to_position(x, y + i, text, font)
113
+ }
114
+
115
+ @mutex.synchronize {
116
+ print string
117
+ }
118
+ end
119
+ end
120
+
@@ -0,0 +1,54 @@
1
+ require 'scroll'
2
+
3
+ class VerticalScroll < Scroll
4
+
5
+ def initialize options
6
+ super
7
+ @message_block_height = @message_block_size
8
+ end
9
+
10
+ def get_y_position available_area_height, message_size = 0
11
+ if (@start == BEGINNING)
12
+ @y + (@area_height - available_area_height)
13
+ else
14
+ @y + available_area_height - message_size
15
+ end
16
+ end
17
+
18
+ def print_message message, font, available_area
19
+
20
+ available_area_width, available_area_height = available_area
21
+ avail_height = @message_block_height > available_area_height ? available_area_height : @message_block_height
22
+
23
+ rows_wrap!(message, available_area_width) if @is_wrap
24
+
25
+ if @adapt_size_message
26
+ message = message.slice(0, available_area_height) if message.size > available_area_height
27
+ else
28
+ message = message.slice(0, avail_height) if message.size > avail_height
29
+ end
30
+
31
+ message.map! do |row|
32
+ row.strip.ljust(available_area_width)
33
+ end
34
+
35
+ if @separator == true
36
+ message[message.size-1] = Font.new(Font::UNDERLINE, font.foreground, font.background).to_bash +
37
+ message.last.ljust(available_area_width, ' ')
38
+ end
39
+
40
+ if (@separator.instance_of? String)
41
+ if (message.size > available_area_height)
42
+ message[message.size-1] = @separator[0] * available_area_width
43
+ else
44
+ message << @separator[0] * available_area_width
45
+ end
46
+ end
47
+
48
+ write(@x, get_y_position(available_area_height, message.size), message, font)
49
+
50
+
51
+ [available_area_width, available_area_height - message.size]
52
+ end
53
+
54
+ end
metadata ADDED
@@ -0,0 +1,62 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: bash-visual
3
+ version: !ruby/object:Gem::Version
4
+ prerelease:
5
+ version: "1.0"
6
+ platform: ruby
7
+ authors:
8
+ - Almazko
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2011-12-25 00:00:00 Z
14
+ dependencies: []
15
+
16
+ description:
17
+ email: a.s.suslov@gmail.com
18
+ executables: []
19
+
20
+ extensions: []
21
+
22
+ extra_rdoc_files: []
23
+
24
+ files:
25
+ - ./lib/scroll.rb
26
+ - ./lib/example1.rb
27
+ - ./lib/vertical_scroll.rb
28
+ - ./lib/main.rb
29
+ - ./lib/horizontal_scroll.rb
30
+ - ./lib/common/random_text.rb
31
+ - ./lib/bash/builder.rb
32
+ - ./lib/bash/console.rb
33
+ - ./lib/bash/font.rb
34
+ homepage: https://github.com/AlmazKo/BashConsole
35
+ licenses:
36
+ - MIT
37
+ post_install_message:
38
+ rdoc_options: []
39
+
40
+ require_paths:
41
+ - lib
42
+ required_ruby_version: !ruby/object:Gem::Requirement
43
+ none: false
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: "0"
48
+ required_rubygems_version: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ">="
52
+ - !ruby/object:Gem::Version
53
+ version: "0"
54
+ requirements: []
55
+
56
+ rubyforge_project:
57
+ rubygems_version: 1.8.11
58
+ signing_key:
59
+ specification_version: 3
60
+ summary: Bash visualization tools.
61
+ test_files: []
62
+