vedeu 0.1.12 → 0.1.13

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.
Files changed (38) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +7 -0
  3. data/lib/vedeu.rb +12 -12
  4. data/lib/vedeu/api/api.rb +23 -18
  5. data/lib/vedeu/api/events.rb +1 -1
  6. data/lib/vedeu/api/interface.rb +29 -19
  7. data/lib/vedeu/api/line.rb +1 -34
  8. data/lib/vedeu/api/stream.rb +1 -34
  9. data/lib/vedeu/models/attributes/attributes.rb +7 -7
  10. data/lib/vedeu/models/attributes/colour_translator.rb +45 -7
  11. data/lib/vedeu/models/colour.rb +4 -2
  12. data/lib/vedeu/models/composition.rb +9 -9
  13. data/lib/vedeu/models/interface.rb +1 -1
  14. data/lib/vedeu/models/line.rb +17 -3
  15. data/lib/vedeu/{api → models}/store.rb +0 -2
  16. data/lib/vedeu/models/stream.rb +17 -3
  17. data/lib/vedeu/output/buffers.rb +14 -8
  18. data/lib/vedeu/output/view.rb +7 -3
  19. data/lib/vedeu/support/esc.rb +1 -14
  20. data/lib/vedeu/support/position.rb +31 -0
  21. data/lib/vedeu/support/terminal.rb +4 -0
  22. data/test/lib/vedeu/api/api_test.rb +21 -0
  23. data/test/lib/vedeu/api/interface_test.rb +765 -51
  24. data/test/lib/vedeu/configuration_test.rb +5 -0
  25. data/test/lib/vedeu/models/composition_test.rb +1 -1
  26. data/test/lib/vedeu/models/interface_test.rb +59 -17
  27. data/test/lib/vedeu/{api → models}/store_test.rb +12 -3
  28. data/test/lib/vedeu/output/clear_test.rb +1 -1
  29. data/test/lib/vedeu/output/render_test.rb +1 -1
  30. data/test/lib/vedeu/output/view_test.rb +17 -0
  31. data/test/lib/vedeu/support/esc_test.rb +0 -10
  32. data/test/lib/vedeu/support/position_test.rb +19 -0
  33. data/test/support/colour_test.sh +100 -0
  34. data/test/{stats.sh → support/stats.sh} +0 -0
  35. data/vedeu.gemspec +1 -1
  36. metadata +16 -10
  37. data/lib/vedeu/api/view.rb +0 -45
  38. data/test/lib/vedeu/api/view_test.rb +0 -565
@@ -9,11 +9,13 @@ module Vedeu
9
9
  end
10
10
 
11
11
  def foreground
12
- @foreground ||= ColourTranslator.new(attributes[:foreground]).foreground
12
+ @foreground ||= ColourTranslator
13
+ .new(attributes[:foreground], { truecolor: false }).foreground
13
14
  end
14
15
 
15
16
  def background
16
- @background ||= ColourTranslator.new(attributes[:background]).background
17
+ @background ||= ColourTranslator
18
+ .new(attributes[:background], { truecolor: false }).background
17
19
  end
18
20
 
19
21
  def to_s
@@ -5,18 +5,22 @@ module Vedeu
5
5
  end
6
6
 
7
7
  def attributes
8
- defaults.merge!(@attributes)
8
+ @_attributes ||= defaults.merge!(@attributes)
9
9
  end
10
10
 
11
11
  def interfaces
12
- @interfaces ||= if _interfaces.nil? || _interfaces.empty?
12
+ @interfaces ||= if attributes[:interfaces].nil? || attributes[:interfaces].empty?
13
13
  []
14
14
 
15
15
  else
16
- [_interfaces].flatten.map do |new_attributes|
17
- stored_attributes = API::Store.query(new_attributes[:name])
16
+ [ attributes[:interfaces] ].flatten.map do |attrs|
17
+ stored = Store.query(attrs[:name])
18
18
 
19
- Interface.new(stored_attributes.merge!(new_attributes))
19
+ combined = stored.merge(attrs) do |key, s, a|
20
+ key == :lines && s.empty? ? a : s
21
+ end
22
+
23
+ Interface.new(combined)
20
24
  end
21
25
 
22
26
  end
@@ -28,10 +32,6 @@ module Vedeu
28
32
 
29
33
  private
30
34
 
31
- def _interfaces
32
- attributes[:interfaces]
33
- end
34
-
35
35
  def defaults
