cyberarm_engine 0.18.0 → 0.19.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f24458d4ec27a35ff7877afa6e4acdc06d153b8cd161c53063a26282dc14802b
4
- data.tar.gz: baf54b9e08f2f78a75e6db02dfdc6e7ad749f73afb9dfad6260f666f75447fe8
3
+ metadata.gz: c8a871fd51f7fb568600a1668f93f37b2fdc3a077d8e6b7310ff297ff60690df
4
+ data.tar.gz: 80fb6e494d039fb78f03c656159d70f7388dd50673bf6171a27d7b63a973cdef
5
5
  SHA512:
6
- metadata.gz: 6296128b5384912865a96a0e80e176cdc92d853838874507c7eebe5ad86089062ea14fd5a12f0e848fa176047064f4ecf2f68aa1ddddfcc35830e01e688fa164
7
- data.tar.gz: '07386961b8796e2e4d73155c8e44c6c2df6906888609f8424a3cb94f947328356851dc6e72dc2cf26ba3952415c6696cca3c8524963359c6f2b5463c81d5cc18'
6
+ metadata.gz: 9a4f3bddd2d3a146fc6a71496eb0bb8d00c10ce7fddaadd2ab81fa4972471ca47d029b43d141a4c39fca3b2d6c75018b1f97e7925d3a943c88891b0e1e79a30a
7
+ data.tar.gz: 43bc7a87c50e0f56c9cecae84dbb1fc03c45ce3a2e30503b8074c42e0d981cabb1e1eb592a5e4e716d27aeb8ae5952421bd514332699f07a4bb8d894240a6e4b
@@ -43,14 +43,177 @@ module CyberarmEngine
43
43
  Gosu::Color.from_ahsv(alpha, hue, saturation, value)
44
44
  end
45
45
 
46
- # NOTE: Use this for future reference? https://github.com/danro/easing-js/blob/master/easing.js
46
+ # Tween functions based on those provided here: https://github.com/danro/easing-js/blob/master/easing.js
47
+ # Under MIT / BSD
47
48
 
48
49
  def tween_linear(t)
49
50
  t
50
51
  end
51
52
 
52
- def tween_ease_in_out(t)
53
+ def tween_ease_in_quad(t)
54
+ t ** 2
55
+ end
56
+
57
+ def tween_ease_out_quad(t)
58
+ -((t - 1) ** 2) -1
59
+ end
60
+
61
+ def tween_ease_in_out_quad(t)
62
+ return 0.5 * (t ** 2) if (t /= 0.5) < 1
63
+ return -0.5 * ((t -= 2) * t - 2)
64
+ end
65
+
66
+ def tween_ease_in_cubic(t)
67
+ t ** 3
68
+ end
69
+
70
+ def tween_ease_out_cubic(t)
71
+ ((t - 1) ** 3) + 1
72
+ end
73
+
74
+ def tween_ease_in_out_cubic(t)
75
+ return 0.5 * (t ** 3) if ((t /= 0.5) < 1)
76
+ return 0.5 * ((t - 2) ** 3) + 2
77
+ end
78
+
79
+ def tween_ease_in_quart(t)
80
+ t ** 4
81
+ end
82
+
83
+ def tween_ease_out_quart(t)
84
+ -((t - 1) ** 4) - 1
85
+ end
86
+
87
+ def tween_ease_in_out_quart(t)
88
+ return 0.5 * (t ** 4) if ((t /= 0.5) < 1)
89
+ return -0.5 * ((t -= 2) * (t ** 3) - 2)
90
+ end
91
+
92
+ def tween_ease_in_quint(t)
93
+ t ** 5
94
+ end
95
+
96
+ def tween_ease_out_quint(t)
97
+ ((t - 1) ** 5) + 1
98
+ end
99
+
100
+ def tween_ease_in_out_quint(t)
101
+ return 0.5 * (t ** 5) if ((t /= 0.5) < 1)
102
+ return 0.5 * ((t - 2) ** 5) + 2
103
+ end
104
+
105
+ def tween_ease_in(t) # sine
106
+ -Math.cos(t * (Math::PI / 2)) + 1
107
+ end
108
+
109
+ def tween_ease_out(t) # sine
110
+ Math.sin(t * (Math::PI / 2))
111
+ end
112
+
113
+ def tween_ease_in_out(t) # sine
53
114
  (-0.5 * (Math.cos(Math::PI * t) - 1))
