vedeu 0.1.18 → 0.1.19

Sign up to get free protection for your applications and to get access to all the features.
Files changed (100) hide show
  1. checksums.yaml +4 -4
  2. data/.yardopts +5 -0
  3. data/Dockerfile +40 -0
  4. data/README.md +7 -30
  5. data/docs/api.md +79 -0
  6. data/docs/events.md +121 -0
  7. data/lib/vedeu.rb +61 -18
  8. data/lib/vedeu/api/api.rb +73 -53
  9. data/lib/vedeu/api/composition.rb +4 -1
  10. data/lib/vedeu/api/defined.rb +35 -0
  11. data/lib/vedeu/api/helpers.rb +20 -15
  12. data/lib/vedeu/api/interface.rb +17 -12
  13. data/lib/vedeu/api/line.rb +20 -12
  14. data/lib/vedeu/api/stream.rb +3 -0
  15. data/lib/vedeu/application.rb +34 -1
  16. data/lib/vedeu/configuration.rb +15 -3
  17. data/lib/vedeu/input/input.rb +77 -0
  18. data/lib/vedeu/launcher.rb +7 -0
  19. data/lib/vedeu/models/attributes/background.rb +15 -2
  20. data/lib/vedeu/models/attributes/coercions.rb +18 -3
  21. data/lib/vedeu/models/attributes/colour_translator.rb +23 -17
  22. data/lib/vedeu/models/attributes/foreground.rb +10 -2
  23. data/lib/vedeu/models/attributes/presentation.rb +62 -0
  24. data/lib/vedeu/models/colour.rb +7 -3
  25. data/lib/vedeu/models/composition.rb +17 -19
  26. data/lib/vedeu/models/geometry.rb +13 -5
  27. data/lib/vedeu/models/interface.rb +35 -19
  28. data/lib/vedeu/models/line.rb +24 -8
  29. data/lib/vedeu/models/stream.rb +13 -7
  30. data/lib/vedeu/models/style.rb +17 -7
  31. data/lib/vedeu/{support → output}/clear.rb +14 -0
  32. data/lib/vedeu/output/compositor.rb +77 -0
  33. data/lib/vedeu/output/refresh.rb +129 -0
  34. data/lib/vedeu/{support → output}/render.rb +49 -13
  35. data/lib/vedeu/{support → output}/view.rb +15 -8
  36. data/lib/vedeu/repositories/buffers.rb +181 -0
  37. data/lib/vedeu/{support → repositories}/events.rb +16 -6
  38. data/lib/vedeu/repositories/focus.rb +109 -0
  39. data/lib/vedeu/repositories/groups.rb +76 -0
  40. data/lib/vedeu/repositories/interfaces.rb +74 -0
  41. data/lib/vedeu/support/common.rb +20 -0
  42. data/lib/vedeu/support/cursor.rb +77 -0
  43. data/lib/vedeu/support/esc.rb +181 -46
  44. data/lib/vedeu/support/event.rb +22 -4
  45. data/lib/vedeu/support/grid.rb +10 -3
  46. data/lib/vedeu/support/log.rb +14 -1
  47. data/lib/vedeu/support/menu.rb +51 -12
  48. data/lib/vedeu/support/position.rb +9 -0
  49. data/lib/vedeu/support/terminal.rb +49 -15
  50. data/lib/vedeu/support/trace.rb +11 -4
  51. data/test/integration/defining_interfaces_test.rb +27 -0
  52. data/test/integration/views/basic_view_test.rb +767 -0
  53. data/test/lib/vedeu/api/api_test.rb +32 -37
  54. data/test/lib/vedeu/api/composition_test.rb +23 -61
  55. data/test/lib/vedeu/api/defined_test.rb +49 -0
  56. data/test/lib/vedeu/api/helpers_test.rb +91 -0
  57. data/test/lib/vedeu/api/interface_test.rb +136 -688
  58. data/test/lib/vedeu/api/line_test.rb +28 -32
  59. data/test/lib/vedeu/application_test.rb +6 -0
  60. data/test/lib/vedeu/configuration_test.rb +8 -4
  61. data/test/lib/vedeu/{support → input}/input_test.rb +9 -0
  62. data/test/lib/vedeu/launcher_test.rb +6 -0
  63. data/test/lib/vedeu/models/attributes/{coercer_test.rb → coercions_test.rb} +11 -10
  64. data/test/lib/vedeu/models/attributes/colour_translator_test.rb +13 -0
  65. data/test/lib/vedeu/models/attributes/presentation_test.rb +30 -0
  66. data/test/lib/vedeu/models/colour_test.rb +8 -0
  67. data/test/lib/vedeu/models/composition_test.rb +208 -200
  68. data/test/lib/vedeu/models/geometry_test.rb +39 -0
  69. data/test/lib/vedeu/models/interface_test.rb +11 -1
  70. data/test/lib/vedeu/models/line_test.rb +8 -1
  71. data/test/lib/vedeu/models/stream_test.rb +35 -0
  72. data/test/lib/vedeu/models/style_test.rb +8 -0
  73. data/test/lib/vedeu/{support → output}/clear_test.rb +1 -1
  74. data/test/lib/vedeu/output/compositor_test.rb +64 -0
  75. data/test/lib/vedeu/output/refresh_test.rb +48 -0
  76. data/test/lib/vedeu/{support → output}/render_test.rb +36 -0
  77. data/test/lib/vedeu/{support → output}/view_test.rb +0 -0
  78. data/test/lib/vedeu/repositories/buffers_test.rb +48 -0
  79. data/test/lib/vedeu/{support → repositories}/events_test.rb +0 -0
  80. data/test/lib/vedeu/repositories/focus_test.rb +74 -0
  81. data/test/lib/vedeu/repositories/groups_test.rb +66 -0
  82. data/test/lib/vedeu/repositories/interfaces_test.rb +6 -0
  83. data/test/lib/vedeu/support/common_test.rb +6 -0
  84. data/test/lib/vedeu/support/cursor_test.rb +79 -0
  85. data/test/lib/vedeu/support/log_test.rb +6 -0
  86. data/test/lib/vedeu/support/terminal_test.rb +6 -28
  87. data/test/lib/vedeu/support/trace_test.rb +6 -0
  88. data/test/test_helper.rb +37 -0
  89. data/vedeu.gemspec +1 -1
  90. metadata +65 -33
  91. data/bin/log +0 -13
  92. data/lib/vedeu/support/buffer.rb +0 -69
  93. data/lib/vedeu/support/buffers.rb +0 -106
  94. data/lib/vedeu/support/focus.rb +0 -83
  95. data/lib/vedeu/support/groups.rb +0 -61
  96. data/lib/vedeu/support/input.rb +0 -67
  97. data/test/lib/vedeu/support/buffer_test.rb +0 -83
  98. data/test/lib/vedeu/support/buffers_test.rb +0 -15
  99. data/test/lib/vedeu/support/focus_test.rb +0 -114
  100. data/test/lib/vedeu/support/groups_test.rb +0 -65
