coolline 0.3.0 → 0.4.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/lib/coolline.rb +2 -0
- data/lib/coolline/ansi.rb +98 -0
- data/lib/coolline/coolline.rb +66 -69
- data/lib/coolline/editor.rb +6 -0
- data/lib/coolline/menu.rb +107 -0
- data/lib/coolline/version.rb +1 -1
- data/repl.rb +1 -1
- data/test/editor_test.rb +49 -0
- metadata +16 -9
data/lib/coolline.rb
CHANGED
@@ -0,0 +1,98 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
class Coolline
|
4
|
+
# Mixin that allows to manipulate strings that contain ANSI color codes:
|
5
|
+
# getting their length, printing their n first characters, etc.
|
6
|
+
#
|
7
|
+
# Additionally, it can output certain commonly needed sequences — using the
|
8
|
+
# {#print} method to write to the output.
|
9
|
+
module ANSI
|
10
|
+
Code = %r{(\e\[\??\d+(?:[;\d]*)\w)}
|
11
|
+
|
12
|
+
# @return [Integer] Amount of characters within the string, disregarding
|
13
|
+
# color codes.
|
14
|
+
def ansi_length(string)
|
15
|
+
strip_ansi_codes(string).length
|
16
|
+
end
|
17
|
+
|
18
|
+
# @return [String] The initial string without ANSI codes.
|
19
|
+
def strip_ansi_codes(string)
|
20
|
+
string.gsub(Code, "")
|
21
|
+
end
|
22
|
+
|
23
|
+
# @return [Boolean] True if the beginning of the string is an ANSI code.
|
24
|
+
def start_with_ansi_code?(string)
|
25
|
+
(string =~ Code) == 0
|
26
|
+
end
|
27
|
+
|
28
|
+
# Prints a slice of a string containing ANSI color codes. This allows to
|
29
|
+
# print a string of a fixed width, while still keeping the right colors,
|
30
|
+
# etc.
|
31
|
+
#
|
32
|
+
# @param [String] string
|
33
|
+
# @param [Integer] start
|
34
|
+
# @param [Integer] stop Stop index, excluded from the range.
|
35
|
+
def ansi_print(string, start, stop)
|
36
|
+
i = 0
|
37
|
+
string.split(Code).each do |str|
|
38
|
+
if start_with_ansi_code? str
|
39
|
+
print str
|
40
|
+
else
|
41
|
+
if i >= start
|
42
|
+
print str[0..(stop - i - 1)]
|
43
|
+
elsif i < start && i + str.size >= start
|
44
|
+
print str[(start - i), stop - start - 1]
|
45
|
+
end
|
46
|
+
|
47
|
+
i += str.size
|
48
|
+
break if i >= stop
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
# Clears the current line and resets the select graphics settings.
|
54
|
+
def reset_line
|
55
|
+
print "\r\e[0m\e[0K"
|
56
|
+
end
|
57
|
+
|
58
|
+
# Clears the screen and moves the cursor to the top-left corner.
|
59
|
+
def clear_screen
|
60
|
+
print "\e[2J"
|
61
|
+
go_to(1, 1)
|
62
|
+
end
|
63
|
+
|
64
|
+
# Moves the cursor to (x, y), where x is the colmun and y the line
|
65
|
+
# number. Both are 1-indexed. The origin is the top-left corner.
|
66
|
+
#
|
67
|
+
# @param [Integer] x
|
68
|
+
# @param [Integer] y
|
69
|
+
def go_to(x, y)
|
70
|
+
print "\e[#{y};#{x}H"
|
71
|
+
end
|
72
|
+
|
73
|
+
# Moves the cursor to the given (1-indexed) column number.
|
74
|
+
def go_to_col(x)
|
75
|
+
print "\e[#{x}G"
|
76
|
+
end
|
77
|
+
|
78
|
+
# Resets the current ansi color codes.
|
79
|
+
def reset_color
|
80
|
+
print "\e[0m"
|
81
|
+
end
|
82
|
+
|
83
|
+
# Erases the current line.
|
84
|
+
def erase_line
|
85
|
+
print "\e[0K"
|
86
|
+
end
|
87
|
+
|
88
|
+
# Moves to the beginning of the next line.
|
89
|
+
def go_to_next_line
|
90
|
+
print "\e[E"
|
91
|
+
end
|
92
|
+
|
93
|
+
# Moves to the beginning of the previous line.
|
94
|
+
def go_to_previous_line
|
95
|
+
print "\e[F"
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
data/lib/coolline/coolline.rb
CHANGED
@@ -1,6 +1,8 @@
|
|
1
1
|
require 'io/console'
|
2
2
|
|
3
3
|
class Coolline
|
4
|
+
include ANSI
|
5
|
+
|
4
6
|
if config_home = ENV["XDG_CONFIG_HOME"] and !config_home.empty?
|
5
7
|
ConfigDir = File.join(config_home, "coolline")
|
6
8
|
else
|
@@ -22,8 +24,6 @@ class Coolline
|
|
22
24
|
"/dev/null"
|
23
25
|
end
|
24
26
|
|
25
|
-
AnsiCode = %r{(\e\[\??\d+(?:[;\d]*)\w)}
|
26
|
-
|
27
27
|
# @return [Hash] All the defaults settings
|
28
28
|
Settings = {
|
29
29
|
:word_boundaries => [" ", "-", "_"],
|
@@ -34,7 +34,7 @@ class Coolline
|
|
34
34
|
Handler.new(?\C-a, &:beginning_of_line),
|
35
35
|
Handler.new(?\C-e, &:end_of_line),
|
36
36
|
Handler.new(?\C-k, &:kill_line),
|
37
|
-
Handler.new(?\C-u, &:
|
37
|
+
Handler.new(?\C-u, &:kill_beginning_of_line),
|
38
38
|
Handler.new(?\C-f, &:forward_char),
|
39
39
|
Handler.new(?\C-b, &:backward_char),
|
40
40
|
Handler.new(?\C-d, &:kill_current_char_or_leave),
|
@@ -73,7 +73,7 @@ class Coolline
|
|
73
73
|
],
|
74
74
|
|
75
75
|
:unknown_char_proc => :insert_string.to_proc,
|
76
|
-
:transform_proc =>
|
76
|
+
:transform_proc => proc { |line| line },
|
77
77
|
:completion_proc => proc { |cool| [] },
|
78
78
|
|
79
79
|
:history_file => HistoryFile,
|
@@ -127,6 +127,8 @@ class Coolline
|
|
127
127
|
yield self if block_given?
|
128
128
|
|
129
129
|
@history ||= History.new(@history_file, @history_size)
|
130
|
+
|
131
|
+
@menu = Menu.new(@input, @output)
|
130
132
|
end
|
131
133
|
|
132
134
|
# @return [IO]
|
@@ -173,6 +175,9 @@ class Coolline
|
|
173
175
|
# @return [String] Current prompt
|
174
176
|
attr_accessor :prompt
|
175
177
|
|
178
|
+
# @return [Menu]
|
179
|
+
attr_accessor :menu
|
180
|
+
|
176
181
|
# Reads a line from the terminal
|
177
182
|
# @param [String] prompt Characters to print before each line
|
178
183
|
def readline(prompt = ">> ")
|
@@ -188,13 +193,15 @@ class Coolline
|
|
188
193
|
|
189
194
|
@should_exit = false
|
190
195
|
|
191
|
-
|
196
|
+
reset_line
|
192
197
|
print @prompt
|
193
198
|
|
194
199
|
@history.index = @history.size - 1
|
195
200
|
@history << @line
|
196
201
|
|
197
202
|
until (char = @input.getch) == "\r"
|
203
|
+
@menu.erase
|
204
|
+
|
198
205
|
handle(char)
|
199
206
|
return if @should_exit
|
200
207
|
|
@@ -202,49 +209,11 @@ class Coolline
|
|
202
209
|
@history_moved = false
|
203
210
|
end
|
204
211
|
|
205
|
-
|
206
|
-
prompt_size = strip_ansi_codes(@prompt).size
|
207
|
-
line = transform(@line)
|
208
|
-
|
209
|
-
stripped_line_width = strip_ansi_codes(line).size
|
210
|
-
line << " " * [width - stripped_line_width - prompt_size, 0].max
|
211
|
-
|
212
|
-
# reset the color, and kill the line
|
213
|
-
print "\r\e[0m\e[0K"
|
214
|
-
|
215
|
-
if strip_ansi_codes(@prompt + line).size <= width
|
216
|
-
print @prompt + line
|
217
|
-
print "\e[#{prompt_size + @pos + 1}G"
|
218
|
-
else
|
219
|
-
print @prompt
|
220
|
-
|
221
|
-
left_width = width - prompt_size
|
222
|
-
|
223
|
-
start_index = [@pos - left_width + 1, 0].max
|
224
|
-
end_index = start_index + left_width - 1
|
225
|
-
|
226
|
-
i = 0
|
227
|
-
line.split(AnsiCode).each do |str|
|
228
|
-
if start_with_ansi_code? str
|
229
|
-
# always print ansi codes to ensure the color is right
|
230
|
-
print str
|
231
|
-
else
|
232
|
-
if i >= start_index
|
233
|
-
print str[0..(end_index - i)]
|
234
|
-
elsif i < start_index && i + str.size >= start_index
|
235
|
-
print str[(start_index - i), left_width]
|
236
|
-
end
|
237
|
-
|
238
|
-
i += str.size
|
239
|
-
break if i >= end_index
|
240
|
-
end
|
241
|
-
end
|
242
|
-
if @pos < left_width + 1
|
243
|
-
print "\e[#{prompt_size + @pos + 1}G"
|
244
|
-
end
|
245
|
-
end
|
212
|
+
render
|
246
213
|
end
|
247
214
|
|
215
|
+
@menu.erase
|
216
|
+
|
248
217
|
print "\n"
|
249
218
|
|
250
219
|
@history[-1] = @line if @history.size != 0
|
@@ -252,7 +221,35 @@ class Coolline
|
|
252
221
|
|
253
222
|
@history.save_line
|
254
223
|
|
255
|
-
@line
|
224
|
+
@line
|
225
|
+
end
|
226
|
+
|
227
|
+
# Displays the current code on the terminal
|
228
|
+
def render
|
229
|
+
width = @input.winsize[1]
|
230
|
+
prompt_size = ansi_length(@prompt)
|
231
|
+
line = transform(@line)
|
232
|
+
|
233
|
+
stripped_line_width = ansi_length(line)
|
234
|
+
line += " " * [width - stripped_line_width - prompt_size, 0].max
|
235
|
+
|
236
|
+
reset_line
|
237
|
+
|
238
|
+
if ansi_length(@prompt + line) <= width
|
239
|
+
print @prompt + line
|
240
|
+
else
|
241
|
+
print @prompt
|
242
|
+
|
243
|
+
left_width = width - prompt_size
|
244
|
+
|
245
|
+
start_index = [@pos - left_width + 1, 0].max
|
246
|
+
end_index = start_index + left_width
|
247
|
+
|
248
|
+
ansi_print(line, start_index, end_index)
|
249
|
+
end
|
250
|
+
|
251
|
+
@menu.display
|
252
|
+
go_to_col [prompt_size + @pos + 1, width].min
|
256
253
|
end
|
257
254
|
|
258
255
|
# Reads a line with no prompt
|
@@ -367,40 +364,40 @@ class Coolline
|
|
367
364
|
line[word_beginning_before(pos)...pos]
|
368
365
|
end
|
369
366
|
|
370
|
-
#
|
371
|
-
def
|
372
|
-
|
373
|
-
|
374
|
-
|
375
|
-
|
367
|
+
# Sets the word at point, and moves the cursor to after the end of said word.
|
368
|
+
def completed_word=(string)
|
369
|
+
beg = word_beginning_before(pos)
|
370
|
+
line[beg...pos] = string
|
371
|
+
self.pos = beg + string.size
|
372
|
+
end
|
376
373
|
|
377
|
-
|
374
|
+
# @param [Array<String>] candidates
|
375
|
+
# @return [String] The common part between all completion candidates
|
376
|
+
def common_beginning(candidates)
|
377
|
+
candidates.inject do |common, el|
|
378
378
|
i = 0
|
379
379
|
i += 1 while common[i] == el[i]
|
380
380
|
|
381
381
|
el[0...i]
|
382
382
|
end
|
383
|
-
|
384
|
-
beg = word_beginning_before(pos)
|
385
|
-
line[beg...pos] = result
|
386
|
-
self.pos = beg + result.size
|
387
383
|
end
|
388
384
|
|
389
|
-
|
390
|
-
|
391
|
-
|
385
|
+
# Tries to complete the current word
|
386
|
+
def complete
|
387
|
+
return if word_boundary? line[pos - 1]
|
392
388
|
|
393
|
-
|
394
|
-
string.gsub(AnsiCode, "")
|
395
|
-
end
|
389
|
+
completions = @completion_proc.call(self)
|
396
390
|
|
397
|
-
|
398
|
-
|
391
|
+
if completions.empty?
|
392
|
+
menu.string = "(No completions found)"
|
393
|
+
else
|
394
|
+
menu.list = completions
|
395
|
+
self.completed_word = common_beginning(completions)
|
396
|
+
end
|
399
397
|
end
|
400
398
|
|
401
|
-
def
|
402
|
-
|
403
|
-
print "\e[0;0H" # goto 0, 0
|
399
|
+
def word_boundary?(char)
|
400
|
+
char =~ word_boundaries_regexp
|
404
401
|
end
|
405
402
|
|
406
403
|
private
|
data/lib/coolline/editor.rb
CHANGED
@@ -128,6 +128,12 @@ class Coolline
|
|
128
128
|
line[pos..-1] = ""
|
129
129
|
end
|
130
130
|
|
131
|
+
# Removes everything up to the current character
|
132
|
+
def kill_beginning_of_line
|
133
|
+
line[0...pos] = ""
|
134
|
+
self.pos = 0
|
135
|
+
end
|
136
|
+
|
131
137
|
# Removes all the characters in the line
|
132
138
|
def clear_line
|
133
139
|
line.clear
|
@@ -0,0 +1,107 @@
|
|
1
|
+
class Coolline
|
2
|
+
# A menu allows to display some information on a rectangle below the cursor.
|
3
|
+
#
|
4
|
+
# It displays a string or a list of strings until the user presses another
|
5
|
+
# key.
|
6
|
+
class Menu
|
7
|
+
include ANSI
|
8
|
+
|
9
|
+
def initialize(input, output)
|
10
|
+
@input = input
|
11
|
+
@output = output
|
12
|
+
|
13
|
+
@string = ""
|
14
|
+
|
15
|
+
@last_line_count = 0
|
16
|
+
end
|
17
|
+
|
18
|
+
# @return [String] Information to be displayed
|
19
|
+
attr_accessor :string
|
20
|
+
|
21
|
+
# Sets the menu's string to a list of items, formatted in columns.
|
22
|
+
#
|
23
|
+
# @param [Array<String>] items
|
24
|
+
def list=(items)
|
25
|
+
if items.empty?
|
26
|
+
self.string = ""
|
27
|
+
else
|
28
|
+
height, width = @input.winsize
|
29
|
+
|
30
|
+
col_width = items.map { |s| ansi_length(s) }.max
|
31
|
+
col_count = width / col_width
|
32
|
+
item_count = col_count * (height - 1)
|
33
|
+
|
34
|
+
self.string = format_columns(items[0, item_count], col_count, col_width)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
# Renders the menu below the current line.
|
39
|
+
#
|
40
|
+
# This will ensure not to draw to much, so that the line currently being
|
41
|
+
# edited will always stay visible.
|
42
|
+
#
|
43
|
+
# Once the menu is drawn, the cursor returns to the correct line.
|
44
|
+
def display
|
45
|
+
# An empty string shouldn't be treated like a 1-line string.
|
46
|
+
return if @string.empty?
|
47
|
+
|
48
|
+
height, width = @input.winsize
|
49
|
+
|
50
|
+
lines = @string.lines.to_a
|
51
|
+
|
52
|
+
lines[0, height - 1].each do |line|
|
53
|
+
print "\n\r"
|
54
|
+
ansi_print(line.chomp, 0, width)
|
55
|
+
end
|
56
|
+
reset_color
|
57
|
+
|
58
|
+
[lines.size, height].min.times { go_to_previous_line }
|
59
|
+
|
60
|
+
@last_line_count = [height - 1, lines.size].min
|
61
|
+
end
|
62
|
+
|
63
|
+
# Erases anything that had been written by the menu.
|
64
|
+
#
|
65
|
+
# This allows to hide the menu once it is no longer relevant.
|
66
|
+
#
|
67
|
+
# Notice it can only work by knowing how many lines the menu drew on the
|
68
|
+
# screen last time it was called, and assuming the terminal size didn't
|
69
|
+
# change.
|
70
|
+
def erase
|
71
|
+
return if @last_line_count.zero?
|
72
|
+
|
73
|
+
self.string = ""
|
74
|
+
|
75
|
+
@last_line_count.times do
|
76
|
+
go_to_next_line
|
77
|
+
erase_line
|
78
|
+
end
|
79
|
+
reset_color
|
80
|
+
|
81
|
+
@last_line_count.times { go_to_previous_line }
|
82
|
+
|
83
|
+
@last_line_count = 0
|
84
|
+
end
|
85
|
+
|
86
|
+
private
|
87
|
+
|
88
|
+
# @param [Array<String>] items Items to show
|
89
|
+
# @param [Integer] col_count Amount of columns to show
|
90
|
+
# @param [Integer] col_width Width of each column
|
91
|
+
#
|
92
|
+
# @return [String] Items formatted appropriately
|
93
|
+
def format_columns(items, col_count, col_width)
|
94
|
+
string = ""
|
95
|
+
|
96
|
+
items.each_slice(col_count) do |line|
|
97
|
+
string << line.map { |s| s.ljust(col_width - 1) } * " " << "\n"
|
98
|
+
end
|
99
|
+
|
100
|
+
string
|
101
|
+
end
|
102
|
+
|
103
|
+
def print(*objs)
|
104
|
+
@output.print(*objs)
|
105
|
+
end
|
106
|
+
end
|
107
|
+
end
|
data/lib/coolline/version.rb
CHANGED
data/repl.rb
CHANGED
data/test/editor_test.rb
CHANGED
@@ -63,6 +63,13 @@ context "editor of an empty line" do
|
|
63
63
|
asserts(:line).equals ""
|
64
64
|
end
|
65
65
|
|
66
|
+
context "after killing the beginning of the line" do
|
67
|
+
hookup { topic.kill_beginning_of_line }
|
68
|
+
|
69
|
+
asserts(:pos).equals 0
|
70
|
+
asserts(:line).equals ""
|
71
|
+
end
|
72
|
+
|
66
73
|
context "after transposing words" do
|
67
74
|
hookup { topic.transpose_words }
|
68
75
|
|
@@ -142,6 +149,13 @@ context "editor before many words" do
|
|
142
149
|
asserts(:line).equals ""
|
143
150
|
end
|
144
151
|
|
152
|
+
context "after killing the beginning of the line" do
|
153
|
+
hookup { topic.kill_beginning_of_line }
|
154
|
+
|
155
|
+
asserts(:pos).equals 0
|
156
|
+
asserts(:line).equals "a lovely dragon"
|
157
|
+
end
|
158
|
+
|
145
159
|
context "after transposing words" do
|
146
160
|
hookup { topic.transpose_words }
|
147
161
|
|
@@ -216,6 +230,13 @@ context "editor between two words" do
|
|
216
230
|
asserts(:line).equals "foo "
|
217
231
|
end
|
218
232
|
|
233
|
+
context "after killing the beginning of the line" do
|
234
|
+
hookup { topic.kill_beginning_of_line }
|
235
|
+
|
236
|
+
asserts(:pos).equals 0
|
237
|
+
asserts(:line).equals " bar"
|
238
|
+
end
|
239
|
+
|
219
240
|
context "after transposing words" do
|
220
241
|
hookup { topic.transpose_words }
|
221
242
|
|
@@ -318,6 +339,13 @@ context "editor between two out of three words" do
|
|
318
339
|
asserts(:line).equals "foo bar"
|
319
340
|
end
|
320
341
|
|
342
|
+
context "after killing the beginning of the line" do
|
343
|
+
hookup { topic.kill_beginning_of_line }
|
344
|
+
|
345
|
+
asserts(:pos).equals 0
|
346
|
+
asserts(:line).equals " baz"
|
347
|
+
end
|
348
|
+
|
321
349
|
context "after transposing words" do
|
322
350
|
hookup { topic.transpose_words }
|
323
351
|
|
@@ -425,6 +453,13 @@ context "editor at the end of a line" do
|
|
425
453
|
asserts(:line).equals "a lovely dragon"
|
426
454
|
end
|
427
455
|
|
456
|
+
context "after killing the beginning of the line" do
|
457
|
+
hookup { topic.kill_beginning_of_line }
|
458
|
+
|
459
|
+
asserts(:pos).equals 0
|
460
|
+
asserts(:line).equals ""
|
461
|
+
end
|
462
|
+
|
428
463
|
context "after transposing words" do
|
429
464
|
hookup { topic.transpose_words }
|
430
465
|
|
@@ -537,6 +572,13 @@ context "editor in the middle of a sentence" do
|
|
537
572
|
asserts(:line).equals "foo bar "
|
538
573
|
end
|
539
574
|
|
575
|
+
context "after killing the beginning of the line" do
|
576
|
+
hookup { topic.kill_beginning_of_line }
|
577
|
+
|
578
|
+
asserts(:pos).equals 0
|
579
|
+
asserts(:line).equals "baz qux"
|
580
|
+
end
|
581
|
+
|
540
582
|
context "after transposing words" do
|
541
583
|
hookup { topic.transpose_words }
|
542
584
|
|
@@ -649,6 +691,13 @@ context "editor in the middle of a word" do
|
|
649
691
|
asserts(:line).equals "foo bar b"
|
650
692
|
end
|
651
693
|
|
694
|
+
context "after killing the beginning of the line" do
|
695
|
+
hookup { topic.kill_beginning_of_line }
|
696
|
+
|
697
|
+
asserts(:pos).equals 0
|
698
|
+
asserts(:line).equals "az qux"
|
699
|
+
end
|
700
|
+
|
652
701
|
context "after transposing words" do
|
653
702
|
hookup { topic.transpose_words }
|
654
703
|
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: coolline
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.4.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,11 +9,11 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-
|
12
|
+
date: 2012-12-01 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: riot
|
16
|
-
requirement:
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ! '>='
|
@@ -21,7 +21,12 @@ dependencies:
|
|
21
21
|
version: '0'
|
22
22
|
type: :development
|
23
23
|
prerelease: false
|
24
|
-
version_requirements:
|
24
|
+
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
26
|
+
requirements:
|
27
|
+
- - ! '>='
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: '0'
|
25
30
|
description: ! 'A readline-like library that allows to change how the input
|
26
31
|
|
27
32
|
is displayed.
|
@@ -32,17 +37,19 @@ executables: []
|
|
32
37
|
extensions: []
|
33
38
|
extra_rdoc_files: []
|
34
39
|
files:
|
40
|
+
- lib/coolline/editor.rb
|
41
|
+
- lib/coolline/ansi.rb
|
42
|
+
- lib/coolline/version.rb
|
43
|
+
- lib/coolline/menu.rb
|
35
44
|
- lib/coolline/handler.rb
|
36
45
|
- lib/coolline/history.rb
|
37
|
-
- lib/coolline/editor.rb
|
38
46
|
- lib/coolline/coolline.rb
|
39
|
-
- lib/coolline/version.rb
|
40
47
|
- lib/coolline.rb
|
41
48
|
- test/helpers.rb
|
42
|
-
- test/editor_test.rb
|
43
49
|
- test/coolline_test.rb
|
44
|
-
- test/run_all.rb
|
45
50
|
- test/history_test.rb
|
51
|
+
- test/editor_test.rb
|
52
|
+
- test/run_all.rb
|
46
53
|
- repl.rb
|
47
54
|
- .gemtest
|
48
55
|
homepage: http://github.com/Mon-Ouie/coolline
|
@@ -65,7 +72,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
65
72
|
version: '0'
|
66
73
|
requirements: []
|
67
74
|
rubyforge_project:
|
68
|
-
rubygems_version: 1.8.
|
75
|
+
rubygems_version: 1.8.23
|
69
76
|
signing_key:
|
70
77
|
specification_version: 3
|
71
78
|
summary: Sounds like readline, smells like readline, but isn't readline
|