36
36
  {
37
37
  interfaces: []
@@ -11,7 +11,7 @@ module Vedeu
11
11
  end
12
12
 
13
13
  def attributes
14
- defaults.merge!(@attributes)
14
+ @_attributes ||= defaults.merge!(@attributes)
15
15
  end
16
16
 
17
17
  def name
@@ -1,11 +1,21 @@
1
1
  module Vedeu
2
2
  class Line
3
- def initialize(attributes = {})
3
+ def self.build(attributes = {}, &block)
4
+ new(attributes, &block).attributes
5
+ end
6
+
7
+ def initialize(attributes = {}, &block)
4
8
  @attributes = attributes
9
+
10
+ if block_given?
11
+ @self_before_instance_eval = eval('self', block.binding)
12
+
13
+ instance_eval(&block)
14
+ end
5
15
  end
6
16
 
7
17
  def attributes
8
- defaults.merge!(@attributes)
18
+ @_attributes ||= defaults.merge!(@attributes)
9
19
  end
10
20
 
11
21
  def colour
@@ -30,8 +40,12 @@ module Vedeu
30
40
  {
31
41
  colour: {},
32
42
  streams: [],
33
- style: ''
43
+ style: []
34
44
  }
35
45
  end
46
+
47
+ def method_missing(method, *args, &block)
48
+ @self_before_instance_eval.send(method, *args, &block)
49
+ end
36
50
  end
37
51
  end
@@ -1,7 +1,6 @@
1
1
  module Vedeu
2
2
  EntityNotFound = Class.new(StandardError)
3
3
 
4
- module API
5
4
  module Store
6
5
  extend self
7
6
 
@@ -23,5 +22,4 @@ module Vedeu
23
22
  @storage ||= {}
24
23
  end
25
24
  end
26
- end
27
25
  end
@@ -1,11 +1,21 @@
1
1
  module Vedeu
2
2
  class Stream
3
- def initialize(attributes = {})
3
+ def self.build(attributes = {}, &block)
4
+ new(attributes, &block).attributes
5
+ end
6
+
7
+ def initialize(attributes = {}, &block)
4
8
  @attributes = attributes
9
+
10
+ if block_given?
11
+ @self_before_instance_eval = eval('self', block.binding)
12
+
13
+ instance_eval(&block)
14
+ end
5
15
  end
6
16
 
7
17
  def attributes
8
- defaults.merge!(@attributes)
18
+ @_attributes ||= defaults.merge!(@attributes)
9
19
  end
10
20
 
11
21
  def colour
@@ -53,11 +63,15 @@ module Vedeu
53
63
  def defaults
54
64
  {
55
65
  colour: {},
56
- style: '',
66
+ style: [],
57
67
  text: '',
58
68
  width: nil,
59
69
  align: :left
60
70
  }
61
71
  end
72
+
73
+ def method_missing(method, *args, &block)
74
+ @self_before_instance_eval.send(method, *args, &block)
75
+ end
62
76
  end
63
77
  end
@@ -6,17 +6,17 @@ module Vedeu
6
6
 
7
7
  def create(interface)
8
8
  buffers[interface.name][:clear] = Clear.call(interface)
9
+ buffers[interface.name][:group] = interface.group
9
10
 
10
- Vedeu.events.event("_refresh_#{interface.name}_".to_sym, interface.delay) do
11
+ Vedeu.event("_refresh_#{interface.name}_".to_sym, interface.delay) do
11
12
  refresh(interface.name)
12
13
  end
13
14
 
14
- # TODO: cannot refresh group since no logic to fetch group from buffer
15
- # unless interface.group.nil? || interface.group.empty?
16
- # Vedeu.events.event("_refresh_#{interface.group}_".to_sym, interface.delay) do
17
- # refresh_group(interface.group)
18
- # end
19
- # end
15
+ unless interface.group.nil? || interface.group.empty?
16
+ Vedeu.event("_refresh_group_#{interface.group}_".to_sym, interface.delay) do
17
+ refresh_group(interface.group)
18
+ end
19
+ end
20
20
  end
21
21
 
22
22
  def enqueue(name, sequence)
@@ -29,6 +29,12 @@ module Vedeu
29
29
  end
30
30
  end
31
31
 
32
+ def refresh_group(group)
33
+ buffers.select.map do |name, buffer|
34
+ name if buffer[:group] == group
35
+ end.compact.map { |name| refresh(name) }
36
+ end
37
+
32
38
  def refresh(name)
33
39
  data = query(name)
34
40
 
@@ -57,7 +63,7 @@ module Vedeu
57
63
 
58
64
  def buffers
59
65
  @buffers ||= Hash.new do |hash, key|
60
- hash[key] = { current: '', next: [], clear: '' }
66
+ hash[key] = { current: '', next: [], clear: '', group: '' }
61
67
  end
62
68
  end
63
69
  end
@@ -13,7 +13,7 @@ module Vedeu
13
13
  end
14
14
 
15
15
  def render
16
- composition.interfaces.map do |interface|
16
+ interfaces.map do |interface|
17
17
  Buffers.enqueue(interface.name, interface.to_s)
18
18
  end
19
19
  end
@@ -26,11 +26,15 @@ module Vedeu
26
26
 
27
27
  attr_reader :object
28
28
 
29
+ def interfaces
30
+ composition.interfaces
31
+ end
32
+
29
33
  def composition
30
- @_composition ||= Composition.new(interfaces)
34
+ @_composition ||= Composition.new(attributes)
31
35
  end
32
36
 
33
- def interfaces
37
+ def attributes
34
38
  {
35
39
  interfaces: [ output ]
36
40
  }
@@ -3,20 +3,7 @@ module Vedeu
3
3
  extend self
4
4
 
5
5
  def set_position(y = 1, x = 1, &block)
6
- row = (y == 0 || y == nil) ? 1 : y
7
- column = (x == 0 || x == nil) ? 1 : x
8
-
9
- if block_given?
10
- out = []
11
- out << ["\e[", row, ';', column, 'H'].join
12
- out << yield
13
- out << ["\e[", row, ';', column, 'H'].join
14
- out
15
-
16
- else
17
- ["\e[", row, ';', column, 'H'].join
18
-
19
- end
6
+ Position.new(y, x).to_s(&block)
20
7
  end
21
8
 
22
9
  def string(value = '')
@@ -0,0 +1,31 @@
1
+ module Vedeu
2
+ class Position
3
+ def initialize(y = 1, x = 1)
4
+ @y, @x = y, x
5
+ end
6
+
7
+ def to_s(&block)
8
+ if block_given?
9
+ [ sequence, yield, sequence ].join
10
+
11
+ else
12
+ sequence
13
+
14
+ end
15
+ end
16
+
17
+ private
18
+
19
+ def sequence
20
+ ["\e[", y, ';', x, 'H'].join
21
+ end
22
+
23
+ def y
24
+ (@y == 0 || @y == nil) ? 1 : @y
25
+ end
26
+
27
+ def x
28
+ (@x == 0 || @x == nil) ? 1 : @x
29
+ end
30
+ end
31
+ end
@@ -45,6 +45,10 @@ module Vedeu
45
45
  yield
46
46
  end
47
47
 
48
+ def clear_screen
49
+ output Esc.string 'clear'
50
+ end
51
+
48
52
  def restore_screen
49
53
  output Esc.string 'screen_exit'
50
54
  output clear_last_line
@@ -0,0 +1,21 @@
1
+ require 'test_helper'
2
+
3
+ module Vedeu
4
+ describe API do
5
+ describe '.height' do
6
+ it 'returns the terminal height' do
7
+ IO.console.stub(:winsize, [24, 40]) do
8
+ Vedeu.height.must_equal(24)
9
+ end
10
+ end
11
+ end
12
+
13
+ describe '.width' do
14
+ it 'returns the terminal width' do
15
+ IO.console.stub(:winsize, [24, 40]) do
16
+ Vedeu.width.must_equal(40)
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
@@ -3,70 +3,784 @@ require 'test_helper'
3
3
  module Vedeu
4
4
  module API
5
5
  describe Interface do
6
- before { API::Store.reset }
6
+ describe '#define' do
7
+ before { Vedeu::Store.reset }
7
8
 
8
- interface = Interface.new('widget')
9
+ interface = Interface.new({ name: 'widget' })
9
10
 
10
- it 'creates and stores a new interface' do
11
- interface.create.must_be_instance_of(Vedeu::Interface)
12
- end
11
+ it 'creates and stores a new interface' do
12
+ interface.define.must_be_instance_of(Vedeu::Interface)
13
+ end
14
+
15
+ it 'allows interfaces to share behaviour' do
16
+ IO.console.stub :winsize, [10, 40] do
17
+ main = Vedeu.interface('main') do
18
+ colour foreground: '#ff0000', background: '#000000'
19
+ cursor false
20
+ centred true
21
+ width 10
22
+ height 2
23
+ group 'example_group'
24
+ delay 0.25
25
+ end
26
+ status = Vedeu.interface('status') do
27
+ colour foreground: 'aadd00', background: '#4040cc'
28
+ cursor true
29
+ centred true
30
+ width 10
31
+ height 1
32
+ y use('main').bottom
33
+ x use('main').left
34
+ group 'example_group'
35
+ delay 0.25
36
+ end
13
37
 
14
- it 'allows interfaces to share behaviour' do
15
- IO.console.stub :winsize, [10, 40] do
16
- main = Vedeu.interface('main') do
17
- colour foreground: '#ff0000', background: '#000000'
18
- cursor false
19
- centred true
20
- width 10
21
- height 2
22
- end
23
- status = Vedeu.interface('status') do
24
- colour foreground: 'aadd00', background: '#4040cc'
25
- cursor true
26
- centred true
27
- width 10
28
- height 1
29
- y use('main').bottom
30
- x use('main').left
31
- end
32
-
33
- main.left.must_equal(15)
34
- main.top.must_equal(4)
35
- status.left.must_equal(15)
36
- status.top.must_equal(5)
38
+ main.left.must_equal(15)
39
+ main.top.must_equal(4)
40
+ status.left.must_equal(15)
41
+ status.top.must_equal(5)
42
+ end
37
43
  end
38
- end
39
44
 
40
- it 'raises an exception when the value is out of bounds' do
41
- proc { interface.create { x 0 } }.must_raise(XOutOfBounds)
42
- end
45
+ it 'raises an exception when the value is out of bounds' do
46
+ proc { interface.define { x 0 } }.must_raise(XOutOfBounds)
47
+ end
43
48
 
44
- it 'raises an exception when the value is out of bounds' do
45
- proc { interface.create { x 999 } }.must_raise(XOutOfBounds)
46
- end
49
+ it 'raises an exception when the value is out of bounds' do
50
+ proc { interface.define { x 999 } }.must_raise(XOutOfBounds)
51
+ end
47
52
 
48
- it 'raises an exception when the value is out of bounds' do
49
- proc { interface.create { y 0 } }.must_raise(YOutOfBounds)
50
- end
53
+ it 'raises an exception when the value is out of bounds' do
54
+ proc { interface.define { y 0 } }.must_raise(YOutOfBounds)
55
+ end
51
56
 
52
- it 'raises an exception when the value is out of bounds' do
53
- proc { interface.create { y 999 } }.must_raise(YOutOfBounds)
54
- end
57
+ it 'raises an exception when the value is out of bounds' do
58
+ proc { interface.define { y 999 } }.must_raise(YOutOfBounds)
59
+ end
55
60
 
56
- it 'raises an exception when the value is out of bounds' do
57
- proc { interface.create { width 0 } }.must_raise(InvalidWidth)
58
- end
61
+ it 'raises an exception when the value is out of bounds' do
62
+ proc { interface.define { width 0 } }.must_raise(InvalidWidth)
63
+ end
59
64
 
60
- it 'raises an exception when the value is out of bounds' do
61
- proc { interface.create { width 999 } }.must_raise(InvalidWidth)
62
- end
65
+ it 'raises an exception when the value is out of bounds' do
66
+ proc { interface.define { width 999 } }.must_raise(InvalidWidth)
67
+ end
63
68
 
64
- it 'raises an exception when the value is out of bounds' do
65
- proc { interface.create { height 0 } }.must_raise(InvalidHeight)
69
+ it 'raises an exception when the value is out of bounds' do
70
+ proc { interface.define { height 0 } }.must_raise(InvalidHeight)
71
+ end
72
+
73
+ it 'raises an exception when the value is out of bounds' do
74
+ proc { interface.define { height 999 } }.must_raise(InvalidHeight)
75
+ end
66
76
  end
67
77
 
68
- it 'raises an exception when the value is out of bounds' do
69
- proc { interface.create { height 999 } }.must_raise(InvalidHeight)
78
+ describe '#build' do
79
+ before do
80
+ Vedeu::Store.reset
81
+ Vedeu.interface('testing_view') do
82
+ x 1
83
+ y 1
84
+ colour foreground: '#ffffff', background: '#000000'
85
+ centred false
86
+ end
87
+ end
88
+
89
+ it 'builds a basic view' do
90
+ Vedeu.view 'testing_view' do
91
+ line do
92
+ text '1. A line of text.'
93
+ text '2. Another line of text.'
94
+ end
95
+ end.must_equal(
96
+ {
97
+ name: 'testing_view',
98
+ group: '',
99
+ colour: {},
100
+ style: '',
101
+ geometry: {},
102
+ cursor: true,
103
+ delay: 0.0,
104
+ lines: [
105
+ {
106
+ colour: {},
107
+ style: [],
108
+ streams: [
109
+ {
110
+ text: '1. A line of text.',
111
+ }, {
112
+ text: '2. Another line of text.',
113
+ }
114
+ ]
115
+ }
116
+ ]
117
+ }
118
+ )
119
+ end
120
+
121
+ it 'handles coloured lines' do
122
+ Vedeu.view 'testing_view' do
123
+ line do
124
+ text '1. Line without colours.'
125
+ end
126
+ end.must_equal(
127
+ {
128
+ name: 'testing_view',
129
+ group: '',
130
+ colour: {},
131
+ style: '',
132
+ geometry: {},
133
+ cursor: true,
134
+ delay: 0.0,
135
+ lines: [
136
+ {
137
+ colour: {},
138
+ style: [],
139
+ streams: [{ text: '1. Line without colours.' }]
140
+ }
141
+ ]
142
+ }
143
+ )
144
+ end
145
+
146
+ it 'handles coloured lines' do
147
+ Vedeu.view 'testing_view' do
148
+ line do
149
+ colour background: '#ff0000', foreground: '#ffff00'
150
+ text '2. Line with colours.'
151
+ end
152
+ end.must_equal(
153
+ {
154
+ name: 'testing_view',
155
+ group: '',
156
+ colour: {},
157
+ style: '',
158
+ geometry: {},
159
+ cursor: true,
160
+ delay: 0.0,
161
+ lines: [
162
+ {
163
+ colour: { background: '#ff0000', foreground: '#ffff00' },
164
+ style: [],
165
+ streams: [{ text: '2. Line with colours.' }]
166
+ }
167
+ ]
168
+ }
169
+ )
170
+ end
171
+
172
+ it 'handles coloured lines' do
173
+ Vedeu.view 'testing_view' do
174
+ line do
175
+ colour foreground: '#a7ff00', background: '#005700'
176
+ text '3. Line with explicit colour declaration.'
177
+ end
178
+ end.must_equal(
179
+ {
180
+ name: 'testing_view',
181
+ group: '',
182
+ colour: {},
183
+ style: '',
184
+ geometry: {},
185
+ cursor: true,
186
+ delay: 0.0,
187
+ lines: [
188
+ {
189
+ colour: { background: '#005700', foreground: '#a7ff00' },
190
+ style: [],
191
+ streams: [{ text: '3. Line with explicit colour declaration.' }]
192
+ }
193
+ ]
194
+ }
195
+ )
196
+ end
197
+
198
+ it 'handles coloured lines' do
199
+ Vedeu.view 'testing_view' do
200
+ line do # actually uses streams
201
+ foreground '#ff00ff' do
202
+ text '4. Line with only foreground set.'
203
+ end
204
+ end
205
+ end.must_equal(
206
+ {
207
+ name: 'testing_view',
208
+ group: '',
209
+ colour: {},
210
+ style: '',
211
+ geometry: {},
212
+ cursor: true,
213
+ delay: 0.0,
214
+ lines: [
215
+ {
216
+ colour: {},
217
+ style: [],
218
+ streams: [{
219
+ colour: { foreground: '#ff00ff' },
220
+ style: [],
221
+ text: '4. Line with only foreground set.',
222
+ width: nil,
223
+ align: :left
224
+ }]
225
+ }
226
+ ]
227
+ }
228
+ )
229
+ end
230
+
231
+ it 'handles coloured lines' do
232
+ Vedeu.view 'testing_view' do
233
+ line do # actually uses streams
234
+ background '#00ff00' do
235
+ text '5. Line with only background set.'
236
+ end
237
+ end
238
+ end.must_equal(
239
+ {
240
+ name: 'testing_view',
241
+ group: '',
242
+ colour: {},
243
+ style: '',
244
+ geometry: {},
245
+ cursor: true,
246
+ delay: 0.0,
247
+ lines: [
248
+ {
249
+ colour: {},
250
+ style: [],
251
+ streams: [{
252
+ colour: { background: '#00ff00' },
253
+ style: [],
254
+ text: '5. Line with only background set.',
255
+ width: nil,
256
+ align: :left
257
+ }]
258
+ }
259
+ ]
260
+ }
261
+ )
262
+ end
263
+
264
+ it 'handles styles' do
265
+ Vedeu.view 'testing_view' do
266
+ line do
267
+ style 'normal'
268
+ text '1. Line with a normal style.'
269
+ end
270
+ end.must_equal(
271
+ {
272
+ name: 'testing_view',
273
+ group: '',
274
+ colour: {},
275
+ style: '',
276
+ geometry: {},
277
+ cursor: true,
278
+ delay: 0.0,
279
+ lines: [
280
+ {
281
+ colour: {},
282
+ style: ['normal'],
283
+ streams: [{
284
+ text: '1. Line with a normal style.'
285
+ }]
286
+ }
287
+ ]
288
+ }
289
+ )
290
+ end
291
+
292
+ it 'handles styles' do
293
+ Vedeu.view 'testing_view' do
294
+ line do
295
+ style 'underline'
296
+ text '2. Line with an underline style.'
297
+ end
298
+ end.must_equal(
299
+ {
300
+ name: 'testing_view',
301
+ group: '',
302
+ colour: {},
303
+ style: '',
304
+ geometry: {},
305
+ cursor: true,
306
+ delay: 0.0,
307
+ lines: [
308
+ {
309
+ colour: {},
310
+ style: ['underline'],
311
+ streams: [{
312
+ text: '2. Line with an underline style.'
313
+ }]
314
+ }
315
+ ]
316
+ }
317
+ )
318
+ end
319
+
320
+ it 'handles styles' do
321
+ Vedeu.view 'testing_view' do
322
+ line do # actually uses streams
323
+ style 'normal' do
324
+ text '3. Line with a normal style.'
325
+ end
326
+ end
327
+ end.must_equal(
328
+ {
329
+ name: 'testing_view',
330
+ group: '',
331
+ colour: {},
332
+ style: '',
333
+ geometry: {},
334
+ cursor: true,
335
+ delay: 0.0,
336
+ lines: [
337
+ {
338
+ colour: {},
339
+ style: [],
340
+ streams: [{
341
+ colour: {},
342
+ style: ['normal'],
343
+ text: '3. Line with a normal style.',
344
+ width: nil,
345
+ align: :left
346
+ }]
347
+ }
348
+ ]
349
+ }
350
+ )
351
+ end
352
+
353
+ it 'handles styles' do
354
+ Vedeu.view 'testing_view' do
355
+ line do # actually uses streams
356
+ style 'underline' do
357
+ text '4. Line with an underlined style.'
358
+ end
359
+ end
360
+ end.must_equal(
361
+ {
362
+ name: 'testing_view',
363
+ group: '',
364
+ colour: {},
365
+ style: '',
366
+ geometry: {},
367
+ cursor: true,
368
+ delay: 0.0,
369
+ lines: [
370
+ {
371
+ colour: {},
372
+ style: [],
373
+ streams: [{
374
+ colour: {},
375
+ style: ['underline'],
376
+ text: '4. Line with an underlined style.',
377
+ width: nil,
378
+ align: :left
379
+ }]
380
+ }
381
+ ]
382
+ }
383
+ )
384
+ end
385
+
386
+ it 'handles streams, which means sub-line colours and styles' do
387
+ Vedeu.view 'testing_view' do
388
+ line do
389
+ stream do
390
+ text 'A stream of text.'
391
+ end
392
+ end
393
+ end.must_equal(
394
+ {
395
+ name: 'testing_view',
396
+ group: '',
397
+ colour: {},
398
+ style: '',
399
+ geometry: {},
400
+ cursor: true,
401
+ delay: 0.0,
402
+ lines: [
403
+ {
404
+ colour: {},
405
+ style: [],
406
+ streams: [
407
+ {
408
+ colour: {},
409
+ style: [],
410
+ text: 'A stream of text.',
411
+ width: nil,
412
+ align: :left
413
+ }
414
+ ]
415
+ }
416
+ ]
417
+ }
418
+ )
419
+ end
420
+
421
+ it 'handles streams, which means sub-line colours and styles' do
422
+ Vedeu.view 'testing_view' do
423
+ line do
424
+ stream do # Stream is an 'explicit declaration'.
425
+ # We don't need it unless we want to add colours and styles.
426
+ # See below.
427
+ text '1. Two streams of text, these will be'
428
+ end
429
+
430
+ stream do
431
+ text ' on the same line- note the space.'
432
+ end
433
+ end
434
+ end.must_equal(
435
+ {
436
+ name: 'testing_view',
437
+ group: '',
438
+ colour: {},
439
+ style: '',
440
+ geometry: {},
441
+ cursor: true,
442
+ delay: 0.0,
443
+ lines: [
444
+ {
445
+ colour: {},
446
+ style: [],
447
+ streams: [
448
+ {
449
+ colour: {},
450
+ style: [],
451
+ text: '1. Two streams of text, these will be',
452
+ width: nil,
453
+ align: :left
454
+ }, {
455
+ colour: {},
456
+ style: [],
457
+ text: ' on the same line- note the space.',
458
+ width: nil,
459
+ align: :left
460
+ }
461
+ ]
462
+ }
463
+ ]
464
+ }
465
+ )
466
+ end
467
+
468
+ it 'handles streams, which means sub-line colours and styles' do
469
+ Vedeu.view 'testing_view' do
470
+ line do
471
+ stream do
472
+ text '2. Streams can have'
473
+ end
474
+
475
+ stream do
476
+ colour foreground: '#ff0000', background: '#00ff00'
477
+ text ' colours too.'
478
+ end
479
+ end
480
+ end.must_equal(
481
+ {
482
+ name: 'testing_view',
483
+ group: '',
484
+ colour: {},
485
+ style: '',
486
+ geometry: {},
487
+ cursor: true,
488
+ delay: 0.0,
489
+ lines: [
490
+ {
491
+ colour: {},
492
+ style: [],
493
+ streams: [
494
+ {
495
+ colour: {},
496
+ style: [],
497
+ text: '2. Streams can have',
498
+ width: nil,
499
+ align: :left
500
+ }, {
501
+ colour: {
502
+ foreground: '#ff0000',
503
+ background: '#00ff00'
504
+ },
505
+ style: [],
506
+ text: ' colours too.',
507
+ width: nil,
508
+ align: :left
509
+ }
510
+ ]
511
+ }
512
+ ]
513
+ }
514
+ )
515
+ end
516
+
517
+ it 'handles streams, which means sub-line colours and styles' do
518
+ Vedeu.view 'testing_view' do
519
+ line do
520
+ stream do
521
+ text '3. Streams can have'
522
+ end
523
+
524
+ stream do
525
+ style 'underline'
526
+ text ' styles too.'
527
+ end
528
+ end
529
+ end.must_equal(
530
+ {
531
+ name: 'testing_view',
532
+ group: '',
533
+ colour: {},
534
+ style: '',
535
+ geometry: {},
536
+ cursor: true,
537
+ delay: 0.0,
538
+ lines: [
539
+ {
540
+ colour: {},
541
+ style: [],
542
+ streams: [
543
+ {
544
+ colour: {},
545
+ style: [],
546
+ text: '3. Streams can have',
547
+ width: nil,
548
+ align: :left
549
+ }, {
550
+ colour: {},
551
+ style: ['underline'],
552
+ text: ' styles too.',
553
+ width: nil,
554
+ align: :left
555
+ }
556
+ ]
557
+ }
558
+ ]
559
+ }
560
+ )
561
+ end
562
+
563
+ it 'handles alignment' do
564
+ Vedeu.view 'testing_view' do
565
+ line do
566
+ stream do
567
+ width 80
568
+ text 'This is aligned left, and padded with spaces.'
569
+ end
570
+ end
571
+ end.must_equal(
572
+ {
573
+ name: 'testing_view',
574
+ group: '',
575
+ colour: {},
576
+ style: '',
577
+ geometry: {},
578
+ cursor: true,
579
+ delay: 0.0,
580
+ lines: [{
581
+ colour: {},
582
+ style: [],
583
+ streams: [{
584
+ align: :left,
585
+ colour: {},
586
+ style: [],
587
+ width: 80,
588
+ text: 'This is aligned left, and padded with spaces.'
589
+ }]
590
+ }]
591
+ }
592
+ )
593
+ end
594
+
595
+ it 'handles alignment' do
596
+ Vedeu.view 'testing_view' do
597
+ line do
598
+ stream do
599
+ width 80
600
+ align :left # explicit
601
+ text 'This is aligned left, and padded with spaces.'
602
+ end
603
+ end
604
+ end.must_equal(
605
+ {
606
+ name: 'testing_view',
607
+ group: '',
608
+ colour: {},
609
+ style: '',
610
+ geometry: {},
611
+ cursor: true,
612
+ delay: 0.0,
613
+ lines: [{
614
+ colour: {},
615
+ style: [],
616
+ streams: [{
617
+ colour: {},
618
+ style: [],
619
+ width: 80,
620
+ align: :left,
621
+ text: 'This is aligned left, and padded with spaces.'
622
+ }]
623
+ }]
624
+ }
625
+ )
626
+ end
627
+
628
+ it 'handles alignment' do
629
+ Vedeu.view 'testing_view' do
630
+ line do
631
+ stream do
632
+ width 80
633
+ align :centre
634
+ text 'This is aligned centrally, and padded with spaces.'
635
+ end
636
+ end
637
+ end.must_equal(
638
+ {
639
+ name: 'testing_view',
640
+ group: '',
641
+ colour: {},
642
+ style: '',
643
+ geometry: {},
644
+ cursor: true,
645
+ delay: 0.0,
646
+ lines: [{
647
+ colour: {},
648
+ style: [],
649
+ streams: [{
650
+ colour: {},
651
+ style: [],
652
+ width: 80,
653
+ align: :centre,
654
+ text: 'This is aligned centrally, and padded with spaces.'
655
+ }]
656
+ }]
657
+ }
658
+ )
659
+ end
660
+
661
+ it 'handles alignment' do
662
+ Vedeu.view 'testing_view' do
663
+ line do
664
+ stream do
665
+ width 80
666
+ align :right
667
+ text 'This is aligned right, and padded with spaces.'
668
+ end
669
+ end
670
+ end.must_equal(
671
+ {
672
+ name: 'testing_view',
673
+ group: '',
674
+ colour: {},
675
+ style: '',
676
+ geometry: {},
677
+ cursor: true,
678
+ delay: 0.0,
679
+ lines: [{
680
+ colour: {},
681
+ style: [],
682
+ streams: [{
683
+ colour: {},
684
+ style: [],
685
+ width: 80,
686
+ align: :right,
687
+ text: 'This is aligned right, and padded with spaces.'
688
+ }]
689
+ }]
690
+ }
691
+ )
692
+ end
693
+
694
+ it 'handles multiple colour and text statements correctly' do
695
+ Vedeu.view 'testing_view' do
696
+ line do
697
+ foreground('#ffff00') { text "\u{25B2}" }
698
+ text " Prev"
699
+
700
+ foreground('#ffff00') { text "\u{25BC}" }
701
+ text " Next"
702
+
703
+ foreground('#ffff00') { text "\u{21B2}" }
704
+ text " Select"
705
+
706
+ foreground('#ffff00') { text "\u{2395}" }
707
+ text " Pause"
708
+
709
+ foreground('#ffff00') { text "Q" }
710
+ text " Quit"
711
+ end
712
+ end.must_equal(
713
+ {
714
+ name: 'testing_view',
715
+ group: '',
716
+ colour: {},
717
+ style: '',
718
+ geometry: {},
719
+ cursor: true,
720
+ delay: 0.0,
721
+ lines: [
722
+ {
723
+ colour: {},
724
+ style: [],
725
+ streams: [
726
+ {
727
+ colour: {
728
+ foreground: "#ffff00"
729
+ },
730
+ style: [],
731
+ text: "▲",
732
+ width: nil,
733
+ align: :left
734
+ }, {
735
+ text: " Prev",
736
+ }, {
737
+ colour: {
738
+ foreground: "#ffff00"
739
+ },
740
+ style: [],
741
+ text: "▼",
742
+ width: nil,
743
+ align: :left
744
+ }, {
745
+ text: " Next",
746
+ }, {
747
+ colour: {
748
+ foreground: "#ffff00"
749
+ },
750
+ style: [],
751
+ text: "↲",
752
+ width: nil,
753
+ align: :left
754
+ }, {
755
+ text: " Select",
756
+ }, {
757
+ colour: {
758
+ foreground: "#ffff00"
759
+ },
760
+ style: [],
761
+ text: "⎕",
762
+ width: nil,
763
+ align: :left
764
+ }, {
765
+ text: " Pause",
766
+ }, {
767
+ colour: {
768
+ foreground: "#ffff00"
769
+ },
770
+ style: [],
771
+ text: "Q",
772
+ width: nil,
773
+ align: :left
774
+ }, {
775
+ text: " Quit",
776
+ }
777
+ ]
778
+ }
779
+ ]
780
+ }
781
+ )
782
+ end
783
+
70
784
  end
71
785
  end
72
786
  end