@@ -2,6 +2,31 @@ require 'test_helper'
2
2
 
3
3
  module Vedeu
4
4
  describe Geometry do
5
+ describe '#initialize' do
6
+ it 'returns an instance of itself' do
7
+ attributes = {}
8
+ Geometry.new(attributes).must_be_instance_of(Geometry)
9
+ end
10
+ end
11
+
12
+ describe '#y' do
13
+ it 'returns the value of y when it is a proc' do
14
+ IO.console.stub(:winsize, [25, 80]) do
15
+ geometry = Geometry.new({ y: proc { 17 } })
16
+ geometry.y.must_equal(17)
17
+ end
18
+ end
19
+ end
20
+
21
+ describe '#x' do
22
+ it 'returns the value of x when it is a proc' do
23
+ IO.console.stub(:winsize, [25, 80]) do
24
+ geometry = Geometry.new({ x: proc { 58 } })
25
+ geometry.x.must_equal(58)
26
+ end
27
+ end
28
+ end
29
+
5
30
  describe '#viewport_width' do
6
31
  it 'returns the viewport width when the interface fits the terminal' do
7
32
  IO.console.stub(:winsize, [25, 80]) do
@@ -17,6 +42,13 @@ module Vedeu
17
42
  geometry.viewport_width.must_equal(55)
18
43
  end
19
44
  end
45
+
46
+ it 'returns an unusable viewport width when the terminal is tiny' do
47
+ IO.console.stub(:winsize, [25, -10]) do
48
+ geometry = Geometry.new({ width: 60, height: 1, x: 5, y: 1 })
49
+ geometry.viewport_width.must_equal(1)
50
+ end
51
+ end
20
52
  end
21
53
 
22
54
  describe '#viewport_height' do