54
115
  end
116
+
117
+ def tween_ease_in_expo(t)
118
+ (t == 0) ? 0 : 2 ** 10 * (t - 1)
119
+ end
120
+
121
+ def tween_ease_out_expo(t)
122
+ (t == 1) ? 1 : -(2 ** -10 * t) + 1
123
+ end
124
+
125
+ def tween_ease_in_out_expo(t)
126
+ return 0 if (t == 0)
127
+ return 1 if (t == 1)
128
+ return 0.5 * (2 ** 10 * (t - 1)) if ((t /= 0.5) < 1)
129
+ return 0.5 * (-(2 ** -10 * (t -= 1)) + 2)
130
+ end
131
+
132
+ def tween_ease_in_circ(t)
133
+ -(Math.sqrt(1 - (t * t)) - 1)
134
+ end
135
+
136
+ def tween_ease_out_circ(t)
137
+ Math.sqrt(1 - ((t - 1) ** 2))
138
+ end
139
+
140
+ def tween_ease_in_out_circ(t)
141
+ return -0.5 * (Math.sqrt(1 - t * t) - 1) if ((t /= 0.5) < 1)
142
+ return 0.5 * (Math.sqrt(1 - (t -= 2) * t) + 1)
143
+ end
144
+
145
+ def tween_ease_in_back(t)
146
+ s = 1.70158
147
+ t * t * ((s + 1) * t - s)
148
+ end
149
+
150
+ def tween_ease_out_back(t)
151
+ s = 1.70158
152
+ (t = t - 1) * t * ((s + 1) * t + s) + 1
153
+ end
154
+
155
+ def tween_ease_in_out_back(t)
156
+ s = 1.70158
157
+ return 0.5 * (t * t * (((s *= (1.525)) + 1) * t - s)) if ((t /= 0.5) < 1)
158
+ return 0.5 * ((t -= 2) * t * (((s *= (1.525)) + 1) * t + s) + 2)
159
+ end
160
+
161
+ def tween_elastic(t)
162
+ -1 * (4 ** (-8 * t)) * Math.sin((t * 6 - 1) * (2 * Math::PI) / 2) + 1
163
+ end
164
+
165
+ def tween_swing_from_to(t)
166
+ s = 1.70158
167
+ return 0.5 * (t * t * (((s *= (1.525)) + 1) * t - s)) if (t /= 0.5) < 1
168
+ return 0.5 * ((t -= 2) * t * (((s *= (1.525)) + 1) * t + s) + 2)
169
+ end
170
+
171
+ def tween_swing_from(t)
172
+ s = 1.70158;
173
+ t * t * ((s + 1) * t - s)
174
+ end
175
+
176
+ def tween_swing_to(t)
177
+ s = 1.70158
178
+ (t -= 1) * t * ((s + 1) * t + s) + 1
179
+ end
180
+
181
+ def tween_bounce(t)
182
+ if (t < (1 / 2.75))
183
+ (7.5625 * t * t)
184
+ elsif (t < (2 / 2.75))
185
+ (7.5625 * (t -= (1.5 / 2.75)) * t + 0.75)
186
+ elsif (t < (2.5 / 2.75))
187
+ (7.5625 * (t -= (2.25 / 2.75)) * t + 0.9375)
188
+ else
189
+ (7.5625 * (t -= (2.625 / 2.75)) * t + 0.984375)
190
+ end
191
+ end
192
+
193
+ def tween_bounce_past(t)
194
+ if (t < (1 / 2.75))
195
+ # missing "2 -"?
196
+ (7.5625 * t * t)
197
+ elsif (t < (2 / 2.75))
198
+ 2 - (7.5625 * (t -= (1.5 / 2.75)) * t + 0.75)
199
+ elsif (t < (2.5 / 2.75))
200
+ 2 - (7.5625 * (t -= (2.25 / 2.75)) * t + 0.9375)
201
+ else
202
+ 2 - (7.5625 * (t -= (2.625 / 2.75)) * t + 0.984375)
203
+ end
204
+ end
205
+
206
+ def tween_ease_from_to(t)
207
+ return 0.5 * (t ** 4) if ((t /= 0.5) < 1)
208
+ return -0.5 * ((t -= 2) * (t ** 3) - 2)
209
+ end
210
+
211
+ def tween_ease_from(t)
212
+ t ** 4
213
+ end
214
+
215
+ def tween_ease_to(t)
216
+ t ** 0.25
217
+ end
55
218
  end
