ansi 1.2.5 → 1.3.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.
- data/.ruby +34 -31
- data/HISTORY.rdoc +18 -0
- data/LICENSE/BSD-2-Clause.txt +25 -0
- data/LICENSE/GPL-2.0.txt +339 -0
- data/LICENSE/MIT.txt +21 -0
- data/LICENSE/RUBY.txt +60 -0
- data/NOTICE.rdoc +116 -4
- data/README.rdoc +6 -12
- data/lib/ansi.rb +6 -0
- data/lib/ansi.rbz +40 -0
- data/lib/ansi.yml +34 -31
- data/lib/ansi/bbcode.rb +3 -0
- data/lib/ansi/chart.rb +95 -0
- data/lib/ansi/code.rb +189 -260
- data/lib/ansi/constants.rb +18 -0
- data/lib/ansi/core.rb +24 -0
- data/lib/ansi/diff.rb +98 -61
- data/lib/ansi/string.rb +7 -8
- data/lib/ansi/terminal.rb +3 -3
- data/qed/01_ansicode.rdoc +0 -7
- data/qed/09_diff.rb +5 -5
- data/qed/10_core.rdoc +11 -0
- data/test/case_ansicode.rb +20 -10
- data/test/case_bbcode.rb +7 -8
- data/test/case_mixin.rb +14 -7
- data/test/case_progressbar.rb +2 -2
- metadata +26 -27
- data/LICENSE +0 -205
- data/Rakefile +0 -4
data/lib/ansi/code.rb
CHANGED
@@ -1,204 +1,130 @@
|
|
1
|
-
require 'Win32/Console/ANSI' if RUBY_PLATFORM =~ /win32/
|
2
|
-
|
3
1
|
module ANSI
|
4
2
|
|
5
|
-
|
6
|
-
|
3
|
+
require 'Win32/Console/ANSI' if RUBY_PLATFORM =~ /(win32|w32)/
|
4
|
+
|
5
|
+
require 'ansi/constants'
|
6
|
+
|
7
|
+
# Global variialbe can be used to prevent ANSI codes
|
8
|
+
# from being used in ANSI's methods that do so to string.
|
9
|
+
#
|
10
|
+
# NOTE: This has no effect of methods that return ANSI codes.
|
11
|
+
$ansi = true
|
7
12
|
|
8
|
-
#
|
13
|
+
# ANSI Codes
|
9
14
|
#
|
10
15
|
# Ansi::Code module makes it very easy to use ANSI codes.
|
11
16
|
# These are esspecially nice for beautifying shell output.
|
12
17
|
#
|
13
|
-
#
|
14
|
-
#
|
15
|
-
# red + "Hello" + blue + "World"
|
18
|
+
# Ansi::Code.red + "Hello" + Ansi::Code.blue + "World"
|
16
19
|
# => "\e[31mHello\e[34mWorld"
|
17
20
|
#
|
18
|
-
# red
|
21
|
+
# Ansi::Code.red{ "Hello" } + Ansi::Code.blue{ "World" }
|
19
22
|
# => "\e[31mHello\e[0m\e[34mWorld\e[0m"
|
20
23
|
#
|
21
|
-
#
|
22
|
-
#
|
23
|
-
# The following is a list of supported display codes.
|
24
|
-
#
|
25
|
-
# save
|
26
|
-
# restore
|
27
|
-
# clear_screen
|
28
|
-
# cls # synonym for :clear_screen
|
29
|
-
# clear_line
|
30
|
-
# clr # synonym for :clear_line
|
31
|
-
# move
|
32
|
-
# up
|
33
|
-
# down
|
34
|
-
# left
|
35
|
-
# right
|
36
|
-
#
|
37
|
-
# The following is a list of supported "style" codes.
|
38
|
-
#
|
39
|
-
# clear
|
40
|
-
# reset # synonym for :clear
|
41
|
-
# bold
|
42
|
-
# dark
|
43
|
-
# italic # not widely implemented
|
44
|
-
# underline
|
45
|
-
# underscore # synonym for :underline
|
46
|
-
# blink
|
47
|
-
# rapid_blink # not widely implemented
|
48
|
-
# negative # no reverse because of String#reverse
|
49
|
-
# concealed
|
50
|
-
# strikethrough # not widely implemented
|
51
|
-
#
|
52
|
-
# The following is a list of supported color codes.
|
53
|
-
#
|
54
|
-
# black
|
55
|
-
# red
|
56
|
-
# green
|
57
|
-
# yellow
|
58
|
-
# blue
|
59
|
-
# magenta
|
60
|
-
# cyan
|
61
|
-
# white
|
62
|
-
#
|
63
|
-
# on_black
|
64
|
-
# on_red
|
65
|
-
# on_green
|
66
|
-
# on_yellow
|
67
|
-
# on_blue
|
68
|
-
# on_magenta
|
69
|
-
# on_cyan
|
70
|
-
# on_white
|
24
|
+
# IMPORTANT! Do not mixin Ansi::Code, instead use {ANSI::Mixin}.
|
71
25
|
#
|
72
|
-
#
|
73
|
-
#
|
74
|
-
# == Acknowledgement
|
75
|
-
#
|
76
|
-
# This library is a partial adaptation of ANSIColor by Florian Frank.
|
77
|
-
#
|
78
|
-
# ANSIColor Copyright (c) 2002 Florian Frank
|
79
|
-
#
|
80
|
-
# == Developer's Notes
|
81
|
-
#
|
82
|
-
# TODO: Any ANSI codes left to add? Modes?
|
26
|
+
# See {ANSI::Code::CHART} for list of all supported codes.
|
83
27
|
#
|
28
|
+
#--
|
84
29
|
# TODO: up, down, right, left, etc could have yielding methods too?
|
30
|
+
#++
|
85
31
|
|
86
32
|
module Code
|
87
33
|
extend self
|
88
34
|
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
UNDERLINE = "\e[4m"
|
95
|
-
UNDERSCORE = "\e[4m"
|
96
|
-
BLINK = "\e[5m"
|
97
|
-
RAPID = "\e[6m" # not widely implemented
|
98
|
-
REVERSE = "\e[7m"
|
99
|
-
NEGATIVE = "\e[7m" # alternate to reverse because of String#reverse
|
100
|
-
CONCEALED = "\e[8m"
|
101
|
-
STRIKE = "\e[9m" # not widely implemented
|
102
|
-
|
103
|
-
BLACK = "\e[30m"
|
104
|
-
RED = "\e[31m"
|
105
|
-
GREEN = "\e[32m"
|
106
|
-
YELLOW = "\e[33m"
|
107
|
-
BLUE = "\e[34m"
|
108
|
-
MAGENTA = "\e[35m"
|
109
|
-
CYAN = "\e[36m"
|
110
|
-
WHITE = "\e[37m"
|
111
|
-
|
112
|
-
ON_BLACK = "\e[40m"
|
113
|
-
ON_RED = "\e[41m"
|
114
|
-
ON_GREEN = "\e[42m"
|
115
|
-
ON_YELLOW = "\e[43m"
|
116
|
-
ON_BLUE = "\e[44m"
|
117
|
-
ON_MAGENTA = "\e[45m"
|
118
|
-
ON_CYAN = "\e[46m"
|
119
|
-
ON_WHITE = "\e[47m"
|
120
|
-
|
121
|
-
# Save current cursor positon.
|
122
|
-
SAVE = "\e[s"
|
123
|
-
|
124
|
-
# Restore saved cursor positon.
|
125
|
-
RESTORE = "\e[u"
|
126
|
-
|
127
|
-
# Clear to the end of the current line.
|
128
|
-
CLEAR_LINE = "\e[K"
|
129
|
-
|
130
|
-
# Clear to the end of the current line.
|
131
|
-
CLR = "\e[K"
|
132
|
-
|
133
|
-
# Clear the screen and move cursor to home.
|
134
|
-
CLEAR_SCREEN = "\e[2J"
|
135
|
-
|
136
|
-
# Clear the screen and move cursor to home.
|
137
|
-
CLS = "\e[2J"
|
35
|
+
# include ANSI Constants
|
36
|
+
include Constants
|
37
|
+
|
38
|
+
# Regexp for matching most ANSI codes.
|
39
|
+
PATTERN = /\e\[(\d+)m/
|
138
40
|
|
41
|
+
# ANSI clear code.
|
42
|
+
ENDCODE = "\e[0m"
|
43
|
+
|
44
|
+
# List of primary styles.
|
139
45
|
def self.styles
|
140
46
|
%w{bold dark italic underline underscore blink rapid reverse negative concealed strike}
|
141
47
|
end
|
142
48
|
|
49
|
+
# List of primary colors.
|
50
|
+
def self.colors
|
51
|
+
%w{black red green yellow blue magenta cyan white}
|
52
|
+
end
|
53
|
+
|
54
|
+
=begin
|
143
55
|
styles.each do |style|
|
144
56
|
module_eval <<-END, __FILE__, __LINE__
|
145
57
|
def #{style}(string=nil)
|
146
58
|
if string
|
59
|
+
return string unless $ansi
|
147
60
|
#warn "use ANSI block notation for future versions"
|
148
|
-
return "\#{#{style.upcase}}\#{string}\#{
|
61
|
+
return "\#{#{style.upcase}}\#{string}\#{ENDCODE}"
|
149
62
|
end
|
150
63
|
if block_given?
|
151
|
-
return
|
64
|
+
return yield unless $ansi
|
65
|
+
return "\#{#{style.upcase}}\#{yield}\#{ENDCODE}"
|
152
66
|
end
|
153
67
|
#{style.upcase}
|
154
68
|
end
|
155
69
|
END
|
156
70
|
end
|
71
|
+
=end
|
157
72
|
|
158
|
-
|
159
|
-
%w{black red green yellow blue magenta cyan white}
|
160
|
-
end
|
161
|
-
|
73
|
+
=begin
|
162
74
|
# Dynamically create color methods.
|
163
75
|
|
164
76
|
colors.each do |color|
|
165
77
|
module_eval <<-END, __FILE__, __LINE__
|
166
78
|
def #{color}(string=nil)
|
167
79
|
if string
|
80
|
+
return string unless $ansi
|
168
81
|
#warn "use ANSI block notation for future versions"
|
169
|
-
return "\#{#{color.upcase}}\#{string}\#{
|
82
|
+
return "\#{#{color.upcase}}\#{string}\#{ENDCODE}"
|
170
83
|
end
|
171
84
|
if block_given?
|
172
|
-
return
|
85
|
+
return yield unless $ansi
|
86
|
+
return "\#{#{color.upcase}}\#{yield}\#{ENDCODE}"
|
173
87
|
end
|
174
88
|
#{color.upcase}
|
175
89
|
end
|
176
90
|
|
177
91
|
def on_#{color}(string=nil)
|
178
92
|
if string
|
93
|
+
return string unless $ansi
|
179
94
|
#warn "use ANSI block notation for future versions"
|
180
|
-
return "\#{ON_#{color.upcase}}\#{string}\#{
|
95
|
+
return "\#{ON_#{color.upcase}}\#{string}\#{ENDCODE}"
|
181
96
|
end
|
182
97
|
if block_given?
|
183
|
-
return
|
98
|
+
return yield unless $ansi
|
99
|
+
return "\#{ON_#{color.upcase}}\#{yield}\#{ENDCODE}"
|
184
100
|
end
|
185
101
|
ON_#{color.upcase}
|
186
102
|
end
|
187
103
|
END
|
188
104
|
end
|
105
|
+
=end
|
189
106
|
|
190
|
-
#
|
107
|
+
# Return ANSI code given a list of symbolic names.
|
108
|
+
def [](*codes)
|
109
|
+
code(*codes)
|
110
|
+
end
|
191
111
|
|
112
|
+
# Dynamically create color on color methods.
|
113
|
+
#
|
114
|
+
# @deprecated
|
115
|
+
#
|
192
116
|
colors.each do |color|
|
193
117
|
colors.each do |on_color|
|
194
118
|
module_eval <<-END, __FILE__, __LINE__
|
195
119
|
def #{color}_on_#{on_color}(string=nil)
|
196
120
|
if string
|
121
|
+
return string unless $ansi
|
197
122
|
#warn "use ANSI block notation for future versions"
|
198
|
-
return #{color.upcase} + ON_#{color.upcase} + string +
|
123
|
+
return #{color.upcase} + ON_#{color.upcase} + string + ENDCODE
|
199
124
|
end
|
200
125
|
if block_given?
|
201
|
-
|
126
|
+
return yield unless $ansi
|
127
|
+
#{color.upcase} + ON_#{on_color.upcase} + yield.to_s + ENDCODE
|
202
128
|
else
|
203
129
|
#{color.upcase} + ON_#{on_color.upcase}
|
204
130
|
end
|
@@ -207,45 +133,35 @@ module ANSI
|
|
207
133
|
end
|
208
134
|
end
|
209
135
|
|
210
|
-
#
|
211
|
-
def
|
212
|
-
|
213
|
-
end
|
214
|
-
|
215
|
-
# Reset code.
|
216
|
-
def reset
|
217
|
-
RESET
|
218
|
-
end
|
219
|
-
|
220
|
-
# Save current cursor positon.
|
221
|
-
def save
|
222
|
-
SAVE
|
223
|
-
end
|
136
|
+
# Use method missing to dispatch ANSI code methods.
|
137
|
+
def method_missing(code, *args, &blk)
|
138
|
+
esc = nil
|
224
139
|
|
225
|
-
|
226
|
-
|
227
|
-
|
228
|
-
|
229
|
-
|
230
|
-
# Clear to the end of the current line.
|
231
|
-
def clear_line
|
232
|
-
CLEAR_LINE
|
233
|
-
end
|
234
|
-
|
235
|
-
# Clear to the end of the current line.
|
236
|
-
def clr
|
237
|
-
CLR
|
238
|
-
end
|
140
|
+
if CHART.key?(code)
|
141
|
+
esc = "\e[#{CHART[code]}m"
|
142
|
+
elsif SPECIAL_CHART.key?(code)
|
143
|
+
esc = SPECIAL_CHART[code]
|
144
|
+
end
|
239
145
|
|
240
|
-
|
241
|
-
|
242
|
-
|
146
|
+
if esc
|
147
|
+
if string = args.first
|
148
|
+
return string unless $ansi
|
149
|
+
#warn "use ANSI block notation for future versions"
|
150
|
+
return "#{esc}#{string}#{ENDCODE}"
|
151
|
+
end
|
152
|
+
if block_given?
|
153
|
+
return yield unless $ansi
|
154
|
+
return "#{esc}#{yield}#{ENDCODE}"
|
155
|
+
end
|
156
|
+
esc
|
157
|
+
else
|
158
|
+
super(code, *args, &blk)
|
159
|
+
end
|
243
160
|
end
|
244
161
|
|
245
|
-
#
|
246
|
-
|
247
|
-
|
248
|
-
end
|
162
|
+
# TODO: How to deal with position codes when $ansi is false?
|
163
|
+
# Should we reaise an error or just not push the codes?
|
164
|
+
# For now, we will leave this it as is.
|
249
165
|
|
250
166
|
# Like +move+ but returns to original positon after
|
251
167
|
# yielding the block.
|
@@ -292,127 +208,140 @@ module ANSI
|
|
292
208
|
# "\e[#;#R"
|
293
209
|
#end
|
294
210
|
|
295
|
-
# Apply
|
211
|
+
# Apply ANSI codes to a first argument or block value.
|
296
212
|
#
|
297
|
-
#
|
213
|
+
# @example
|
214
|
+
# ansi("Valentine", :red, :on_white)
|
298
215
|
#
|
299
|
-
|
300
|
-
|
301
|
-
codes.each do |code|
|
302
|
-
s << "\e[#{TABLE[code]}m"
|
303
|
-
end
|
304
|
-
s << yield.to_s
|
305
|
-
s << CLEAR
|
306
|
-
end
|
307
|
-
|
308
|
-
# Alternate term for #style.
|
309
|
-
alias_method :color, :style
|
310
|
-
|
216
|
+
# @example
|
217
|
+
# ansi(:red, :on_white){ "Valentine" }
|
311
218
|
#
|
312
|
-
|
219
|
+
# @return [String]
|
220
|
+
# String wrapped ANSI code.
|
221
|
+
#
|
222
|
+
def ansi(*codes) #:yield:
|
313
223
|
if block_given?
|
314
|
-
yield.
|
224
|
+
string = yield.to_s
|
315
225
|
else
|
316
|
-
|
226
|
+
string = codes.shift.to_s
|
317
227
|
end
|
228
|
+
|
229
|
+
return string unless $ansi
|
230
|
+
|
231
|
+
code(*codes) + string + ENDCODE
|
318
232
|
end
|
319
233
|
|
234
|
+
# Remove ANSI codes from string or block value.
|
320
235
|
#
|
321
|
-
|
322
|
-
|
323
|
-
#
|
324
|
-
|
325
|
-
|
236
|
+
# @param [String]
|
237
|
+
# String from which to remove ANSI codes.
|
238
|
+
#
|
239
|
+
# @return [String]
|
240
|
+
# String wrapped ANSI code.
|
241
|
+
#
|
242
|
+
#--
|
243
|
+
# TODO: Allow selective removal using *codes argument?
|
244
|
+
#++
|
245
|
+
def unansi(string=nil) #:yield:
|
326
246
|
if block_given?
|
327
|
-
yield.
|
328
|
-
elsif string
|
329
|
-
string.gsub(PATTERN, '')
|
247
|
+
string = yield.to_s
|
330
248
|
else
|
331
|
-
|
249
|
+
string = string.to_s
|
332
250
|
end
|
251
|
+
string.gsub(PATTERN, '')
|
333
252
|
end
|
334
253
|
|
335
|
-
#
|
336
|
-
# rather than a block. The primary purpose of this method
|
337
|
-
# is to speed up the String#ansi call.
|
254
|
+
# Alias for #ansi method.
|
338
255
|
#
|
339
|
-
#
|
256
|
+
# @deprecated
|
257
|
+
# Here for backward scompatibility.
|
258
|
+
alias_method :style, :ansi
|
259
|
+
|
260
|
+
# Alias for #unansi method.
|
261
|
+
#
|
262
|
+
# @deprecated
|
263
|
+
# Here for backwards compatibility.
|
264
|
+
alias_method :unstyle, :unansi
|
265
|
+
|
266
|
+
# Alternate term for #ansi.
|
267
|
+
#
|
268
|
+
# @deprecated
|
269
|
+
# May change in future definition.
|
270
|
+
alias_method :color, :ansi
|
271
|
+
|
272
|
+
# Alias for unansi.
|
340
273
|
#
|
341
|
-
|
342
|
-
|
274
|
+
# @deprecated
|
275
|
+
# May change in future definition.
|
276
|
+
alias_method :uncolor, :unansi
|
277
|
+
|
278
|
+
# Look-up code from chart, or if Integer simply pass through.
|
279
|
+
# Also resolves :random and :on_random.
|
280
|
+
#
|
281
|
+
# @param codes [Array<Symbol,Integer]
|
282
|
+
# Symbols or integers to covnert to ANSI code.
|
283
|
+
#
|
284
|
+
# @return [String] ANSI code
|
285
|
+
def code(*codes)
|
286
|
+
list = []
|
343
287
|
codes.each do |code|
|
344
|
-
|
288
|
+
list << \
|
289
|
+
case code
|
290
|
+
when Integer
|
291
|
+
code
|
292
|
+
when Array
|
293
|
+
rgb(*code)
|
294
|
+
when :random
|
295
|
+
random
|
296
|
+
when :on_random
|
297
|
+
random(true)
|
298
|
+
else
|
299
|
+
CHART[code.to_sym]
|
300
|
+
end
|
345
301
|
end
|
346
|
-
|
347
|
-
s << CLEAR
|
302
|
+
"\e[" + (list * ";") + "m"
|
348
303
|
end
|
349
304
|
|
350
|
-
#
|
351
|
-
#
|
352
|
-
|
353
|
-
|
305
|
+
# Provides a random primary ANSI color.
|
306
|
+
#
|
307
|
+
# @param background [Boolean]
|
308
|
+
# Use `true` for background color, otherwise foreground color.
|
309
|
+
#
|
310
|
+
# @return [Integer] ANSI color number
|
311
|
+
def random(background=false)
|
312
|
+
(background ? 40 : 30) + rand(8)
|
354
313
|
end
|
355
314
|
|
356
|
-
#
|
357
|
-
|
358
|
-
|
359
|
-
#
|
360
|
-
|
361
|
-
|
362
|
-
:
|
363
|
-
|
364
|
-
:dark => 2,
|
365
|
-
:italic => 3,
|
366
|
-
:underline => 4,
|
367
|
-
:underscore => 4,
|
368
|
-
:blink => 5,
|
369
|
-
:rapid => 6,
|
370
|
-
:reverse => 7,
|
371
|
-
:negative => 7,
|
372
|
-
:concealed => 8,
|
373
|
-
:strike => 9,
|
374
|
-
:black => 30,
|
375
|
-
:red => 31,
|
376
|
-
:green => 32,
|
377
|
-
:yellow => 33,
|
378
|
-
:blue => 34,
|
379
|
-
:magenta => 35,
|
380
|
-
:cyan => 36,
|
381
|
-
:white => 37,
|
382
|
-
:on_black => 40,
|
383
|
-
:on_red => 41,
|
384
|
-
:on_green => 42,
|
385
|
-
:on_yellow => 43,
|
386
|
-
:on_blue => 44,
|
387
|
-
:on_magenta => 45,
|
388
|
-
:on_cyan => 46,
|
389
|
-
:on_white => 47
|
390
|
-
}
|
391
|
-
end
|
315
|
+
# Creates an xterm-256 color from rgb value.
|
316
|
+
#
|
317
|
+
# @param background [Boolean]
|
318
|
+
# Use `true` for background color, otherwise foreground color.
|
319
|
+
#
|
320
|
+
def rgb(red, green, blue, background=false)
|
321
|
+
"#{background ? 48 : 38};5;#{rgb_value(red, green, blue)}"
|
322
|
+
end
|
392
323
|
|
393
|
-
|
394
|
-
|
324
|
+
# Creates an xterm-256 color from a CSS-style color string.
|
325
|
+
def hex(string, background=false)
|
326
|
+
string.tr!('#','')
|
327
|
+
x = (string.size == 6 ? 2 : 1)
|
328
|
+
r, g, b = [0,1,2].map{ |i| string[i*x,2].to_i(16) }
|
329
|
+
rgb(r, g, b, background)
|
330
|
+
end
|
395
331
|
|
396
|
-
|
397
|
-
class String
|
398
|
-
#
|
399
|
-
def ansi(*codes)
|
400
|
-
ANSI::Code.ansi(self, *codes)
|
401
|
-
end
|
332
|
+
private
|
402
333
|
|
403
|
-
|
404
|
-
|
405
|
-
|
406
|
-
|
334
|
+
# Gets closest xterm-256 color.
|
335
|
+
def rgb_256(r, g, b)
|
336
|
+
r, g, b = [r, g, b].map{ |c| rgb_valid(c); (6 * (c.to_f / 256.0)).to_i }
|
337
|
+
v = (r * 36 + g * 6 + b + 16).abs
|
338
|
+
raise ArgumentError, "RGB value outside 0-255 range" if v > 255
|
339
|
+
v
|
340
|
+
end
|
407
341
|
|
408
|
-
#
|
409
|
-
def unansi
|
410
|
-
ANSI::Code.unansi(self)
|
411
342
|
end
|
412
343
|
|
413
344
|
#
|
414
|
-
|
415
|
-
replace(unansi)
|
416
|
-
end
|
345
|
+
extend Code
|
417
346
|
end
|
418
347
|
|