@@ -34,6 +66,13 @@ module Vedeu
34
66
  geometry.viewport_height.must_equal(10)
35
67
  end
36
68
  end
69
+
70
+ it 'returns an unusable viewport height when the terminal is tiny' do
71
+ IO.console.stub(:winsize, [-10, 80]) do
72
+ geometry = Geometry.new({ width: 60, height: 20, x: 1, y: 5 })
73
+ geometry.viewport_height.must_equal(1)
74
+ end
75
+ end
37
76
  end
38
77
 
39
78
  describe '#origin' do
@@ -20,6 +20,15 @@ module Vedeu
20
20
  })
21
21
  }
22
22
 
23
+ describe '#initialize' do
24
+ it 'returns an instance of itself' do
25
+ attributes = {}
26
+
27
+ Interface.new(attributes).must_be_instance_of(Interface)
28
+ end
29
+ end
30
+
31
+
23
32
  describe '#attributes' do
24
33
  it 'returns the value' do
25
34
  interface.attributes.must_equal(
@@ -39,7 +48,8 @@ module Vedeu
39
48
  height: 15
40
49
  },
41
50
  cursor: true,
42
- delay: 0.0
51
+ delay: 0.0,
52
+ parent: nil
43
53
  }
44
54
  )
45
55
  end
@@ -10,10 +10,17 @@ module Vedeu
10
10
  background: '#000000'
11
11
  },
12
12
  streams: [],
13
- style: 'normal'
13
+ style: 'normal',
14
+ parent: nil,
14
15
  }
15
16
  }
16
17
 
18
+ describe '#initialize' do
19
+ it 'returns an instance of itself' do
20
+ Line.new(attributes).must_be_instance_of(Line)
21
+ end
22
+ end
23
+
17
24
  describe '#attributes' do
18
25
  it 'returns the attributes' do
19
26
  line.attributes.must_equal(attributes)
@@ -18,6 +18,13 @@ module Vedeu
18
18
  let(:align) { :left }
19
19
  let(:width) { 9 }
20
20
 
21
+ describe '#initialize' do
22
+ it 'returns an instance of itself' do
23
+ attributes = {}
24
+ Stream.new(attributes).must_be_instance_of(Stream)
25
+ end
26
+ end
27
+
21
28
  describe '#text' do
22
29
  it 'has a text attribute' do
23
30
  stream.text.must_equal('Some text')
@@ -37,6 +44,34 @@ module Vedeu
37
44
  end
38
45
 
39
46
  describe '#to_s' do
47
+ it 'reverts to the colours of the line after rendering itself' do
48
+ line = Line.new({
49
+ colour: {
50
+ foreground: '#00ff00',
51
+ background: '#000000'
52
+ },
53
+ style: 'normal'
54
+ })
55
+ stream = Stream.new({
56
+ colour: {
57
+ foreground: '#ff0000',
58
+ background: '#000000'
59
+ },
60
+ text: 'Some text',
61
+ style: 'underline',
62
+ width: nil,
63
+ align: :left,
64
+ parent: line.view_attributes,
65
+ })
66
+ stream.to_s.must_equal(
67
+ "\e[38;2;255;0;0m\e[48;2;0;0;0m" \
68
+ "\e[4m" \
69
+ "Some text" \
70
+ "\e[24m\e[22m\e[27m" \
71
+ "\e[38;2;0;255;0m\e[48;2;0;0;0m"
72
+ )
73
+ end
74
+
40
75
  describe 'when a width is set and align is default' do
41
76
  let(:width) { 20 }
42
77
 
@@ -2,6 +2,14 @@ require 'test_helper'
2
2
 
3
3
  module Vedeu
4
4
  describe Style do
5
+ describe '#initialize' do
6
+ it 'returns an instance of itself' do
7
+ values = ''
8
+
9
+ Style.new(values).must_be_instance_of(Style)
10
+ end
11
+ end
12
+
5
13
  describe '#to_s' do
6
14
  describe 'for a single style' do
7
15
  let(:values) { 'normal' }
@@ -2,7 +2,7 @@ require 'test_helper'
2
2
 
3
3
  module Vedeu
4
4
  describe Clear do
5
- before { Buffers.reset }
5
+ before { Interfaces.reset }
6
6
 
7
7
  describe '#initialize' do
8
8
  it 'returns an instance of itself' do