56
219
  end
@@ -1,10 +1,11 @@
1
1
  module CyberarmEngine
2
2
  class BackgroundNineSlice
3
3
  include CyberarmEngine::Common
4
- attr_accessor :x, :y, :z, :width, :height
4
+ attr_accessor :x, :y, :z, :width, :height, :left, :top, :right, :bottom, :mode, :color
5
+ attr_reader :image
5
6
 
6
- def initialize(image_path:, x: 0, y: 0, z: 0, width: 64, height: 64, mode: :tiled, left: 4, top: 4, right: 56, bottom: 56)
7
- @image = get_image(image_path)
7
+ def initialize(image_path: nil, x: 0, y: 0, z: 0, width: 0, height: 0, mode: :tiled, left: 1, top: 1, right: 1, bottom: 1, color: Gosu::Color::WHITE)
8
+ @image = get_image(image_path) if image_path
8
9
 
9
10
  @x = x
10
11
  @y = y
@@ -20,23 +21,33 @@ module CyberarmEngine
20
21
  @right = right
21
22
  @bottom = bottom
22
23
 
23
- nine_slice
24
+ @color = color
25
+
26
+ nine_slice if @image
27
+ end
28
+
29
+ def image=(image_path)
30
+ old_image = @image
31
+ @image = image_path ? get_image(image_path) : image_path
32
+ nine_slice if @image && old_image != @image
24
33
  end
25
34
 
26
35
  def nine_slice
27
- @segment_top_left = Gosu.render(@left, @top) { @image.draw(0, 0, 0) }
28
- @segment_top_right = Gosu.render(@image.width - @right, @top) { @image.draw(-@right, 0, 0) }
36
+ # pp [@left, @top, @right, @bottom, @image.width]
29
37
 
30
- @segment_left = Gosu.render(@left, @bottom - @top) { @image.draw(0, -@top, 0) }
31
- @segment_right = Gosu.render(@image.width - @right, @bottom - @top) { @image.draw(-@right, -@top, 0) }
38
+ @segment_top_left = @image.subimage(0, 0, @left, @top)
39
+ @segment_top_right = @image.subimage(@image.width - @right, 0, @right, @top)
32
40
 
33
- @segment_bottom_left = Gosu.render(@left, @image.height - @bottom) { @image.draw(0, -@bottom, 0) }
34
- @segment_bottom_right = Gosu.render(@image.width - @right, @image.height - @bottom) { @image.draw(-@right, -@bottom, 0) }
41
+ @segment_left = @image.subimage(0, @top, @left, @image.height - (@top + @bottom))
42
+ @segment_right = @image.subimage(@image.width - @right, @top, @left, @image.height - (@top + @bottom))
35
43
 
