rubysketch 0.5.3 → 0.5.4

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: 2aae68b50056538ec9f1de57091af05176af8b629331d40e16b640de83d4a610
4
- data.tar.gz: 8929fd46a62eeb5457f386a72b255d3a6267fc1380bb29aabe9b093a722ecb34
3
+ metadata.gz: 82a93ef9dac4ae855bfa85f9a076ed05c807875db70be9c5e72419137499434e
4
+ data.tar.gz: 2f432e94c80ad231f50ca11df96ecd6a13c389551f75c426e161701e25d85a23
5
5
  SHA512:
6
- metadata.gz: fe6b88ffc3d9ee14f6b9206df4b554d498cd6a4b5b13a21baf8a6b0cfcebec4888322d12f6cee09829cc7a1038ad9ad2854945d5bb4e8706337bbfa310c113ab
7
- data.tar.gz: 56dac7438fb09ed3d8164e390e44dc785be289e6c4a4e5c3b9550fd5363c87f0a5a05f94806b6f68e691019e9297e2be6710435c5b0cafa35b2527ca1d7d1124
6
+ metadata.gz: cdf7238a4d07fe88b5d1fe3d68ea6f62d9536b142afda5dad1f4c15538bae2047d4e188bbc88e0777d641650ad9c5f5864720345ad5ec950e2ff18e83f552db9
7
+ data.tar.gz: 310a71a0b3388876bd0c0910a09bb9aa12e5686e5885ec8e4b2a32cb4af629ed18a010731a77b4a8ea1a9a4be41de504098767d0d133e3344554d5078508ad29
@@ -20,8 +20,9 @@ def setup_dependencies(build: true, only: nil)
20
20
 
21
21
  exts.each do |ext|
22
22
  gem = RENAMES[ext.to_sym].then {|s| s || ext}