@@ -0,0 +1,64 @@
1
+ require 'test_helper'
2
+
3
+ module Vedeu
4
+ describe Compositor do
5
+ before { Terminal.console.stubs(:print) }
6
+
7
+ describe '.render' do
8
+ it 'raises an exception if the buffer/interface cannot be found' do
9
+ proc { Compositor.render('') }.must_raise(BufferNotFound)
10
+ end
11
+
12
+ context 'when the buffer is nil' do
13
+ it 'clears the defined area for the interface' do
14
+ Vedeu.interface('xenon') do
15
+ x 1
16
+ y 1
17
+ width 5
18
+ height 3
19
+ end
20
+
21
+ Compositor.render('xenon').must_equal([
22
+ "\e[1;1H \e[1;1H" \
23
+ "\e[2;1H \e[2;1H" \
24
+ "\e[3;1H \e[3;1H" \
25
+ "\e[?25h"
26
+ ])
27
+ end
28
+ end
29
+
30
+ context 'when the buffer is not nil' do
31
+ it 'renders the content in the defined area for the interface' do
32
+ Vedeu.interface('neon') do
33
+ x 1
34
+ y 1
35
+ width 5
36
+ height 3
37
+ end
38
+
39
+ class MyCompositorView < Vedeu::View
40
+ def render
41
+ view 'neon' do
42
+ line 'argon'
43
+ line 'boron'
44
+ line 'radon'
45
+ end
46
+ end
47
+ end
48
+
49
+ MyCompositorView.render
50
+
51
+ Compositor.render('neon').must_equal([
52
+ "\e[1;1H \e[1;1H" \
53
+ "\e[2;1H \e[2;1H" \
54
+ "\e[3;1H \e[3;1H" \
55
+ "\e[1;1Hargon" \
56
+ "\e[2;1Hboron" \
57
+ "\e[3;1Hradon" \
58
+ "\e[?25h"
59
+ ])
60
+ end
61
+ end
62
+ end
63
+ end
64
+ end
@@ -0,0 +1,48 @@
1
+ require 'test_helper'
2
+
3
+ module Vedeu
4
+ describe Refresh do
5
+ describe '.add_interface' do
6
+ it 'returns false when provided with no attributes' do
7
+ Refresh.add_interface({}).must_equal(false)
8
+ end
9
+ end
10
+
11
+ describe '.add_group' do
12
+ it 'returns false when provided with no attributes' do
13
+ Refresh.add_group({}).must_equal(false)
14
+ end
15
+ end
16
+
17
+ describe '.all' do
18
+ it 'returns an empty collection when there are no registered ' \
19
+ 'interfaces' do
20
+ Interfaces.reset
21
+
22
+ Refresh.all.must_equal([])
23
+ end
24
+ end
25
+
26
+ describe '.by_focus' do
27
+ it 'raises an exception when there are no registered interfaces' do
28
+ Focus.reset
29
+
30
+ proc { Refresh.by_focus }.must_raise(NoInterfacesDefined)
31
+ end
32
+ end
33
+
34
+ describe '.by_group' do
35
+ it 'raises an exception when the group cannot be found' do
36
+ Groups.reset
37
+
38
+ proc { Refresh.by_group('') }.must_raise(GroupNotFound)
39
+ end
40
+ end
41
+
42
+ describe '.by_name' do
43
+ it 'raises an exception when the buffer cannot be found' do
44
+ proc { Refresh.by_name('') }.must_raise(BufferNotFound)
45
+ end
46
+ end
47
+ end
48
+ end
@@ -95,6 +95,42 @@ module Vedeu
95
95
  "\e[3;1Hthis is the third, it is even lo\e[?25l"
96
96
  )
97
97
  end
98
+
99
+ it 'returns the content for the interface, starting at the optional ' \
100
+ 'top' do
101
+ interface = Interface.new({
102
+ name: '.call',
103
+ geometry: {
104
+ width: 32,
105
+ height: 4,
106
+ },
107
+ lines: [
108
+ {
109
+ streams: [{ text: 'this is the first' }]
110
+ }, {
111
+ streams: { text: 'this is the second and it is long' }
112
+ }, {
113
+ streams: [
114
+ { text: 'this is the third, ' },
115
+ { text: 'it is even longer ' },
116
+ { text: 'and still truncated' }
117
+ ]
118
+ }, {
119
+ streams: [{ text: 'this is exciting!' }]
120
+ }
121
+ ]
122
+ })
123
+ Render.call(interface, { top: 1 }).must_equal(
124
+ "\e[1;1H \e[1;1H" \
125
+ "\e[2;1H \e[2;1H" \
126
+ "\e[3;1H \e[3;1H" \
127
+ "\e[4;1H \e[4;1H" \
128
+ "\e[1;1Hthis is the second and it is lon" \
129
+ "\e[2;1Hthis is the third, it is even lo" \
130
+ "\e[3;1Hthis is exciting!\e[?25h"
131
+ )
132
+ end
133
+
98
134
  end