36
- @segment_top = Gosu.render(@right - @left, @top) { @image.draw(-@left, 0, 0) }
37
- @segment_bottom = Gosu.render(@right - @left, @image.height - @bottom) { @image.draw(-@left, -@bottom, 0) }
44
+ @segment_bottom_left = @image.subimage(0, @image.height - @bottom, @left, @bottom)
45
+ @segment_bottom_right = @image.subimage(@image.width - @right, @image.height - @bottom, @right, @bottom)
38
46
 
39
- @segment_middle = Gosu.render(@right - @left, @bottom - @top) { @image.draw(-@left, -@top, 0) }
47
+ @segment_top = @image.subimage(@left, 0, @image.width - (@left + @right), @top)
48
+ @segment_bottom = @image.subimage(@left, @image.height - @bottom, @image.width - (@left + @right), @bottom)
49
+
50
+ @segment_middle = @image.subimage(@left, @top, @image.width - (@left + @right), @image.height - (@top + @bottom))
40
51
  end
41
52
 
42
53
  def cx
@@ -56,67 +67,73 @@ module CyberarmEngine
56
67
  end
57
68
 
58
69
  def width_scale
59
- width_scale = (@width - (@left + (@image.width - @right))).to_f / (@right - @left)
70
+ scale = (@width.to_f - (@left + @right)) / (@image.width - (@left + @right))
71
+ scale.abs
60
72
  end
61
73
 
62
74
  def height_scale
63
- height_scale = (@height - (@top + (@image.height - @bottom))).to_f / (@bottom - @top)
75
+ scale = (@height - (@top + @bottom)).to_f / (@image.height - (@top + @bottom))
76
+ scale.abs
64
77
  end
65
78
 
66
79
  def draw
80
+ return unless @image && @segment_top_left
81
+
67
82
  @mode == :tiled ? draw_tiled : draw_stretched
68
83
  end
69
84
 
70
85
  def draw_stretched
71
- @segment_top_left.draw(@x, @y, @z)
72
- @segment_top.draw(@x + @segment_top_left.width, @y, @z, width_scale) # SCALE X
73
- @segment_top_right.draw((@x + @width) - @segment_top_right.width, @y, @z)
74
-
75
- @segment_right.draw((@x + @width) - @segment_right.width, @y + @top, @z, 1, height_scale) # SCALE Y
76
- @segment_bottom_right.draw((@x + @width) - @segment_bottom_right.width, @y + @height - @segment_bottom_right.height, @z)
77
- @segment_bottom.draw(@x + @segment_bottom_left.width, (@y + @height) - @segment_bottom.height, @z, width_scale) # SCALE X
78
- @segment_bottom_left.draw(@x, (@y + @height) - @segment_bottom_left.height, @z)
79
- @segment_left.draw(@x, @y + @top, @z, 1, height_scale) # SCALE Y
80
- @segment_middle.draw(@x + @segment_top_left.width, @y + @segment_top.height, @z, width_scale, height_scale) # SCALE X and SCALE Y
86
+ @segment_top_left.draw(@x, @y, @z, 1, 1, @color)
87
+ @segment_top.draw(@x + @segment_top_left.width, @y, @z, width_scale, 1, @color) # SCALE X
88
+ @segment_top_right.draw((@x + @width) - @segment_top_right.width, @y, @z, 1, 1, @color)
89
+
90
+ @segment_right.draw((@x + @width) - @segment_right.width, @y + @top, @z, 1, height_scale, @color) # SCALE Y
91
+ @segment_bottom_right.draw((@x + @width) - @segment_bottom_right.width, @y + @height - @segment_bottom_right.height, @z, 1, 1, @color)
92
+ @segment_bottom.draw(@x + @segment_bottom_left.width, (@y + @height) - @segment_bottom.height, @z, width_scale, 1, @color) # SCALE X
93
+ @segment_bottom_left.draw(@x, (@y + @height) - @segment_bottom_left.height, @z, 1, 1, @color)
94
+ @segment_left.draw(@x, @y + @top, @z, 1, height_scale, @color) # SCALE Y
95
+ @segment_middle.draw(@x + @segment_top_left.width, @y + @segment_top.height, @z, width_scale, height_scale, @color) # SCALE X and SCALE Y
81
96
  end