23
- clone = "git clone --depth 1 https://github.com/xord/#{ext}.git ../#{ext}"
24
23
  ver = gemspec[/add_runtime_dependency.*['"]#{gem}['"].*['"]\s*~>\s*([\d\.]+)\s*['"]/, 1]
24
+ opts = '-c advice.detachedHead=false --depth 1'
25
+ clone = "git clone #{opts} https://github.com/xord/#{ext}.git ../#{ext}"
25
26
 
26
27
  # 'rake subtree:push' pushes all subrepos, so cloning by new tag
27
28
  # often fails before tagging each new tag
data/ChangeLog.md CHANGED
@@ -1,6 +1,13 @@
1
1
  # rubysketch ChangeLog
2
2
 
3
3
 
4
+ ## [v0.5.4] - 2023-04-30
5
+
6
+ - Add Sprite#image=() and Sprite#offset=()
7
+ - gravity() takes vector by pixel
8
+ - Add documents for Sprite class and test it
9
+
10
+
4
11
  ## [v0.5.3] - 2023-04-22
5
12
 
6
13
  - Depends on Beeps
data/RubySketch.podspec CHANGED
@@ -23,11 +23,15 @@ Pod::Spec.new do |s|
23
23
  incdirs = exts.map {|x| "#{root}/#{x}/include"}.concat %W[
24
24
  #{root}/src
25
25
  #{root}/beeps/vendor/stk/include
26
+ #{root}/beeps/vendor/AudioFile
27
+ #{root}/beeps/vendor/r8brain-free-src
28
+ #{root}/beeps/vendor/signalsmith-stretch
26
29
  #{root}/rays/vendor/glm
27
30
  #{root}/rays/vendor/clipper/cpp
28
31
  #{root}/rays/vendor/poly2tri/poly2tri
29
32
  #{root}/rays/vendor/splines-lib
30
- #{root}/reflex/vendor/Box2D/Box2D
33
+ #{root}/reflex/vendor/box2d/include
34
+ #{root}/reflex/vendor/box2d/src
31
35
  ${PODS_ROOT}/CRuby/CRuby/include
32
36
  ]
33
37
 
@@ -63,16 +67,25 @@ Pod::Spec.new do |s|
63
67
  end
64
68
 
65
69
  s.subspec "Beeps" do |spec|
66
- spec.source_files = "beeps/src/*.cpp"
67
- spec.frameworks = %w[OpenAL]
70
+ spec .source_files = "beeps/src/*.cpp"
71
+ spec.osx.source_files = "beeps/src/osx/*.{cpp,mm}"
72
+ spec.ios.source_files = "beeps/src/osx/*.{cpp,mm}"
73
+ spec.frameworks = %w[OpenAL AVFoundation]
68
74
 
69
75
  spec.subspec "STK" do |sub|
70
76
  sub.source_files = "beeps/vendor/stk/src/*.cpp"
71
- sub.exclude_files = %W[Tcp Udp Socket Thread Mutex InetWv Rt].map {|s|
77
+ sub.exclude_files = %w[Tcp Udp Socket Thread Mutex InetWv Rt].map {|s|
72
78
  "beeps/vendor/stk/src/#{s}*.cpp"
73
79
  }
74
80
  end
75
81
 
82
+ spec.subspec "R8BrainFreeSrc" do |sub|
83
+ sub.source_files = "beeps/vendor/r8brain-free-src/*.cpp"
84
+ sub.exclude_files = %w[example pffft_double/].map {|s|
85
+ "beeps/vendor/r8brain-free-src/#{s}*.cpp"
86
+ }
87
+ end
88
+
76
89
  spec.subspec "Ext" do |ext|
77
90
  ext.source_files = "beeps/ext/beeps/*.cpp"
78
91
  end
@@ -108,7 +121,7 @@ Pod::Spec.new do |s|
108
121
  spec.ios.frameworks = %w[CoreMotion]
109
122
 
110
123
  spec.subspec "Box2D" do |sub|
111
- sub.source_files = "reflex/vendor/Box2D/Box2D/Box2D/**/*.cpp"
124
+ sub.source_files = "reflex/vendor/box2d/src/**/*.cpp"
112
125
  end
113
126
 
114
127
  spec.subspec "Ext" do |ext|
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.5.3
1
+ 0.5.4
@@ -1,4 +1,3 @@
1
- require 'forwardable'
2
1
  require 'beeps'
3
2
  require 'processing/all'
4
3
 
@@ -10,3 +9,11 @@ require 'rubysketch/sprite'
10
9
  require 'rubysketch/sound'
11
10
  require 'rubysketch/graphics_context'
12
11
  require 'rubysketch/context'
12
+
13
+
14
+ module RubySketch
15
+
16
+ Vector = Processing::Vector
17
+ Image = Processing::Image
18
+
19
+ end# RubySketch
@@ -5,47 +5,103 @@ module RubySketch
5
5
 
6
6
  include GraphicsContext
7
7
 
8
+ Sound = RubySketch::Sound
9
+ Sprite = RubySketch::Sprite
10
+
11
+ # @private
8
12
  def initialize(window)
9
13
  super
10
- @sprites__ = window.add SpritesView.new
14
+ @layer__ = window.add_overlay SpriteLayer.new
11
15
  end
12
16
 
17
+ # Creates a new sprite and add it to physics engine.
18
+ #
19
+ # @overload createSprite(image: img)
20
+ # pos: [0, 0], size: [image.width, image.height]
21
+ # @param [Image] img sprite image
22
+ #
23
+ # @overload createSprite(x, y, image: img)
24
+ # pos: [x, y], size: [image.width, image.height]
25
+ # @param [Numeric] x x of sprite position
26
+ # @param [Numeric] y y of sprite position
27
+ # @param [Image] img sprite image
28
+ #
29
+ # @overload createSprite(x, y, w, h)
30
+ # pos(x, y), size: [w, h]
31
+ # @param [Numeric] x x of sprite position
32
+ # @param [Numeric] y y of sprite position
33
+ # @param [Numeric] w width of sprite
34
+ # @param [Numeric] h height of sprite
35
+ #
36
+ # @overload createSprite(x, y, w, h, image: img, offset: off)
37
+ # pos: [x, y], size: [w, h], offset: [offset.x, offset.x]
38
+ # @param [Numeric] x x of sprite position
39
+ # @param [Numeric] y y of sprite position
40
+ # @param [Numeric] w width of sprite
41
+ # @param [Numeric] h height of sprite
42
+ # @param [Image] img sprite image
43
+ # @param [Vector] off offset of sprite image
44
+ #
13
45
  def createSprite(*args, **kwargs)
14
46
  addSprite Sprite.new(*args, **kwargs)
15
47
  end
16
48
 
49
+ # Adds the sprite to the physics engine.
50
+ #
51
+ # @param [Sprite] sprite sprite object
52
+ #
17
53
  def addSprite(sprite)
18
- @sprites__.add sprite.getInternal__ if sprite
54
+ @layer__.add sprite.getInternal__ if sprite
19
55
  sprite
20
56
  end
21
57
 
58
+ # Removes the sprite from the physics engine.
59
+ #
60
+ # @param [Sprite] sprite sprite object
61
+ #
22
62
  def removeSprite(sprite)
23
- @sprites__.remove sprite.getInternal__ if sprite
63
+ @layer__.remove sprite.getInternal__ if sprite
24
64
  sprite
25
65
  end
26
66
 
67
+ # @private
27
68
  def loadSound(path)
28
69
  Sound.load path
29
70
  end
30
71
 
72
+ # Sets gravity for the physics engine.
73
+ #
74
+ # @overload gravity(vec)
75
+ # @param [Vector] vec gracity vector
76
+ #
77
+ # @overload gravity(ary)
78
+ # @param [Array<Numeric>] ary gravityX, gravityY
79
+ #
80
+ # @overload gravity(x, y)
81
+ # @param [Numeric] x x of gravity vector
82
+ # @param [Numeric] y y of gracity vector
83
+ #
31
84
  def gravity(*args)
32
85
  x, y =
33
- case args
34
- when Processing::Vector then args.array
86
+ case arg = args.first
87
+ when Vector then arg.array
88
+ when Array then arg
35
89
  else args
36
90
  end
37
- @sprites__.then do |v|
38
- v.gravity x * v.meter, y * v.meter
39
- end
91
+ @layer__.gravity x, y
40
92
  end
41
93
 
42
- class SpritesView < Reflex::View
43
- def on_draw(e)
44
- e.block
45
- end
94
+ end# Context
95
+
96
+
97
+ # @private
98
+ class SpriteLayer < Reflex::View
99
+
100
+ def on_draw(e)
101
+ e.block
46
102
  end
47
103
 
48
- end# Context
104
+ end# SpriteLayer
49
105
 
50
106
 
51
107
  end# RubySketch
@@ -1,6 +1,7 @@
1
1
  module RubySketch
2
2
 
3
3
 
4
+ # @private
4
5
  module Extension
5
6
 
6
7
  module_function
@@ -3,34 +3,27 @@ module RubySketch
3
3
 
4
4
  module GraphicsContext
5
5
 
6
+ # Draws one or more sprites.
7
+ #
8
+ # @param [Array<Sprite>] sprites
9
+ #
6
10
  def sprite(*sprites)
7
11
  sprites.flatten! if sprites.first&.is_a? Array
8
12
  sprites.each do |sp|
9
13
  v = sp.getInternal__
10
- f, angle, img, offset = v.frame, v.angle, sp.image, sp.offset
14
+ f, angle = v.frame, v.angle
11
15
  if angle == 0
12
- drawSprite__ f.x, f.y, f.w, f.h, img, offset
16
+ sp.on_draw__ f.x, f.y, f.w, f.h
13
17
  else
14
18
  pushMatrix do
15
19
  translate f.x, f.y
16
20
  rotate radians(angle)
17
- drawSprite__ 0, 0, f.w, f.h, img, offset
21
+ sp.on_draw__ 0, 0, f.w, f.h
18
22
  end
19
23
  end
20
24
  end
21
25
  end
22
26
 
23
- def drawSprite__(x, y, w, h, img, offset)
24
- if img && offset
25
- ox, oy = offset
26
- copy img, ox, oy, w, h, x, y, w, h
27
- elsif img
28
- image img, x, y
29
- else
30
- rect x, y, w, h
31
- end
32
- end
33
-
34
27
  end# GraphicsContext
35
28
 
36
29
 
@@ -1,3 +1,4 @@
1
+ # @private
1
2
  class Rays::Point
2
3
  def toVector()
3
4
  Processing::Vector.new x, y, z
@@ -1,6 +1,7 @@
1
1
  module RubySketch
2
2
 
3
3
 
4
+ # @private
4
5
  class Sound
5
6
 
6
7
  # @private
@@ -8,6 +9,8 @@ module RubySketch
8
9
  @sound = sound
9
10
  end
10
11
 
12
+ # Play sound.
13
+ #
11
14
  def play()
12
15
  old = @player
13
16
  @player = @sound.play
@@ -15,12 +18,16 @@ module RubySketch
15
18
  true
16
19
  end
17
20
 
21
+ # Pause sound.
22
+ #
18
23
  def pause()
19
24
  return false unless @player
20
25
  @player.pause
21
26
  true
22
27
  end
23
28
 
29
+ # Stop sound.
30
+ #
24
31
  def stop()
25
32
  return false unless @player
26
33
  @player.stop
@@ -28,22 +35,46 @@ module RubySketch
28
35
  true
29
36
  end
30
37
 
38
+ # Returns whether the sound is playing or not.
39
+ #
40
+ # @return [Boolean] playing or not
41
+ #
31
42
  def playing?()
32
43
  @player ? @player.playing? : false
33
44
  end
34
45
 
46
+ # Returns whether the sound is paused or not.
47
+ #
48
+ # @return [Boolean] paused or not
49
+ #
35
50
  def paused?()
36
- !playing? && !stopped?
51
+ @player ? @player.paused? : false
37
52
  end
38
53
 
54
+ # Returns whether the sound is stopped or not.
55
+ #
56
+ # @return [Boolean] stopped or not
57
+ #
39
58
  def stopped?()
40
59
  @player ? @player.stopped? : true
41
60
  end
42
61
 
62
+ # Save the sound data to a file.
63
+ #
64
+ # @param [String] path file path
65
+ #
66
+ # @return [Sound] self
67
+ #
43
68
  def save(path)
44
69
  @sound.save path
45
70
  end
46
71
 
72
+ # Load a sound file.
73
+ #
74
+ # @param [String] path file path
75
+ #
76
+ # @return [Sound] sound object
77
+ #
47
78
  def self.load(path)
48
79
  f = Beeps::FileIn.new path
49
80
  self.new Beeps::Sound.new(f, f.seconds, nchannels: f.nchannels)
@@ -1,128 +1,409 @@
1
1
  module RubySketch
2
2
 
3
3
 
4
+ # Sprite object.
5
+ #
4
6
  class Sprite
5
7
 
6
- extend Forwardable
8
+ # Initialize sprite object.
9
+ #
10
+ # @overload new(image: img)
11
+ # pos: [0, 0], size: [image.width, image.height]
12
+ # @param [Image] img sprite image
13
+ #
14
+ # @overload new(x, y, image: img)
15
+ # pos: [x, y], size: [image.width, image.height]
16
+ # @param [Numeric] x x of sprite position
17
+ # @param [Numeric] y y of sprite position
18
+ # @param [Image] img sprite image
19
+ #
20
+ # @overload new(x, y, w, h)
21
+ # pos(x, y), size: [w, h]
22
+ # @param [Numeric] x x of sprite position
23
+ # @param [Numeric] y y of sprite position
24
+ # @param [Numeric] w width of sprite
25
+ # @param [Numeric] h height of sprite
26
+ #
27
+ # @overload new(x, y, w, h, image: img, offset: off)
28
+ # pos: [x, y], size: [w, h], offset: [offset.x, offset.x]
29
+ # @param [Numeric] x x of sprite position
30
+ # @param [Numeric] y y of sprite position
31
+ # @param [Numeric] w width of sprite
32
+ # @param [Numeric] h height of sprite
33
+ # @param [Image] img sprite image
34
+ # @param [Vector] off offset of sprite image
35
+ #
36
+ def initialize(x = 0, y = 0, w = nil, h = nil, image: nil, offset: nil)
37
+ w ||= (image&.width || 0)
38
+ h ||= (image&.height || 0)
39
+ raise 'invalid size' unless w >= 0 && h >= 0
40
+ raise 'invalid image' if image && !image.getInternal__.is_a?(Rays::Image)
7
41
 
8
- def initialize(x = 0, y = 0, w = nil, h = nil, image: nil, offset: nil, dynamic: false)
9
- w ||= image&.width || 0
10
- h ||= image&.height || 0
11
- raise 'invalid size' unless w >= 0 && h >= 0
42
+ @view__ = SpriteView.new(self, x: x, y: y, w: w, h: h, back: :white)
12
43
 
13
- @image__, @offset__ = image, offset
14
- @view__ = View.new self, x: x, y: y, w: w, h: h, back: :white, dynamic: dynamic
44
+ self.image = image if image
45
+ self.offset = offset if offset
15
46
  end
16
47
 
17
- def_delegators :@view__,
18
- :x, :x=,
19
- :y, :y=,
20
- :w, :h,
21
- :width, :height,
22
- :dynamic?, :dynamic=,
23
- :density, :density=,
24
- :friction, :friction=,
25
- :restitution, :restitution=
48
+ # Returns the position of the sprite.
49
+ #
50
+ # @return [Vector] position
51
+ #
52
+ def position()
53
+ @view__.position.toVector
54
+ end
26
55
 
27
- def update(&block)
28
- @view__.on_update = block
56
+ # Sets the position of the sprite.
57
+ #
58
+ # @overload position=(vec)
59
+ # @param [Vector] vec position vector
60
+ #
61
+ # @overload position=(ary)
62
+ # @param [Array<Numeric>] ary positionX, positionY
63
+ #
64
+ # @return [Vector] position
65
+ #
66
+ def position=(arg)
67
+ @view__.position = arg.is_a?(Vector) ? arg.getInternal__ : arg
68
+ arg
29
69
  end
30
70
 
31
- def contact(&block)
32
- @view__.on_contact = block
71
+ # Returns the x-coordinate position of the sprite.
72
+ #
73
+ # @return [Numeric] sprite position x
74
+ #
75
+ def x()
76
+ @view__.x
33
77
  end
34
78
 
35
- def contact?(&block)
36
- @view__.will_contact = block
79
+ # Set the x-coordinate position of the sprite.
80
+ #
81
+ # @param [Numeric] n sprite position x
82
+ #
83
+ # @return [Numeric] sprite position x
84
+ #
85
+ def x=(n)
86
+ @view__.x = n
87
+ n
37
88
  end
38
89
 
39
- def position()
40
- @view__.position.toVector
90
+ # Returns the y-coordinate position of the sprite.
91
+ #
92
+ # @return [Numeric] sprite position y
93
+ #
94
+ def y()
95
+ @view__.y
41
96
  end
42
97
 
43
- def position=(vector)
44
- @view__.position = vector.getInternal__
98
+ # Set the y-coordinate position of the sprite.
99
+ #
100
+ # @param [Numeric] n sprite position y
101
+ #
102
+ # @return [Numeric] sprite position y
103
+ #
104
+ def y=(n)
105
+ @view__.y = n
106
+ n
45
107
  end
46
108
 
109
+ alias pos position
110
+ alias pos= position=
111
+
112
+ # Returns the size of the sprite.
113
+ #
114
+ # @return [Vector] size
115
+ #
47
116
  def size()
48
117
  @view__.size.toVector
49
118
  end
50
119
 
51
- def image()
52
- @image__
120
+ # Returns the width of the sprite.
121
+ #
122
+ # @return [Numeric] width
123
+ #
124
+ def width()
125
+ @view__.width
53
126
  end
54
127
 
55
- def offset()
56
- @offset__
128
+ # Returns the height of the sprite.
129
+ #
130
+ # @return [Numeric] height
131
+ #
132
+ def height()
133
+ @view__.height
57
134
  end
58
135
 
136
+ alias w width
137
+ alias h height
138
+
139
+ # Returns the velocity of the sprite.
140
+ #
141
+ # @return [Vector] velocity
142
+ #
59
143
  def velocity()
60
144
  @view__.velocity.toVector
61
145
  end
62
146
 
63
- def velocity=(vector)
64
- @view__.velocity = vector.getInternal__
147
+ # Sets the velocity of the sprite.
148
+ #
149
+ # @overload velocity=(vec)
150
+ # @param [Vector] vec velocity vector
151
+ #
152
+ # @overload velocity=(ary)
153
+ # @param [Array<Numeric>] ary velocityX, velocityY
154
+ #
155
+ # @return [Vector] velocity
156
+ #
157
+ def velocity=(arg)
158
+ @view__.velocity = arg.is_a?(Vector) ? arg.getInternal__ : arg
159
+ arg
65
160
  end
66
161
 
162
+ # Returns the x-axis velocity of the sprite.
163
+ #
164
+ # @return [Numeric] velocity.x
165
+ #
67
166
  def vx()
68
167
  @view__.velocity.x
69
168
  end
70
169
 
71
- def vx=(value)
72
- @view__.velocity = @view__.velocity.tap {|v| v.x = value}
73
- value
170
+ # Sets the x-axis velocity of the sprite.
171
+ #
172
+ # @param [Numeric] n x-axis velocity
173
+ #
174
+ # @return [Numeric] velocity.x
175
+ #
176
+ def vx=(n)
177
+ @view__.velocity = @view__.velocity.tap {|v| v.x = n}
178
+ n
74
179
  end
75
180
 
181
+ # Returns the y-axis velocity of the sprite.
182
+ #
183
+ # @return [Numeric] velocity.y
184
+ #
76
185
  def vy()
77
186
  @view__.velocity.y
78
187
  end
79
188
 
80
- def vy=(value)
81
- @view__.velocity = @view__.velocity.tap {|v| v.y = value}
82
- value
189
+ # Sets the y-axis velocity of the sprite.
190
+ #
191
+ # @param [Numeric] n y-axis velocity
192
+ #
193
+ # @return [Numeric] velocity.y
194
+ #
195
+ def vy=(n)
196
+ @view__.velocity = @view__.velocity.tap {|v| v.y = n}
197
+ n
198
+ end
199
+
200
+ alias vel velocity
201
+ alias vel= velocity=
202
+
203
+ # Returns the image of the sprite.
204
+ #
205
+ # @return [Image] sprite image
206
+ #
207
+ def image()
208
+ @image__
209
+ end
210
+
211
+ # Sets the sprite image.
212
+ #
213
+ # @param [Image] img sprite image
214
+ #
215
+ # @return [Image] sprite image
216
+ #
217
+ def image=(img)
218
+ @image__ = img
219
+ end
220
+
221
+ # Returns the offset of the sprite image.
222
+ #
223
+ # @return [Vector] offset of the sprite image
224
+ #
225
+ def offset()
226
+ @offset__
227
+ end
228
+
229
+ def offset=(arg)
230
+ @offset__ =
231
+ case arg
232
+ when Vector then arg
233
+ when Array then Vector.new(*arg[0, 2])
234
+ when nil then nil
235
+ else raise ArgumentError
236
+ end
237
+ end
238
+
239
+ # Returns whether the sprite is movable by the physics engine.
240
+ #
241
+ # @return [Boolean] true if dynamic
242
+ #
243
+ def dynamic?()
244
+ @view__.dynamic?
245
+ end
246
+
247
+ # Sets whether the sprite is movable by the physics engine.
248
+ #
249
+ # @param [Boolean] bool movable or not
250
+ #
251
+ # @return [Boolean] true if dynamic
252
+ #
253
+ def dynamic=(bool)
254
+ @view__.dynamic = bool
255
+ bool
256
+ end
257
+
258
+ # Returns the density of the sprite.
259
+ #
260
+ # @return [Numeric] density
261
+ #
262
+ def density()
263
+ @view__.density
264
+ end
265
+
266
+ # Sets the density of the sprite.
267
+ #
268
+ # @param [Numeric] n density
269
+ #
270
+ # @return [Numeric] density
271
+ #
272
+ def density=(n)
273
+ @view__.density = n
274
+ n
275
+ end
276
+
277
+ # Returns the friction of the sprite.
278
+ #
279
+ # @return [Numeric] friction
280
+ #
281
+ def friction()
282
+ @view__.friction
283
+ end
284
+
285
+ # Sets the friction of the sprite.
286
+ #
287
+ # @param [Numeric] n friction
288
+ #
289
+ # @return [Numeric] friction
290
+ #
291
+ def friction=(n)
292
+ @view__.friction = n
293
+ n
294
+ end
295
+
296
+ # Returns the restitution of the sprite.
297
+ #
298
+ # @return [Numeric] restitution
299
+ #
300
+ def restitution()
301
+ @view__.restitution
302
+ end
303
+
304
+ # Sets the restitution of the sprite.
305
+ #
306
+ # @param [Numeric] n restitution
307
+ #
308
+ # @return [Numeric] restitution
309
+ #
310
+ def restitution=(n)
311
+ @view__.restitution = n
312
+ n
83
313
  end
84
314
 
85
- alias pos position
86
- alias pos= position=
87
- alias vel velocity
88
- alias vel= velocity=
89
315
  alias dens density
90
316
  alias dens= density=
91
317
  alias fric friction
92
- alias fric= friction
318
+ alias fric= friction=
93
319
  alias rest restitution
94
320
  alias rest= restitution=
95
321
 
322
+ # Defines update block.
323
+ #
324
+ # @example vx is updated every frame
325
+ # sprite.update do
326
+ # self.vx *= 0.9
327
+ # end
328
+ #
329
+ # @return [nil] nil
330
+ #
331
+ def update(&block)
332
+ @view__.update = block
333
+ end
334
+
335
+ # Defines contact block.
336
+ #
337
+ # @example Score increases when the player sprite touches a coin
338
+ # playerSprite.contact do |o|
339
+ # score += 1 if o.coin?
340
+ # end
341
+ #
342
+ # @return [nil] nil
343
+ #
344
+ def contact(&block)
345
+ @view__.contact = block
346
+ end
347
+
348
+ # Defines contact? block.
349
+ #
350
+ # @example only collide with an enemy
351
+ # playerSprite.contact? do |o|
352
+ # o.enemy?
353
+ # end
354
+ #
355
+ # @return [nil] nil
356
+ #
357
+ def contact?(&block)
358
+ @view__.will_contact = block
359
+ end
360
+
361
+ # @private
362
+ def on_draw__(x, y, w, h)
363
+ img, off = frame, @image__, @offset__
364
+ if img && off
365
+ copy img, off.x, off.y, f.w, h, x, y, w, h
366
+ elsif img
367
+ image img, x, y
368
+ else
369
+ rect x, y, w, h
370
+ end
371
+ end
372
+
96
373
  # @private
97
374
  def getInternal__()
98
375
  @view__
99
376
  end
100
377
 
101
- class View < Reflex::View
102
- attr_accessor :update, :contact, :will_contact
103
- attr_reader :sprite
378
+ end# Sprite
104
379
 
105
- def initialize(sprite, *a, **k, &b)
106
- @sprite = sprite
107
- super(*a, **k, &b)
108
- end
109
380
 
110
- def on_update(e)
111
- @update.call if @update
112
- end
381
+ # @private
382
+ class SpriteView < Reflex::View
113
383
 
114
- def on_contact(e)
115
- v = e.view
116
- @contact.call v.sprite, e.action if @contact && v.is_a?(View)
117
- end
384
+ attr_accessor :update, :contact, :will_contact
385
+ attr_reader :sprite
118
386
 
119
- def will_contact?(v)
120
- return true if !@will_contact || !v.is_a?(View)
121
- @will_contact.call v.sprite
122
- end
387
+ def initialize(sprite, *a, **k, &b)
388
+ @sprite = sprite
389
+ super(*a, **k, &b)
123
390
  end
124
391
 
125
- end# Sprite
392
+ def on_update(e)
393
+ @update.call if @update
394
+ end
395
+
396
+ def on_contact(e)
397
+ v = e.view
398
+ @contact.call v.sprite, e.action if @contact && v.is_a?(SpriteView)
399
+ end
400
+
401
+ def will_contact?(v)
402
+ return true if !@will_contact || !v.is_a?(SpriteView)
403
+ @will_contact.call v.sprite
404
+ end
405
+
406
+ end# SpriteView
126
407
 
127
408
 
128
409
  end# RubySketch
@@ -1,6 +1,7 @@
1
1
  module RubySketch
2
2
 
3
3
 
4
+ # @private
4
5
  class Window < Processing::Window
5
6
 
6
7
  def on_update(e)
data/pod.rake CHANGED
@@ -19,15 +19,17 @@ task :setup
19
19
 
20
20
  repos.each do |repo, ver|
21
21
  rakefile = "#{repo}/Rakefile"
22
- opts = {
23
- depth: 1,
24
- branch: (ENV['RUBYSKETCH_BRANCH'] || "v#{ver}")
25
- }.map {|k, v| "--#{k} #{v}"}.join ' '
22
+ opts = [
23
+ '-c advice.detachedHead=false',
24
+ '--no-single-branch',
25
+ '--depth 1',
26
+ "--branch #{ENV['RUBYSKETCH_BRANCH'] || ('v' + ver)}"
27
+ ]
26
28
 
27
29
  task :setup => rakefile
28
30
 
29
31
  file rakefile do
30
- sh %( git clone #{opts} #{github}/#{repo} )
32
+ sh %( git clone #{opts.join ' '} #{github}/#{repo} )
31
33
  sh %( cd #{repo} && VENDOR_NOCOMPILE=1 rake vendor erb )
32
34
  end
33
35
  end
data/rubysketch.gemspec CHANGED
@@ -28,12 +28,12 @@ Gem::Specification.new do |s|
28
28
  s.platform = Gem::Platform::RUBY
29
29
  s.required_ruby_version = '>= 2.7.0'
30
30
 
31
- s.add_runtime_dependency 'xot', '~> 0.1.33'
32
- s.add_runtime_dependency 'rucy', '~> 0.1.33'
33
- s.add_runtime_dependency 'beeps', '~> 0.1.33'
34
- s.add_runtime_dependency 'rays', '~> 0.1.33'
35
- s.add_runtime_dependency 'reflexion', '~> 0.1.33'
36
- s.add_runtime_dependency 'processing', '~> 0.5.3'
31
+ s.add_runtime_dependency 'xot', '~> 0.1.34'
32
+ s.add_runtime_dependency 'rucy', '~> 0.1.34'
33
+ s.add_runtime_dependency 'beeps', '~> 0.1.35'
34
+ s.add_runtime_dependency 'rays', '~> 0.1.34'
35
+ s.add_runtime_dependency 'reflexion', '~> 0.1.35'
36
+ s.add_runtime_dependency 'processing', '~> 0.5.5'
37
37
 
38
38
  s.add_development_dependency 'rake'
39
39
  s.add_development_dependency 'test-unit'
data/test/test_sound.rb CHANGED
@@ -73,7 +73,7 @@ class TestSound < Test::Unit::TestCase
73
73
  assert_equal [false, false, true], [s.playing?, s.paused?, s.stopped?]
74
74
  end
75
75
 
76
- def test_save()
76
+ def test_save_load()
77
77
  s = sound
78
78
 
79
79
  File.delete PATH
@@ -81,10 +81,8 @@ class TestSound < Test::Unit::TestCase
81
81
 
82
82
  s.save PATH
83
83
  assert_true File.exist? PATH
84
- end
85
84
 
86
- def test_load()
87
- assert_nothing_raised {sound.play}
85
+ assert_nothing_raised {RS::Sound.load(PATH).play}
88
86
  end
89
87
 
90
88
  end# TestSound
data/test/test_sprite.rb CHANGED
@@ -6,18 +6,190 @@ require_relative 'helper'
6
6
 
7
7
  class TestSprite < Test::Unit::TestCase
8
8
 
9
+ RS = RubySketch
10
+
9
11
  def sprite(*args, **kwargs)
10
- RubySketch::Sprite.new(*args, **kwargs)
12
+ RS::Sprite.new(*args, **kwargs)
11
13
  end
12
14
 
13
15
  def vec(*args, **kwargs)
14
- Processing::Vector.new(*args, **kwargs)
16
+ RS::Vector.new(*args, **kwargs)
17
+ end
18
+
19
+ def image(w, h)
20
+ RS::Image.new Rays::Image.new(w, h)
15
21
  end
16
22
 
17
23
  def test_initialize()
18
- assert_equal 0, sprite.x
19
- assert_equal 0, sprite.y
20
- assert_equal vec(0, 0), sprite.pos
24
+ assert_equal vec(0, 0), sprite .pos
25
+ assert_equal vec(1, 2), sprite(1, 2) .pos
26
+ assert_equal vec(1, 2), sprite(1, 2, 3, 4).pos
27
+
28
+ assert_equal vec(0, 0), sprite .size
29
+ assert_equal vec(3, 4), sprite(1, 2, 3, 4) .size
30
+ assert_equal vec(5, 6), sprite( image: image(5, 6)).size
31
+ assert_equal vec(5, 6), sprite(1, 2, image: image(5, 6)).size
32
+ assert_equal vec(3, 4), sprite(1, 2, 3, 4, image: image(5, 6)).size
33
+
34
+ assert_equal nil, sprite .image
35
+ assert_equal [1, 2], sprite(image: image(1, 2)).image.size
36
+
37
+ assert_equal nil, sprite.offset
38
+ assert_equal vec(1, 2), sprite(offset: [1, 2]).offset
39
+ assert_equal vec(1, 2), sprite(offset: vec(1, 2)).offset
40
+
41
+ assert_raise {sprite 0, 0, -1, 0}
42
+ assert_raise {sprite 0, 0, 0, -1}
43
+ end
44
+
45
+ def test_position()
46
+ s = sprite
47
+ assert_equal vec(0, 0), s.pos
48
+
49
+ s.pos = vec(1, 2)
50
+ assert_equal vec(1, 2), s.pos
51
+
52
+ s.pos = [3, 4]
53
+ assert_equal vec(3, 4), s.pos
54
+ end
55
+
56
+ def test_xy()
57
+ s = sprite
58
+ assert_equal 0, s.x
59
+ assert_equal vec(0, 0), s.pos
60
+
61
+ s.x = 1
62
+ assert_equal 1, s.x
63
+ assert_equal vec(1, 0), s.pos
64
+
65
+ s.y = 2
66
+ assert_equal 2, s.y
67
+ assert_equal vec(1, 2), s.pos
68
+ end
69
+
70
+ def test_size()
71
+ assert_equal vec(0, 0), sprite .size
72
+ assert_equal vec(1, 0), sprite(0, 0, 1) .size
73
+ assert_equal vec(1, 2), sprite(0, 0, 1, 2) .size
74
+ assert_equal vec(3, 4), sprite(image: image(3, 4)).size
75
+ end
76
+
77
+ def test_wh()
78
+ assert_equal 1, sprite(0, 0, 1, 2).width
79
+ assert_equal 2, sprite(0, 0, 1, 2).height
80
+ end
81
+
82
+ def test_velocity()
83
+ s = sprite
84
+ assert_equal vec(0, 0), s.vel
85
+
86
+ s.vel = vec(1, 2)
87
+ assert_equal vec(1, 2), s.vel
88
+
89
+ s.vel = [3, 4]
90
+ assert_equal vec(3, 4), s.vel
91
+ end
92
+
93
+ def test_vxvy()
94
+ s = sprite
95
+ assert_equal 0, s.vx
96
+ assert_equal vec(0, 0), s.vel
97
+
98
+ s.vx = 1
99
+ assert_equal 1, s.vx
100
+ assert_equal vec(1, 0), s.vel
101
+
102
+ s.vy = 2
103
+ assert_equal 2, s.vy
104
+ assert_equal vec(1, 2), s.vel
105
+ end
106
+
107
+ def test_image()
108
+ s = sprite
109
+ assert_equal nil, s.image
110
+
111
+ s.image = image(1, 2)
112
+ assert_equal [1, 2], s.image.size
113
+
114
+ s.image = image(3, 4)
115
+ assert_equal [3, 4], s.image.size
116
+
117
+ s.image = nil
118
+ assert_equal nil, s.image
119
+ end
120
+
121
+ def test_offset()
122
+ s = sprite
123
+ assert_equal nil, s.offset
124
+
125
+ s.offset = [1, 2]
126
+ assert_equal vec(1, 2), s.offset
127
+
128
+ s.offset = vec(3, 4)
129
+ assert_equal vec(3, 4), s.offset
130
+
131
+ s.offset = nil
132
+ assert_equal nil, s.offset
133
+
134
+ assert_raise(ArgumentError) {s.offset = 1}
135
+ end
136
+
137
+ def test_dynamic?()
138
+ s = sprite
139
+ assert_equal false, s.dynamic?
140
+
141
+ s.dynamic = true
142
+ assert_equal true, s.dynamic?
143
+
144
+ s.dynamic = false
145
+ assert_equal false, s.dynamic?
146
+ end
147
+
148
+ def test_density()
149
+ s = sprite
150
+ assert_equal 0, s.dens
151
+
152
+ s.dens = 1
153
+ assert_equal 1, s.dens
154
+ end
155
+
156
+ def test_friction()
157
+ s = sprite
158
+ assert_equal 0, s.fric
159
+
160
+ s.fric = 1
161
+ assert_equal 1, s.fric
162
+ end
163
+
164
+ def test_restitution()
165
+ s = sprite
166
+ assert_equal 0, s.rest
167
+
168
+ s.rest = 1
169
+ assert_equal 1, s.rest
170
+ end
171
+
172
+ def test_blocks()
173
+ s = sprite
174
+ v = s.instance_variable_get :@view__
175
+ assert_nil v.update
176
+ assert_nil v.contact
177
+ assert_nil v.will_contact
178
+
179
+ s.update {}
180
+ assert_not_nil v.update
181
+ assert_nil v.contact
182
+ assert_nil v.will_contact
183
+
184
+ s.contact {}
185
+ assert_not_nil v.update
186
+ assert_not_nil v.contact
187
+ assert_nil v.will_contact
188
+
189
+ s.contact? {}
190
+ assert_not_nil v.update
191
+ assert_not_nil v.contact
192
+ assert_not_nil v.will_contact
21
193
  end
22
194
 
23
195
  end# TestSprite
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rubysketch
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.3
4
+ version: 0.5.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - xordog
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-04-21 00:00:00.000000000 Z
11
+ date: 2023-04-30 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: xot
@@ -16,84 +16,84 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: 0.1.33
19
+ version: 0.1.34
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: 0.1.33
26
+ version: 0.1.34
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: rucy
29
29
  requirement: !ruby/object:Gem::Requirement
30
30
  requirements:
31
31
  - - "~>"
32
32
  - !ruby/object:Gem::Version
33
- version: 0.1.33
33
+ version: 0.1.34
34
34
  type: :runtime
35
35
  prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
38
  - - "~>"
39
39
  - !ruby/object:Gem::Version
40
- version: 0.1.33
40
+ version: 0.1.34
41
41
  - !ruby/object:Gem::Dependency
42
42
  name: beeps
43
43
  requirement: !ruby/object:Gem::Requirement
44
44
  requirements:
45
45
  - - "~>"
46
46
  - !ruby/object:Gem::Version
47
- version: 0.1.33
47
+ version: 0.1.35
48
48
  type: :runtime
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
52
  - - "~>"
53
53
  - !ruby/object:Gem::Version
54
- version: 0.1.33
54
+ version: 0.1.35
55
55
  - !ruby/object:Gem::Dependency
56
56
  name: rays
57
57
  requirement: !ruby/object:Gem::Requirement
58
58
  requirements:
59
59
  - - "~>"
60
60
  - !ruby/object:Gem::Version
61
- version: 0.1.33
61
+ version: 0.1.34
62
62
  type: :runtime
63
63
  prerelease: false
64
64
  version_requirements: !ruby/object:Gem::Requirement
65
65
  requirements:
66
66
  - - "~>"
67
67
  - !ruby/object:Gem::Version
68
- version: 0.1.33
68
+ version: 0.1.34
69
69
  - !ruby/object:Gem::Dependency
70
70
  name: reflexion
71
71
  requirement: !ruby/object:Gem::Requirement
72
72
  requirements:
73
73
  - - "~>"
74
74
  - !ruby/object:Gem::Version
75
- version: 0.1.33
75
+ version: 0.1.35
76
76
  type: :runtime
77
77
  prerelease: false
78
78
  version_requirements: !ruby/object:Gem::Requirement
79
79
  requirements:
80
80
  - - "~>"
81
81
  - !ruby/object:Gem::Version
82
- version: 0.1.33
82
+ version: 0.1.35
83
83
  - !ruby/object:Gem::Dependency
84
84
  name: processing
85
85
  requirement: !ruby/object:Gem::Requirement
86
86
  requirements:
87
87
  - - "~>"
88
88
  - !ruby/object:Gem::Version
89
- version: 0.5.3
89
+ version: 0.5.5
90
90
  type: :runtime
91
91
  prerelease: false
92
92
  version_requirements: !ruby/object:Gem::Requirement
93
93
  requirements:
94
94
  - - "~>"
95
95
  - !ruby/object:Gem::Version
96
- version: 0.5.3
96
+ version: 0.5.5
97
97
  - !ruby/object:Gem::Dependency
98
98
  name: rake
99
99
  requirement: !ruby/object:Gem::Requirement