99
135
  end
100
136
  end
File without changes
@@ -0,0 +1,48 @@
1
+ require 'test_helper'
2
+
3
+ module Vedeu
4
+ describe Buffers do
5
+
6
+ describe '.create' do
7
+ end
8
+
9
+ describe '.add' do
10
+ end
11
+
12
+ describe '.find' do
13
+ context 'when the buffer does not exist by this name' do
14
+ end
15
+
16
+ context 'when the buffer can be found by name' do
17
+ end
18
+ end
19
+
20
+ describe '.latest' do
21
+ context 'when the buffer does not exist by this name' do
22
+ end
23
+
24
+ context 'when the buffer can be found by name' do
25
+ end
26
+ end
27
+
28
+ describe '.content' do
29
+ context 'when the buffer does not exist by this name' do
30
+ end
31
+
32
+ context 'when the buffer can be found by name' do
33
+ end
34
+ end
35
+
36
+ describe '.swap_buffers' do
37
+ context 'when the buffer does not exist by this name' do
38
+ end
39
+
40
+ context 'when the buffer can be found by name' do
41
+ end
42
+ end
43
+
44
+ describe '.reset' do
45
+ end
46
+
47
+ end
48
+ end
@@ -0,0 +1,74 @@
1
+ require 'test_helper'
2
+
3
+ module Vedeu
4
+ describe Focus do
5
+ before { Focus.reset }
6
+ after { Focus.reset }
7
+
8
+ describe '#add' do
9
+ it 'adds an interface to storage focussed' do
10
+ Focus.add({ name: 'thallium' }).must_equal(['thallium'])
11
+ end
12
+
13
+ it 'does not add it again if already exists' do
14
+ Focus.add({ name: 'thallium' })
15
+ Focus.add({ name: 'thallium' })
16
+ Focus.registered.must_equal(['thallium'])
17
+ end
18
+ end
19
+
20
+ describe '#by_name' do
21
+ it 'the named interface is focussed when the method is called' do
22
+ Focus.add({ name: 'thallium' })
23
+ Focus.add({ name: 'lead' })
24
+ Focus.add({ name: 'bismuth' })
25
+ Focus.by_name('lead').must_equal('lead')
26
+ end
27
+
28
+ it 'raises an exception if the interface does not exist' do
29
+ proc { Focus.by_name('not_found') }.must_raise(InterfaceNotFound)
30
+ end
31
+ end
32
+
33
+ describe '#current' do
34
+ it 'returns the name of the interface currently in focus' do
35
+ Focus.add({ name: 'thallium' })
36
+ Focus.add({ name: 'lead' })
37
+ Focus.add({ name: 'bismuth' })
38
+ Focus.current.must_equal('thallium')
39
+ end
40
+
41
+ it 'raises an exception if there are no interfaces defined' do
42
+ proc { Focus.current }.must_raise(NoInterfacesDefined)
43
+ end
44
+ end
45
+
46
+ describe '#next_item' do
47
+ it 'the next interface is focussed when the method is called' do
48
+ Focus.add({ name: 'thallium' })
49
+ Focus.add({ name: 'lead' })
50
+ Focus.add({ name: 'bismuth' })
51
+ Focus.next_item.must_equal('lead')
52
+ end
53
+ end
54
+
55
+ describe '#prev_item' do
56
+ it 'the previous interface is focussed when the method is called' do
57
+ Focus.add({ name: 'thallium' })
58
+ Focus.add({ name: 'lead' })
59
+ Focus.add({ name: 'bismuth' })
60
+ Focus.prev_item.must_equal('bismuth')
61
+ end
62
+ end
63
+
64
+ describe '#registered' do
65
+ it 'returns all the names of the interfaces which can be focussed' do
66
+ Focus.add({ name: 'thallium' })
67
+ Focus.add({ name: 'lead' })
68
+ Focus.add({ name: 'bismuth' })
69
+
70
+ Focus.registered.must_equal(['thallium', 'lead', 'bismuth'])
71
+ end
72
+ end
73
+ end
74
+ end