82
97
 
83
98
  def draw_tiled
84
- @segment_top_left.draw(@x, @y, @z)
99
+ @segment_top_left.draw(@x, @y, @z, 1, 1, @color)
100
+
101
+ # p [width_scale, height_scale]
85
102
 
86
103
  Gosu.clip_to(@x + @segment_top_left.width, @y, @segment_top.width * width_scale, @segment_top.height) do
87
104
  width_scale.ceil.times do |i|
88
- @segment_top.draw(@x + @segment_top_left.width + (@segment_top.width * i), @y, @z) # SCALE X
105
+ @segment_top.draw(@x + @segment_top_left.width + (@segment_top.width * i), @y, @z, 1, 1, @color) # SCALE X
89
106
  end
90
107
  end
91
108
 
92
- @segment_top_right.draw((@x + @width) - @segment_top_right.width, @y, @z)
109
+ @segment_top_right.draw((@x + @width) - @segment_top_right.width, @y, @z, 1, 1, @color)
93
110
 
94
111
  Gosu.clip_to(@x + @width - @segment_top_right.width, @y + @top, @segment_right.width, @segment_right.height * height_scale) do
95
112
  height_scale.ceil.times do |i|
96
- @segment_right.draw((@x + @width) - @segment_right.width, @y + @top + (@segment_right.height * i), @z) # SCALE Y
113
+ @segment_right.draw((@x + @width) - @segment_right.width, @y + @top + (@segment_right.height * i), @z, 1, 1, @color) # SCALE Y
97
114
  end
98
115
  end
99
116
 
100
- @segment_bottom_right.draw((@x + @width) - @segment_bottom_right.width, @y + @height - @segment_bottom_right.height, @z)
117
+ @segment_bottom_right.draw((@x + @width) - @segment_bottom_right.width, @y + @height - @segment_bottom_right.height, @z, 1, 1, @color)
101
118
 
102
119
  Gosu.clip_to(@x + @segment_top_left.width, @y + @height - @segment_bottom.height, @segment_top.width * width_scale, @segment_bottom.height) do
103
120
  width_scale.ceil.times do |i|
104
- @segment_bottom.draw(@x + @segment_bottom_left.width + (@segment_bottom.width * i), (@y + @height) - @segment_bottom.height, @z) # SCALE X
121
+ @segment_bottom.draw(@x + @segment_bottom_left.width + (@segment_bottom.width * i), (@y + @height) - @segment_bottom.height, @z, 1, 1, @color) # SCALE X
105
122
  end
106
123
  end
107
124
 
108
- @segment_bottom_left.draw(@x, (@y + @height) - @segment_bottom_left.height, @z)
125
+ @segment_bottom_left.draw(@x, (@y + @height) - @segment_bottom_left.height, @z, 1, 1, @color)
109
126
 
110
127
  Gosu.clip_to(@x, @y + @top, @segment_left.width, @segment_left.height * height_scale) do
111
128
  height_scale.ceil.times do |i|
112
- @segment_left.draw(@x, @y + @top + (@segment_left.height * i), @z) # SCALE Y
129
+ @segment_left.draw(@x, @y + @top + (@segment_left.height * i), @z, 1, 1, @color) # SCALE Y
113
130
  end
114
131
  end
115
132
 
116
133
  Gosu.clip_to(@x + @segment_top_left.width, @y + @segment_top.height, @width - (@segment_left.width + @segment_right.width), @height - (@segment_top.height + @segment_bottom.height)) do
117
134
  height_scale.ceil.times do |y|
118
135
  width_scale.ceil.times do |x|
119
- @segment_middle.draw(@x + @segment_top_left.width + (@segment_middle.width * x), @y + @segment_top.height + (@segment_middle.height * y), @z) # SCALE X and SCALE Y
136
+ @segment_middle.draw(@x + @segment_top_left.width + (@segment_middle.width * x), @y + @segment_top.height + (@segment_middle.height * y), @z, 1, 1, @color) # SCALE X and SCALE Y
120
137
  end
