vedeu 0.2.1 → 0.2.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.yardopts +1 -0
- data/README.md +1 -2
- data/Rakefile +5 -5
- data/bin/vedeu +8 -4
- data/docs/api.md +3 -1
- data/docs/events.md +43 -29
- data/docs/getting_started.md +2 -0
- data/examples/cursor_app/cursor_app.rb +85 -0
- data/examples/lines_app/lines_app.rb +60 -0
- data/lib/vedeu.rb +9 -3
- data/lib/vedeu/api/api.rb +28 -7
- data/lib/vedeu/api/composition.rb +2 -0
- data/lib/vedeu/api/helpers.rb +2 -0
- data/lib/vedeu/api/interface.rb +2 -20
- data/lib/vedeu/api/keymap.rb +2 -0
- data/lib/vedeu/api/line.rb +2 -0
- data/lib/vedeu/api/menu.rb +3 -1
- data/lib/vedeu/api/stream.rb +25 -2
- data/lib/vedeu/application.rb +4 -4
- data/lib/vedeu/configuration/api.rb +327 -0
- data/lib/vedeu/configuration/cli.rb +110 -0
- data/lib/vedeu/{configuration.rb → configuration/configuration.rb} +49 -99
- data/lib/vedeu/launcher.rb +0 -1
- data/lib/vedeu/models/attributes/colour_translator.rb +2 -2
- data/lib/vedeu/models/colour.rb +0 -1
- data/lib/vedeu/models/composition.rb +2 -8
- data/lib/vedeu/models/cursor.rb +261 -0
- data/lib/vedeu/models/geometry.rb +11 -19
- data/lib/vedeu/models/interface.rb +2 -12
- data/lib/vedeu/models/keymap.rb +2 -0
- data/lib/vedeu/models/line.rb +2 -0
- data/lib/vedeu/models/stream.rb +2 -0
- data/lib/vedeu/models/style.rb +2 -0
- data/lib/vedeu/output/clear.rb +0 -1
- data/lib/vedeu/output/compositor.rb +0 -1
- data/lib/vedeu/output/refresh.rb +3 -0
- data/lib/vedeu/output/render.rb +12 -6
- data/lib/vedeu/output/view.rb +1 -0
- data/lib/vedeu/repositories/cursors.rb +98 -0
- data/lib/vedeu/repositories/events.rb +0 -1
- data/lib/vedeu/repositories/focus.rb +18 -0
- data/lib/vedeu/repositories/menus.rb +4 -4
- data/lib/vedeu/support/common.rb +2 -1
- data/lib/vedeu/support/event.rb +1 -10
- data/lib/vedeu/support/grid.rb +1 -2
- data/lib/vedeu/{repositories → support}/keymap_validator.rb +5 -4
- data/lib/vedeu/support/log.rb +3 -0
- data/lib/vedeu/support/menu.rb +4 -1
- data/lib/vedeu/support/registrar.rb +2 -1
- data/test/integration/defining_interfaces_test.rb +0 -1
- data/test/integration/views/basic_view_test.rb +741 -739
- data/test/lib/vedeu/api/api_test.rb +14 -3
- data/test/lib/vedeu/api/helpers_test.rb +3 -3
- data/test/lib/vedeu/api/interface_test.rb +17 -70
- data/test/lib/vedeu/api/keymap_test.rb +2 -0
- data/test/lib/vedeu/api/line_test.rb +4 -4
- data/test/lib/vedeu/api/menu_test.rb +6 -5
- data/test/lib/vedeu/api/stream_test.rb +18 -0
- data/test/lib/vedeu/configuration/api_test.rb +248 -0
- data/test/lib/vedeu/configuration/cli_test.rb +88 -0
- data/test/lib/vedeu/configuration/configuration_test.rb +67 -0
- data/test/lib/vedeu/input/input_test.rb +2 -2
- data/test/lib/vedeu/models/attributes/background_test.rb +3 -3
- data/test/lib/vedeu/models/attributes/foreground_test.rb +3 -3
- data/test/lib/vedeu/models/composition_test.rb +0 -222
- data/test/lib/vedeu/models/cursor_test.rb +164 -0
- data/test/lib/vedeu/models/interface_test.rb +0 -11
- data/test/lib/vedeu/output/compositor_test.rb +2 -4
- data/test/lib/vedeu/output/render_test.rb +4 -41
- data/test/lib/vedeu/repositories/cursors_test.rb +13 -0
- data/test/lib/vedeu/repositories/focus_test.rb +14 -4
- data/test/lib/vedeu/repositories/menus_test.rb +36 -29
- data/test/lib/vedeu/{repositories → support}/keymap_validator_test.rb +0 -0
- data/test/lib/vedeu/support/menu_test.rb +3 -3
- data/test/lib/vedeu/support/registrar_test.rb +6 -0
- data/test/lib/vedeu/support/terminal_test.rb +2 -2
- data/test/test_helper.rb +1 -1
- data/vedeu.gemspec +1 -1
- metadata +23 -14
- data/elements.txt +0 -118
- data/lib/vedeu/support/cursor.rb +0 -96
- data/test/lib/vedeu/configuration_test.rb +0 -154
- data/test/lib/vedeu/support/cursor_test.rb +0 -79
- data/test/support/model_test_data.json +0 -437
@@ -3,22 +3,13 @@ module Vedeu
|
|
3
3
|
# Calculates and provides interface geometry determined by both the client's
|
4
4
|
# requirements and the terminal's current viewing area.
|
5
5
|
#
|
6
|
-
#
|
6
|
+
# Geometry for Vedeu, as the same for ANSI terminals, has the origin at
|
7
|
+
# top-left, y = 1, x = 1. The 'y' coordinate is deliberately first.
|
7
8
|
#
|
8
9
|
# @api private
|
9
10
|
class Geometry
|
10
11
|
|
11
|
-
|
12
|
-
attr_reader :attributes
|
13
|
-
|
14
|
-
# @return [Boolean]
|
15
|
-
attr_reader :centred
|
16
|
-
|
17
|
-
# @return [Fixnum]
|
18
|
-
attr_reader :height
|
19
|
-
|
20
|
-
# @return [Fixnum]
|
21
|
-
attr_reader :width
|
12
|
+
attr_reader :attributes, :centred, :height, :width
|
22
13
|
|
23
14
|
# Returns a new instance of Geometry.
|
24
15
|
#
|
@@ -110,8 +101,8 @@ module Vedeu
|
|
110
101
|
Esc.set_position(virtual_y[index], left, &block)
|
111
102
|
end
|
112
103
|
|
113
|
-
# Returns
|
114
|
-
# centred or not.
|
104
|
+
# Returns the top coordinate of the interface, a fixed or dynamic value
|
105
|
+
# depending on whether the interface is centred or not.
|
115
106
|
#
|
116
107
|
# @return [Fixnum]
|
117
108
|
def top
|
@@ -139,8 +130,8 @@ module Vedeu
|
|
139
130
|
top - value
|
140
131
|
end
|
141
132
|
|
142
|
-
# Returns
|
143
|
-
# centred or not.
|
133
|
+
# Returns the left coordinate of the interface, a fixed or dynamic value
|
134
|
+
# depending on whether the interface is centred or not.
|
144
135
|
#
|
145
136
|
# @return [Fixnum]
|
146
137
|
def left
|
@@ -168,7 +159,8 @@ module Vedeu
|
|
168
159
|
left - value
|
169
160
|
end
|
170
161
|
|
171
|
-
# Returns
|
162
|
+
# Returns the bottom coordinate of the interface, a fixed or dynamic value
|
163
|
+
# depending on the value of {#top}.
|
172
164
|
#
|
173
165
|
# @return [Fixnum]
|
174
166
|
def bottom
|
@@ -190,8 +182,8 @@ module Vedeu
|
|
190
182
|
bottom + value
|
191
183
|
end
|
192
184
|
|
193
|
-
# Returns
|
194
|
-
#
|
185
|
+
# Returns the right coordinate of the interface, a fixed or dynamic value
|
186
|
+
# depending on the value of {#left}.
|
195
187
|
#
|
196
188
|
# @return [Fixnum]
|
197
189
|
def right
|
@@ -3,6 +3,8 @@ module Vedeu
|
|
3
3
|
# An Interface represents a portion of the terminal defined by
|
4
4
|
# {Vedeu::Geometry}. It is a container for {Vedeu::Line} and {Vedeu::Stream}
|
5
5
|
# objects.
|
6
|
+
#
|
7
|
+
# @api private
|
6
8
|
class Interface
|
7
9
|
|
8
10
|
include Coercions
|
@@ -79,17 +81,6 @@ module Vedeu
|
|
79
81
|
@geometry ||= Geometry.new(attributes[:geometry])
|
80
82
|
end
|
81
83
|
|
82
|
-
# @return [String]
|
83
|
-
def cursor
|
84
|
-
@cursor ||= if attributes[:cursor] == true
|
85
|
-
Esc.string('show_cursor')
|
86
|
-
|
87
|
-
else
|
88
|
-
Esc.string('hide_cursor')
|
89
|
-
|
90
|
-
end
|
91
|
-
end
|
92
|
-
|
93
84
|
private
|
94
85
|
|
95
86
|
# The default values for a new instance of Interface.
|
@@ -104,7 +95,6 @@ module Vedeu
|
|
104
95
|
colour: {},
|
105
96
|
style: '',
|
106
97
|
geometry: {},
|
107
|
-
cursor: true,
|
108
98
|
delay: 0.0,
|
109
99
|
parent: nil,
|
110
100
|
}
|
data/lib/vedeu/models/keymap.rb
CHANGED
data/lib/vedeu/models/line.rb
CHANGED
data/lib/vedeu/models/stream.rb
CHANGED
data/lib/vedeu/models/style.rb
CHANGED
data/lib/vedeu/output/clear.rb
CHANGED
data/lib/vedeu/output/refresh.rb
CHANGED
data/lib/vedeu/output/render.rb
CHANGED
@@ -39,13 +39,11 @@ module Vedeu
|
|
39
39
|
out << interface.origin(index)
|
40
40
|
out << line.to_s
|
41
41
|
end
|
42
|
-
out << interface.cursor
|
43
42
|
out.join
|
44
43
|
end
|
45
44
|
|
46
45
|
private
|
47
46
|
|
48
|
-
# @return [Interface]
|
49
47
|
attr_reader :interface
|
50
48
|
|
51
49
|
# The client application may have created a line that us too long for the
|
@@ -58,9 +56,9 @@ module Vedeu
|
|
58
56
|
# @api private
|
59
57
|
# @return [Array]
|
60
58
|
def processed_lines
|
61
|
-
return [] unless
|
59
|
+
return [] unless visible_lines.any? { |line| line.streams.any? }
|
62
60
|
|
63
|
-
|
61
|
+
visible_lines.map do |line|
|
64
62
|
if exceeds_width?(line)
|
65
63
|
line_length = 0
|
66
64
|
new_streams = []
|
@@ -142,14 +140,22 @@ module Vedeu
|
|
142
140
|
text.chomp.slice(0...value)
|
143
141
|
end
|
144
142
|
|
145
|
-
# Provides
|
143
|
+
# Provides the collection of visible lines associated with the interface.
|
146
144
|
# If the option `:top` was set, we will start at that line. Any lines
|
147
145
|
# outside of the height will not be rendered.
|
148
146
|
#
|
149
147
|
# @api private
|
150
148
|
# @return [Array]
|
149
|
+
def visible_lines
|
150
|
+
lines[top..height]
|
151
|
+
end
|
152
|
+
|
153
|
+
# Provides the collection of lines associated with the interface.
|
154
|
+
#
|
155
|
+
# @api private
|
156
|
+
# @return [Array]
|
151
157
|
def lines
|
152
|
-
interface.lines
|
158
|
+
interface.lines
|
153
159
|
end
|
154
160
|
|
155
161
|
# Provides the currently available height of the interface.
|
data/lib/vedeu/output/view.rb
CHANGED
@@ -0,0 +1,98 @@
|
|
1
|
+
module Vedeu
|
2
|
+
|
3
|
+
# Repository for storing, retrieving and manipulating the cursor position and
|
4
|
+
# visibility for an interface.
|
5
|
+
#
|
6
|
+
# @api private
|
7
|
+
module Cursors
|
8
|
+
|
9
|
+
include Common
|
10
|
+
extend self
|
11
|
+
|
12
|
+
# System events which when called will update the cursor position or
|
13
|
+
# visibility accordingly for the interface in focus.
|
14
|
+
Vedeu.event(:_cursor_up_) { Cursors.use(:move_up) }
|
15
|
+
Vedeu.event(:_cursor_right_) { Cursors.use(:move_right) }
|
16
|
+
Vedeu.event(:_cursor_down_) { Cursors.use(:move_down) }
|
17
|
+
Vedeu.event(:_cursor_left_) { Cursors.use(:move_left) }
|
18
|
+
Vedeu.event(:_cursor_hide_) { Cursors.use(:hide) }
|
19
|
+
Vedeu.event(:_cursor_show_) { Cursors.use(:show) }
|
20
|
+
Vedeu.event(:_cursor_refresh_) { Cursors.use(:refresh) }
|
21
|
+
|
22
|
+
# Adds an interface to the cursors repository.
|
23
|
+
#
|
24
|
+
# @param attributes [Hash]
|
25
|
+
# @return [Hash]
|
26
|
+
def add(attributes)
|
27
|
+
return false unless defined_value?(attributes[:name])
|
28
|
+
|
29
|
+
storage.store(attributes[:name], {
|
30
|
+
name: attributes[:name],
|
31
|
+
x: 1,
|
32
|
+
y: 1,
|
33
|
+
state: :show
|
34
|
+
})
|
35
|
+
end
|
36
|
+
|
37
|
+
# Find the cursor attributes by name.
|
38
|
+
#
|
39
|
+
# @param name [String]
|
40
|
+
# @return [Hash]
|
41
|
+
def find(name)
|
42
|
+
storage.fetch(name) do
|
43
|
+
fail CursorNotFound,
|
44
|
+
"Cursor was not found with this name: #{name.to_s}."
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
# Returns a boolean indicating whether the named interface is registered.
|
49
|
+
#
|
50
|
+
# @api private
|
51
|
+
# @return [Boolean]
|
52
|
+
def registered?(name)
|
53
|
+
return false if storage.empty?
|
54
|
+
|
55
|
+
storage.keys.include?(name)
|
56
|
+
end
|
57
|
+
|
58
|
+
# Perform an action (moving, showing or hiding) and save the new cursor
|
59
|
+
# state.
|
60
|
+
#
|
61
|
+
# @param action [Symbol] A symbol representing the method name to be called
|
62
|
+
# on the Cursor instance.
|
63
|
+
# @return [String] The escape sequence sent to the Terminal on completion
|
64
|
+
# of the action.
|
65
|
+
def use(action)
|
66
|
+
name = Focus.current
|
67
|
+
cursor = Cursor.new(find(name))
|
68
|
+
|
69
|
+
storage.store(name, cursor.send(action))
|
70
|
+
|
71
|
+
Terminal.output(cursor.to_s)
|
72
|
+
end
|
73
|
+
|
74
|
+
private
|
75
|
+
|
76
|
+
# Access to the storage for this repository.
|
77
|
+
#
|
78
|
+
# @api private
|
79
|
+
# @example
|
80
|
+
# { 'holmium' => { name: 'holmium', y: 12, x: 6, state: :show } }
|
81
|
+
#
|
82
|
+
# @return [Hash]
|
83
|
+
def storage
|
84
|
+
@_storage ||= in_memory
|
85
|
+
end
|
86
|
+
|
87
|
+
# Returns an empty collection ready for the storing of cursors by name with
|
88
|
+
# current attributes.
|
89
|
+
#
|
90
|
+
# @api private
|
91
|
+
# @return [Hash]
|
92
|
+
def in_memory
|
93
|
+
{}
|
94
|
+
end
|
95
|
+
|
96
|
+
end
|
97
|
+
|
98
|
+
end
|
@@ -9,6 +9,24 @@ module Vedeu
|
|
9
9
|
|
10
10
|
extend self
|
11
11
|
|
12
|
+
# System events which when called will change which interface is currently
|
13
|
+
# focussed. When the interface is brought into focus, its cursor position
|
14
|
+
# and visibility is restored.
|
15
|
+
Vedeu.event(:_focus_by_name_) do |name|
|
16
|
+
Vedeu::Focus.by_name(name)
|
17
|
+
Vedeu.trigger(:_cursor_refresh_)
|
18
|
+
end
|
19
|
+
|
20
|
+
Vedeu.event(:_focus_next_) do
|
21
|
+
Vedeu::Focus.next_item
|
22
|
+
Vedeu.trigger(:_cursor_refresh_)
|
23
|
+
end
|
24
|
+
|
25
|
+
Vedeu.event(:_focus_prev_) do
|
26
|
+
Vedeu::Focus.prev_item
|
27
|
+
Vedeu.trigger(:_cursor_refresh_)
|
28
|
+
end
|
29
|
+
|
12
30
|
# Add an interface name to the focus list unless it is already registered.
|
13
31
|
#
|
14
32
|
# @param attributes [String]
|
@@ -30,6 +30,8 @@ module Vedeu
|
|
30
30
|
|
31
31
|
Vedeu.log("Registering menu '#{attributes[:name]}'")
|
32
32
|
|
33
|
+
attributes.merge!({ items: Vedeu::Menu.new(attributes[:items]) })
|
34
|
+
|
33
35
|
storage.store(attributes[:name], attributes)
|
34
36
|
end
|
35
37
|
|
@@ -90,11 +92,9 @@ module Vedeu
|
|
90
92
|
# Access a menu by name.
|
91
93
|
#
|
92
94
|
# @param name [String]
|
93
|
-
# @return [Vedeu::Menu
|
95
|
+
# @return [Vedeu::Menu]
|
94
96
|
def use(name)
|
95
|
-
find(name).fetch(:items)
|
96
|
-
fail MenuNotFound, "This menu '#{name}' has no items."
|
97
|
-
end
|
97
|
+
find(name).fetch(:items)
|
98
98
|
end
|
99
99
|
|
100
100
|
private
|
data/lib/vedeu/support/common.rb
CHANGED
@@ -7,9 +7,10 @@ module Vedeu
|
|
7
7
|
|
8
8
|
# Returns a boolean indicating whether a variable has a useful value.
|
9
9
|
#
|
10
|
-
# @param variable [String|Symbol|Array] The variable to check.
|
10
|
+
# @param variable [String|Symbol|Array|Fixnum] The variable to check.
|
11
11
|
# @return [Boolean]
|
12
12
|
def defined_value?(variable)
|
13
|
+
return true if variable.is_a?(Fixnum)
|
13
14
|
return true unless variable.nil? || variable.empty?
|
14
15
|
|
15
16
|
false
|
data/lib/vedeu/support/event.rb
CHANGED
@@ -32,17 +32,8 @@ module Vedeu
|
|
32
32
|
|
33
33
|
private
|
34
34
|
|
35
|
-
# @return [Proc]
|
36
35
|
attr_reader :closure
|
37
|
-
|
38
|
-
# @return []
|
39
|
-
attr_accessor :deadline
|
40
|
-
|
41
|
-
# @return []
|
42
|
-
attr_accessor :executed_at
|
43
|
-
|
44
|
-
# @return []
|
45
|
-
attr_accessor :now
|
36
|
+
attr_accessor :deadline, :executed_at, :now
|
46
37
|
|
47
38
|
# Execute the code stored in the event closure.
|
48
39
|
#
|
data/lib/vedeu/support/grid.rb
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
# Monkey-patch Ruby's Fixnum to provide a columns method.
|
2
|
-
#
|
2
|
+
# @todo Don't monkey-patch because it is naughty.
|
3
3
|
class Fixnum
|
4
4
|
|
5
5
|
# Augment Fixnum to calculate column width in a grid-based layout.
|
@@ -47,7 +47,6 @@ module Vedeu
|
|
47
47
|
|
48
48
|
private
|
49
49
|
|
50
|
-
# @return [Fixnum]
|
51
50
|
attr_reader :value
|
52
51
|
|
53
52
|
# @api private
|
@@ -3,6 +3,7 @@ module Vedeu
|
|
3
3
|
# Validates that a given key is can be used and is not already in-use, either
|
4
4
|
# by the same interface, globally or as a system key.
|
5
5
|
#
|
6
|
+
# @api private
|
6
7
|
class KeymapValidator
|
7
8
|
|
8
9
|
include Common
|
@@ -31,17 +32,17 @@ module Vedeu
|
|
31
32
|
# @see KeymapValidator.check
|
32
33
|
def check
|
33
34
|
if system_key?(key)
|
34
|
-
[false,
|
35
|
+
[false, fail_message(key) + ' by the system.']
|
35
36
|
|
36
37
|
elsif global_key?(key)
|
37
|
-
[false,
|
38
|
+
[false, fail_message(key) + ' as a global key.']
|
38
39
|
|
39
40
|
elsif interface_key?(key, interface)
|
40
41
|
if defined_value?(interface)
|
41
|
-
[false,
|
42
|
+
[false, fail_message(key) + ' by this interface.']
|
42
43
|
|
43
44
|
else
|
44
|
-
[false,
|
45
|
+
[false, fail_message(key) + ' by another interface and therefore ' \
|
45
46
|
'cannot be global.']
|
46
47
|
|
47
48
|
end
|