121
138
  end
122
139
  end
@@ -22,18 +22,19 @@ module CyberarmEngine
22
22
 
23
23
  base_time = Gosu.milliseconds
24
24
 
25
+ @born_time = Gosu.milliseconds
26
+ @continue_after = 5_000
27
+
25
28
  @animators = [
26
29
  Animator.new(start_time: base_time += 1000, duration: 100, from: 0.0, to: 1.0, tween: :ease_in_out),
27
30
  Animator.new(start_time: base_time += -500, duration: 1_000, from: 0.0, to: 1.0, tween: :ease_in_out),
28
31
  Animator.new(start_time: base_time += 500, duration: 1_000, from: 0.0, to: 1.0, tween: :ease_in_out),
29
32
  Animator.new(start_time: base_time += 500, duration: 1_000, from: 0.0, to: 1.0, tween: :ease_in_out),
30
33
  Animator.new(start_time: base_time + 500, duration: 1_000, from: 0.0, to: 1.0, tween: :ease_in_out),
34
+ Animator.new(start_time: Gosu.milliseconds + @continue_after - 1_000, duration: 1_000, from: 0.0, to: 1.0, tween: :ease_in_out),
31
35
 
32
- Animator.new(start_time: Gosu.milliseconds + 250, duration: 500, from: 0.0, to: 1.0, tween: :ease_in_out) # CyberarmEngine LOGO
36
+ Animator.new(start_time: Gosu.milliseconds + 250, duration: 500, from: 0.0, to: 1.0, tween: :swing_to) # CyberarmEngine LOGO
33
37
  ]
34
-
35
- @born_time = Gosu.milliseconds
36
- @continue_after = 5_000
37
38
  end
38
39
 
39
40
  def draw
@@ -60,7 +61,7 @@ module CyberarmEngine
60
61
  Gosu::Color::WHITE
61
62
  )
62
63
 
63
- @title.x = window.width / 2 - @title.width / 2
64
+ @title.x = window.width / 2 - @title.text_width / 2
64
65
  @title.y = (window.height / 2 + (@spacer_height / 2) + @padding) * @animators[1].transition
65
66
  @title.text = "Powered By"
66
67
 
@@ -89,6 +90,8 @@ module CyberarmEngine
89
90
  )
90
91
  end
91
92
  end
93
+
94
+ Gosu.draw_rect(0, 0, window.width, window.height, Gosu::Color.rgba(0, 0, 0, 255 * @animators[5].transition), 10_000)
92
95
  end
93
96
 
94
97
  def update
@@ -112,14 +115,14 @@ module CyberarmEngine
112
115
  height = @title_size + @caption_size + @spacer_height + 2 * @padding + @spacer_height
113
116
 
114
117
  Gosu.record(width.ceil, height.ceil) do
115
- @title.x = (width - @padding * 2) / 2 - @title.width / 2
118
+ @title.x = (width - @padding * 2) / 2 - @title.text_width / 2
116
119
  @title.y = @padding
117
120
  @title.draw
118
121
 
119
122
  Gosu.draw_rect(0, @padding + @title_size + @padding, @spacer_width, @spacer_height, Gosu::Color::WHITE)
120
123
  Gosu.draw_rect(1, @padding + @title_size + @padding + 1, @spacer_width - 2, @spacer_height - 2, color_hint)
121
124
 
122
- @caption.x = (width - @padding * 2) / 2 - @caption.width / 2
125
+ @caption.x = (width - @padding * 2) / 2 - @caption.text_width / 2
123
126
  @caption.y = @padding + @title_size + @padding + @spacer_height + @padding
124
127
  @caption.draw
125
128
  end
@@ -28,8 +28,8 @@ module CyberarmEngine
28
28
  window.show_cursor = boolean
29
29
  end
30
30
 
31
- def draw_rect(x, y, width, height, color, z = 0)
32
- Gosu.draw_rect(x, y, width, height, color, z)
31
+ def draw_rect(x, y, width, height, color, z = 0, mode = :default)
32
+ Gosu.draw_rect(x, y, width, height, color, z, mode)
33
33
  end
34
34
 
35
35
  def fill(color, z = 0)
@@ -97,5 +97,17 @@ module CyberarmEngine
97
97
  def window
98
98
  $window
99
99
  end
100
+
101
+ def control_down?
102
+ Gosu.button_down?(Gosu::KB_LEFT_CONTROL) || Gosu.button_down?(Gosu::KB_RIGHT_CONTROL)
103
+ end
104
+
105
+ def shift_down?
106
+ Gosu.button_down?(Gosu::KB_LEFT_SHIFT) || Gosu.button_down?(Gosu::KB_RIGHT_SHIFT)
107
+ end
108
+
109
+ def alt_down?
110
+ Gosu.button_down?(Gosu::KB_LEFT_ALT) || Gosu.button_down?(Gosu::KB_RIGHT_ALT)
111
+ end
100
112
  end
101
113
  end
@@ -0,0 +1,158 @@
1
+ # frozen_string_literal: true
2
+
3
+ module CyberarmEngine
4
+ class Console
5
+ module Style
6
+ def self.error(string)
7
+ "<c=ff5555>#{string}</c>"
8
+ end
9
+
10
+ def self.warn(string)
11
+ "<c=ff7700>#{string}</c>"
12
+ end
13
+
14
+ def self.notice(string)
15
+ "<c=55ff55>#{string}</c>"
16
+ end
17
+
18
+ def self.highlight(string, color = "5555ff")
19
+ "<c=#{color}>#{string}</c>"
20
+ end
21
+ end
22
+
23
+ class Command
24
+ def self.inherited(subclass)
25
+ @list ||= []
26
+ @commands ||= []
27
+ @list << subclass
28
+ end
29
+
30
+ def self.setup
31
+ @list ||= []
32
+ @commands = []
33
+ @list.each do |subclass|
34
+ cmd = subclass.new
35
+ if @commands.detect { |c| c.command == cmd.command }
36
+ raise "Command '#{cmd.command}' from '#{cmd.class}' already exists!"
37
+ end
38
+
39
+ @commands << cmd
40
+ end
41
+ end
42
+
43
+ def self.use(command, arguments, console)
44
+ found_command = @commands.detect { |cmd| cmd.command == command.to_sym }
45
+
46
+ if found_command
47
+ found_command.handle(arguments, console)
48
+ else
49
+ console.stdin("Command #{Style.error(command)} not found.")
50
+ end
51
+ end
52
+
53
+ def self.find(command)
54
+ @commands.detect { |cmd| cmd.command == command.to_sym }
55
+ end
56
+
57
+ def self.list_commands
58
+ @commands
59
+ end
60
+
61
+ def initialize
62
+ @store = {}
63
+ @subcommands = []
64
+
65
+ setup
66
+ end
67
+
68
+ def setup
69
+ end
70
+
71
+ def subcommand(command, type)
72
+ if @subcommands.detect { |subcmd| subcmd.command == command.to_sym }
73
+ raise "Subcommand '#{command}' for '#{self.command}' already exists!"
74
+ end
75
+
76
+ @subcommands << SubCommand.new(self, command, type)
77
+ end
78
+
79
+ def get(key)
80
+ @store[key]
81
+ end
82
+
83
+ def set(key, value)
84
+ @store[key] = value
85
+ end
86
+
87
+ def group
88
+ raise NotImplementedError
89
+ end
90
+
91
+ def command
92
+ raise NotImplementedError
93
+ end
94
+
95
+ def handle(arguments, console)
96
+ raise NotImplementedError
97
+ end
98
+
99
+ def autocomplete(console)
100
+ split = console.text_input.text.split(" ")
101
+
102
+ if @subcommands.size.positive?
103
+ if !console.text_input.text.end_with?(" ") && split.size == 2
104
+ list = console.abbrev_search(@subcommands.map { |cmd| cmd.command.to_s }, split.last)
105
+
106
+ if list.size == 1
107
+ console.text_input.text = "#{split.first} #{list.first} "
108
+ else
109
+ return unless list.size.positive?
110
+
111
+ console.stdin(list.map { |cmd| Console::Style.highlight(cmd) }.join(", ").to_s)
112
+ end
113
+
114
+ # List available options on subcommand
115
+ elsif (console.text_input.text.end_with?(" ") && split.size == 2) || !console.text_input.text.end_with?(" ") && split.size == 3
116
+ subcommand = @subcommands.detect { |cmd| cmd.command.to_s == (split[1]) }
117
+
118
+ if subcommand
119
+ if split.size == 2
120
+ console.stdin("Available options: #{subcommand.values.map { |value| Console::Style.highlight(value) }.join(',')}")
121
+ else
122
+ list = console.abbrev_search(subcommand.values, split.last)
123
+ if list.size == 1
124
+ console.text_input.text = "#{split.first} #{split[1]} #{list.first} "
125
+ elsif list.size.positive?
126
+ console.stdin("Available options: #{list.map { |value| Console::Style.highlight(value) }.join(',')}")
127
+ end
128
+ end
129
+ end
130
+
131
+ # List available subcommands if command was entered and has only a space after it
132
+ elsif console.text_input.text.end_with?(" ") && split.size == 1
133
+ console.stdin("Available subcommands: #{@subcommands.map { |cmd| Console::Style.highlight(cmd.command) }.join(', ')}")
134
+ end
135
+ end
136
+ end
137
+
138
+ def handle_subcommand(arguments, console)
139
+ if arguments.size.zero?
140
+ console.stdin(usage)
141
+ return
142
+ end
143
+ subcommand = arguments.delete_at(0)
144
+
145
+ found_command = @subcommands.detect { |cmd| cmd.command == subcommand.to_sym }
146
+ if found_command
147
+ found_command.handle(arguments, console)
148
+ else
149
+ console.stdin("Unknown subcommand #{Style.error(subcommand)} for #{Style.highlight(command)}")
150
+ end
151
+ end
152
+
153
+ def usage
154
+ raise NotImplementedError
155
+ end
156
+ end
157
+ end
158
+ end
@@ -0,0 +1,43 @@
1
+ # frozen_string_literal: true
2
+
3
+ module CyberarmEngine
4
+ class Console
5
+ class HelpCommand < CyberarmEngine::Console::Command
6
+ def group
7
+ :global
8
+ end
9
+
10
+ def command
11
+ :help
12
+ end
13
+
14
+ def handle(arguments, console)
15
+ console.stdin(usage(arguments.first))
16
+ end
17
+
18
+ def autocomplete(console)
19
+ split = console.text_input.text.split(" ")
20
+ if !console.text_input.text.start_with?(" ") && split.size == 2
21
+ list = console.abbrev_search(Command.list_commands.map { |cmd| cmd.command.to_s }, split.last)
22
+ if list.size == 1
23
+ console.text_input.text = "#{split.first} #{list.first} "
24
+ elsif list.size > 1
25
+ console.stdin(list.map { |cmd| Style.highlight(cmd) }.join(", "))
26
+ end
27
+ end
28
+ end
29
+
30
+ def usage(command = nil)
31
+ if command
32
+ if cmd = Command.find(command)
33
+ cmd.usage
34
+ else
35
+ "#{Style.error(command)} is not a command"
36
+ end
37
+ else
38
+ "Available commands:\n#{Command.list_commands.map { |cmd| Style.highlight(cmd.command).to_s }.join(', ')}"
39
+ end
40
+ end
41
+ end
42
+ end
43
+ end