ray 0.1.1 → 0.2.0

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 (167) hide show
  1. data/README.md +9 -6
  2. data/Rakefile +1 -5
  3. data/ext/audio.c +25 -19
  4. data/ext/audio_source.c +67 -39
  5. data/ext/color.c +19 -19
  6. data/ext/drawable.c +190 -31
  7. data/ext/extconf.rb +16 -14
  8. data/ext/gl.c +310 -30
  9. data/ext/gl_buffer.c +223 -2
  10. data/ext/gl_index_buffer.c +11 -0
  11. data/ext/gl_int_array.c +24 -22
  12. data/ext/gl_vertex.c +84 -49
  13. data/ext/image.c +115 -51
  14. data/ext/image_target.c +58 -10
  15. data/ext/input.c +73 -6
  16. data/ext/mo.c +583 -0
  17. data/ext/mo.h +189 -0
  18. data/ext/music.c +9 -8
  19. data/ext/pixel_bus.c +349 -0
  20. data/ext/polygon.c +68 -45
  21. data/ext/ray.c +1 -0
  22. data/ext/ray.h +19 -1
  23. data/ext/rect.c +9 -47
  24. data/ext/say.h +1 -2
  25. data/ext/say_all.h +6 -0
  26. data/ext/say_audio.h +3 -0
  27. data/ext/say_audio_context.c +1 -4
  28. data/ext/say_basic_type.c +24 -0
  29. data/ext/say_basic_type.h +4 -0
  30. data/ext/say_buffer.c +217 -88
  31. data/ext/say_buffer.h +20 -5
  32. data/ext/say_buffer_renderer.c +10 -7
  33. data/ext/say_buffer_renderer.h +1 -1
  34. data/ext/say_buffer_slice.c +70 -76
  35. data/ext/say_context.c +109 -22
  36. data/ext/say_context.h +14 -0
  37. data/ext/say_drawable.c +113 -25
  38. data/ext/say_drawable.h +23 -2
  39. data/ext/say_error.c +7 -2
  40. data/ext/say_font.c +30 -27
  41. data/ext/say_font.h +3 -6
  42. data/ext/say_get_proc.c +35 -0
  43. data/ext/say_image.c +102 -27
  44. data/ext/say_image.h +11 -4
  45. data/ext/say_image_target.c +88 -34
  46. data/ext/say_image_target.h +3 -2
  47. data/ext/say_index_buffer.c +31 -19
  48. data/ext/say_index_buffer.h +4 -2
  49. data/ext/say_index_buffer_slice.c +78 -70
  50. data/ext/say_music.c +4 -2
  51. data/ext/say_osx.h +3 -2
  52. data/ext/say_osx_context.h +37 -4
  53. data/ext/say_osx_window.h +32 -37
  54. data/ext/say_pixel_bus.c +163 -0
  55. data/ext/say_pixel_bus.h +44 -0
  56. data/ext/say_polygon.c +2 -2
  57. data/ext/say_shader.c +66 -62
  58. data/ext/say_shader.h +2 -0
  59. data/ext/say_sprite.c +1 -2
  60. data/ext/say_target.c +14 -23
  61. data/ext/say_target.h +3 -1
  62. data/ext/say_text.c +45 -7
  63. data/ext/say_text.h +12 -3
  64. data/ext/say_thread.c +13 -6
  65. data/ext/say_thread.h +1 -1
  66. data/ext/say_thread_variable.c +5 -5
  67. data/ext/say_vertex_type.c +79 -41
  68. data/ext/say_vertex_type.h +6 -2
  69. data/ext/say_view.c +10 -31
  70. data/ext/say_view.h +1 -5
  71. data/ext/say_win.h +2 -2
  72. data/ext/say_win_context.h +49 -11
  73. data/ext/say_win_window.h +30 -27
  74. data/ext/say_window.c +3 -3
  75. data/ext/say_x11.h +3 -1
  76. data/ext/say_x11_context.h +64 -10
  77. data/ext/say_x11_window.h +22 -17
  78. data/ext/shader.c +9 -0
  79. data/ext/sprite.c +7 -1
  80. data/ext/target.c +80 -28
  81. data/ext/text.c +43 -1
  82. data/ext/view.c +53 -1
  83. data/ext/window.c +4 -0
  84. data/lib/ray/animation_list.rb +17 -2
  85. data/lib/ray/audio_source.rb +11 -0
  86. data/lib/ray/color.rb +14 -0
  87. data/lib/ray/drawable.rb +23 -0
  88. data/lib/ray/dsl/event.rb +1 -9
  89. data/lib/ray/dsl/event_runner.rb +3 -4
  90. data/lib/ray/dsl/matcher.rb +20 -1
  91. data/lib/ray/effect.rb +116 -0
  92. data/lib/ray/effect/black_and_white.rb +38 -0
  93. data/lib/ray/effect/color_inversion.rb +16 -0
  94. data/lib/ray/effect/generator.rb +145 -0
  95. data/lib/ray/effect/grayscale.rb +32 -0
  96. data/lib/ray/game.rb +25 -5
  97. data/lib/ray/gl/vertex.rb +105 -26
  98. data/lib/ray/helper.rb +5 -0
  99. data/lib/ray/image.rb +54 -13
  100. data/lib/ray/image_target.rb +7 -0
  101. data/lib/ray/matrix.rb +26 -0
  102. data/lib/ray/music.rb +4 -0
  103. data/lib/ray/pixel_bus.rb +22 -0
  104. data/lib/ray/polygon.rb +17 -0
  105. data/lib/ray/pp.rb +28 -0
  106. data/lib/ray/ray.rb +7 -1
  107. data/lib/ray/rect.rb +7 -13
  108. data/lib/ray/scene.rb +24 -5
  109. data/lib/ray/scene_list.rb +9 -0
  110. data/lib/ray/shader.rb +11 -2
  111. data/lib/ray/sound.rb +4 -0
  112. data/lib/ray/sprite.rb +23 -62
  113. data/lib/ray/target.rb +25 -0
  114. data/lib/ray/text.rb +10 -0
  115. data/lib/ray/turtle.rb +9 -3
  116. data/lib/ray/vector.rb +18 -0
  117. data/lib/ray/vertex.rb +6 -0
  118. data/lib/ray/view.rb +22 -0
  119. data/samples/animation/sprite_motion.rb +0 -60
  120. data/samples/audio/{spacial.rb → spatial.rb} +1 -1
  121. data/samples/buffer/buffer.rb +1 -0
  122. data/samples/buffer/index_buffer.rb +2 -0
  123. data/samples/cptn_ruby/cptn_ruby.rb +6 -7
  124. data/samples/effects/effect.rb +39 -0
  125. data/samples/effects/grayscale.rb +27 -0
  126. data/samples/opengl/image.rb +7 -5
  127. data/samples/opengl/instancing.rb +159 -0
  128. data/samples/opengl/instancing.rbc +3231 -0
  129. data/samples/opengl/obj_loader.rb +9 -8
  130. data/samples/opengl/shader.rb +1 -3
  131. data/samples/shaders/geometry.rb +108 -38
  132. data/samples/shaders/geometry.rbc +2074 -0
  133. data/samples/shaders/shape.rb +2 -2
  134. data/samples/starfighter/starfighter.rb +5 -5
  135. data/samples/window/get_pixel.rb +1 -1
  136. data/test/animation_list_test.rb +18 -4
  137. data/test/drawable_test.rb +70 -1
  138. data/test/effect_generator_test.rb +63 -0
  139. data/test/effect_test.rb +61 -0
  140. data/test/game_test.rb +18 -0
  141. data/test/gl_buffer_test.rb +43 -1
  142. data/test/gl_index_buffer_test.rb +5 -0
  143. data/test/gl_vertex_test.rb +28 -1
  144. data/test/image_test.rb +5 -5
  145. data/test/input_test.rb +49 -0
  146. data/test/pixel_bus_test.rb +28 -0
  147. data/test/rect_test.rb +4 -0
  148. data/{samples/_media → test/res}/Beep.wav +0 -0
  149. data/samples/_media/CptnRuby Gem.png b/data/test/res/CptnRuby → Gem.png +0 -0
  150. data/samples/_media/CptnRuby Map.txt b/data/test/res/CptnRuby → Map.txt +0 -0
  151. data/samples/_media/CptnRuby Tileset.png b/data/test/res/CptnRuby → Tileset.png +0 -0
  152. data/{samples/_media → test/res}/CptnRuby.png +0 -0
  153. data/{samples/_media → test/res}/Space.png +0 -0
  154. data/{samples/_media → test/res}/Star.png +0 -0
  155. data/{samples/_media → test/res}/Starfighter.png +0 -0
  156. data/test/res/cube.obj +28 -0
  157. data/test/res/light3d.c +2 -2
  158. data/test/res/stone.png +0 -0
  159. data/test/scene_test.rb +3 -0
  160. data/test/sprite_test.rb +10 -0
  161. data/test/text_test.rb +31 -2
  162. data/test/view_test.rb +13 -1
  163. metadata +38 -17
  164. data/ext/say_array.c +0 -124
  165. data/ext/say_array.h +0 -34
  166. data/ext/say_table.c +0 -86
  167. data/ext/say_table.h +0 -24
@@ -48,20 +48,66 @@ VALUE ray_gl_buffer_init(VALUE self, VALUE type, VALUE vtype) {
48
48
  return self;
49
49
  }
50
50
 
51
- /* Unbinds any buffer that was bound. */
51
+ /* @return [Boolean] True if the buffer has instance-specific data */
52
+ static
53
+ VALUE ray_gl_buffer_has_instance(VALUE self) {
54
+ return say_buffer_has_instance(ray_rb2buffer(self)) ? Qtrue : Qfalse;
55
+ }
56
+
57
+ /* Unbinds any bound buffer */
52
58
  static
53
59
  VALUE ray_gl_buffer_unbind(VALUE self) {
54
60
  say_buffer_unbind();
55
61
  return Qnil;
56
62
  }
57
63
 
58
- /* Binds the receiver */
64
+ /* Unbinds any bound VBO from array buffer */
65
+ static
66
+ VALUE ray_gl_buffer_unbind_vbo(VALUE self) {
67
+ say_buffer_unbind_vbo();
68
+ return Qnil;
69
+ }
70
+
71
+ /* Binds the receiver, allowing to draw data stored in it */
59
72
  static
60
73
  VALUE ray_gl_buffer_bind(VALUE self) {
61
74
  say_buffer_bind(ray_rb2buffer(self));
62
75
  return self;
63
76
  }
64
77
 
78
+ /* Binds the receivers's VBO as an OpenGL array buffer */
79
+ static
80
+ VALUE ray_gl_buffer_bind_vbo(VALUE self) {
81
+ say_buffer_bind_vbo(ray_rb2buffer(self));
82
+ return self;
83
+ }
84
+
85
+ /*
86
+ * Binds the receivers's VBO containing instance data as an OpenGL array buffer
87
+ */
88
+ static
89
+ VALUE ray_gl_buffer_bind_instance_vbo(VALUE self) {
90
+ say_buffer_bind_instance_vbo(ray_rb2buffer(self));
91
+ return self;
92
+ }
93
+
94
+ /*
95
+ * @return [Integer] The identifier of the OpenGL buffer used by the buffer
96
+ */
97
+ static
98
+ VALUE ray_gl_buffer_vbo(VALUE self) {
99
+ return ULONG2NUM(say_buffer_get_vbo(ray_rb2buffer(self)));
100
+ }
101
+
102
+ /*
103
+ * @return [Integer] The identifier of the OpenGL buffer used by the buffer to
104
+ * store per-instance data
105
+ */
106
+ static
107
+ VALUE ray_gl_buffer_instance_vbo(VALUE self) {
108
+ return ULONG2NUM(say_buffer_get_instance_vbo(ray_rb2buffer(self)));
109
+ }
110
+
65
111
  /*
66
112
  * @overload [](id)
67
113
  * @param [Integer] id
@@ -123,6 +169,77 @@ VALUE ray_gl_buffer_set(VALUE self, VALUE i, VALUE vertex) {
123
169
 
124
170
  return vertex;
125
171
  }
172
+ /*
173
+ * @overload get_instance(id)
174
+ * @param [Integer] id
175
+ * @return [Ray::GL::Vertex::Instance] The instance at the given index
176
+ */
177
+ static
178
+ VALUE ray_gl_buffer_get_instance(VALUE self, VALUE i) {
179
+ say_buffer *buf = ray_rb2buffer(self);
180
+
181
+ if (!say_buffer_has_instance(buf))
182
+ rb_raise(rb_eRuntimeError, "buffer has no instance data");
183
+
184
+ size_t size = say_buffer_get_instance_size(buf);
185
+ size_t index = NUM2ULONG(i);
186
+
187
+ if (index >= size)
188
+ return Qnil;
189
+
190
+ VALUE klass = rb_const_get(rb_iv_get(self, "@vertex_type"),
191
+ rb_intern("Instance"));
192
+ VALUE object = rb_funcall(klass, RAY_METH("allocate"), 0);
193
+
194
+ size_t byte_size = NUM2INT(rb_iv_get(klass, "@vertex_instance_size"));
195
+
196
+ void *ptr = NULL;
197
+ Data_Get_Struct(object, void, ptr);
198
+
199
+ memcpy(ptr, say_buffer_get_instance(buf, index), byte_size);
200
+
201
+ return object;
202
+ }
203
+
204
+ /*
205
+ * @overload set_intance(id, value)
206
+ * @param [Integer] id
207
+ * @param [Ray::GL::Vertex::Instance] value The instance to set the given
208
+ * index.
209
+ */
210
+ static
211
+ VALUE ray_gl_buffer_set_instance(VALUE self, VALUE i, VALUE vertex) {
212
+ rb_check_frozen(self);
213
+
214
+ say_buffer *buf = ray_rb2buffer(self);
215
+
216
+ if (!say_buffer_has_instance(buf))
217
+ rb_raise(rb_eRuntimeError, "buffer has no instance data");
218
+
219
+ VALUE klass = rb_const_get(rb_iv_get(self, "@vertex_type"),
220
+ rb_intern("Instance"));
221
+ if (!RAY_IS_A(vertex, klass)) {
222
+ rb_raise(rb_eTypeError, "Can't convert %s into %s",
223
+ RAY_OBJ_CLASSNAME(vertex), rb_class2name(klass));
224
+ }
225
+
226
+ size_t size = say_buffer_get_instance_size(buf);
227
+ size_t index = NUM2ULONG(i);
228
+
229
+ if (index >= size) {
230
+ rb_raise(rb_eRangeError, "%zu is outside of range 0...%zu",
231
+ size, index);
232
+ }
233
+
234
+ size_t byte_size = NUM2INT(rb_iv_get(klass, "@vertex_instance_size"));
235
+
236
+ void *ptr = NULL;
237
+ Data_Get_Struct(vertex, void, ptr);
238
+
239
+ memcpy(say_buffer_get_instance(buf, index), ptr, byte_size);
240
+
241
+ return vertex;
242
+ }
126
243
 
127
244
  /*
128
245
  * @overload update(range = 0...size)
@@ -176,6 +293,60 @@ VALUE ray_gl_buffer_update(int argc, VALUE *argv, VALUE self) {
176
293
  return self;
177
294
  }
178
295
 
296
+ /*
297
+ * @overload update_instance(range = 0...size)
298
+ * @param [Range<Integer>] range (see #update)
299
+ *
300
+ * Updates a part of the buffer's instance-specific data
301
+ *
302
+ * @overload update_instance(first, size)
303
+ * @param (see #update)
304
+ */
305
+ static
306
+ VALUE ray_gl_buffer_update_instance(int argc, VALUE *argv, VALUE self) {
307
+ say_buffer *buf = ray_rb2buffer(self);
308
+ size_t max_index = say_buffer_get_instance_size(buf);
309
+
310
+ if (!say_buffer_has_instance(buf))
311
+ rb_raise(rb_eRuntimeError, "buffer has no per-instance data");
312
+
313
+ if (argc == 0)
314
+ say_buffer_update_instance(buf);
315
+ else if (argc == 2) {
316
+ size_t begin = NUM2ULONG(argv[0]);
317
+ size_t end = NUM2ULONG(argv[1]);
318
+
319
+ if (end > max_index)
320
+ end = max_index;
321
+
322
+ if (begin > end || begin > max_index)
323
+ return self;
324
+
325
+ size_t size = (end - begin) + 1;
326
+
327
+ say_buffer_update_instance_part(buf, begin, size);
328
+ }
329
+ else {
330
+ VALUE range;
331
+ rb_scan_args(argc, argv, "1", &range); /* raise exception */
332
+
333
+ size_t begin = NUM2ULONG(rb_funcall(range, RAY_METH("begin"), 0));
334
+ size_t end = NUM2ULONG(rb_funcall(range, RAY_METH("end"), 0));
335
+
336
+ if (end > max_index)
337
+ end = max_index;
338
+
339
+ if (begin > end || begin > max_index)
340
+ return self;
341
+
342
+ size_t size = (end - begin) + 1;
343
+
344
+ say_buffer_update_instance_part(buf, begin, size);
345
+ }
346
+
347
+ return self;
348
+ }
349
+
179
350
  /* @return [Integer] Size of the buffer (amount of vertices it contains) */
180
351
  static
181
352
  VALUE ray_gl_buffer_size(VALUE self) {
@@ -195,6 +366,32 @@ VALUE ray_gl_buffer_resize(VALUE self, VALUE size) {
195
366
  return self;
196
367
  }
197
368
 
369
+ /* @return [Integer] Amount of per-instance blocks in the buffer */
370
+ static
371
+ VALUE ray_gl_buffer_instance_size(VALUE self) {
372
+ say_buffer *buf = ray_rb2buffer(self);
373
+ if (!say_buffer_has_instance(buf))
374
+ return Qnil;
375
+ return ULONG2NUM(say_buffer_get_instance_size(buf));
376
+ }
377
+
378
+ /*
379
+ * @overload resize_instance(size)
380
+ * @param [Integere] size (see #resize)
381
+ *
382
+ * Resizes the buffer's instance data, alsos causing it to be updated.
383
+ */
384
+ static
385
+ VALUE ray_gl_buffer_resize_instance(VALUE self, VALUE size) {
386
+ rb_check_frozen(self);
387
+ say_buffer *buf = ray_rb2buffer(self);
388
+ if (!say_buffer_has_instance(buf))
389
+ rb_raise(rb_eRuntimeError, "buffer has no per-instance data");
390
+ say_buffer_resize_instance(buf, NUM2ULONG(size));
391
+ return self;
392
+ }
393
+
394
+
198
395
  /*
199
396
  * Document-class: Ray::GL::Buffer
200
397
  *
@@ -211,14 +408,38 @@ void Init_ray_gl_buffer() {
211
408
  rb_define_alloc_func(ray_cGLBuffer, ray_gl_buffer_alloc);
212
409
  rb_define_method(ray_cGLBuffer, "initialize", ray_gl_buffer_init, 2);
213
410
 
411
+ rb_define_method(ray_cGLBuffer, "has_instance?", ray_gl_buffer_has_instance,
412
+ 0);
413
+
214
414
  rb_define_singleton_method(ray_cGLBuffer, "unbind", ray_gl_buffer_unbind, 0);
415
+ rb_define_singleton_method(ray_cGLBuffer, "unbind_vbo",
416
+ ray_gl_buffer_unbind_vbo, 0);
215
417
  rb_define_method(ray_cGLBuffer, "bind", ray_gl_buffer_bind, 0);
418
+ rb_define_method(ray_cGLBuffer, "bind_vbo", ray_gl_buffer_bind_vbo, 0);
419
+ rb_define_method(ray_cGLBuffer, "bind_instance_vbo",
420
+ ray_gl_buffer_bind_instance_vbo, 0);
421
+
422
+ rb_define_method(ray_cGLBuffer, "vbo", ray_gl_buffer_vbo, 0);
423
+ rb_define_method(ray_cGLBuffer, "instance_vbo", ray_gl_buffer_instance_vbo,
424
+ 0);
216
425
 
217
426
  rb_define_method(ray_cGLBuffer, "[]", ray_gl_buffer_get, 1);
218
427
  rb_define_method(ray_cGLBuffer, "[]=", ray_gl_buffer_set, 2);
219
428
 
429
+ rb_define_method(ray_cGLBuffer, "get_instance", ray_gl_buffer_get_instance,
430
+ 1);
431
+ rb_define_method(ray_cGLBuffer, "set_instance", ray_gl_buffer_set_instance,
432
+ 2);
433
+
220
434
  rb_define_method(ray_cGLBuffer, "update", ray_gl_buffer_update, -1);
435
+ rb_define_method(ray_cGLBuffer, "update_instance",
436
+ ray_gl_buffer_update_instance, -1);
221
437
 
222
438
  rb_define_method(ray_cGLBuffer, "size", ray_gl_buffer_size, 0);
223
439
  rb_define_method(ray_cGLBuffer, "resize", ray_gl_buffer_resize, 1);
440
+
441
+ rb_define_method(ray_cGLBuffer, "instance_size", ray_gl_buffer_instance_size,
442
+ 0);
443
+ rb_define_method(ray_cGLBuffer, "resize_instance",
444
+ ray_gl_buffer_resize_instance, 1);
224
445
  }
@@ -60,6 +60,15 @@ VALUE ray_gl_index_buffer_bind(VALUE self) {
60
60
  return self;
61
61
  }
62
62
 
63
+ /*
64
+ * @return [Integer] The identifier of the OpenGL buffer used by the index
65
+ * buffer.
66
+ */
67
+ static
68
+ VALUE ray_gl_index_buffer_ibo(VALUE self) {
69
+ return ULONG2NUM(say_index_buffer_get_ibo(ray_rb2index_buffer(self)));
70
+ }
71
+
63
72
  /*
64
73
  * @overload [](id)
65
74
  * @param [Integer] id
@@ -190,6 +199,8 @@ void Init_ray_gl_index_buffer() {
190
199
  ray_gl_index_buffer_unbind, 0);
191
200
  rb_define_method(ray_cGLIndexBuffer, "bind", ray_gl_index_buffer_bind, 0);
192
201
 
202
+ rb_define_method(ray_cGLIndexBuffer, "ibo", ray_gl_index_buffer_ibo, 0);
203
+
193
204
  rb_define_method(ray_cGLIndexBuffer, "[]", ray_gl_index_buffer_get, 1);
194
205
  rb_define_method(ray_cGLIndexBuffer, "[]=", ray_gl_index_buffer_set, 2);
195
206
 
@@ -2,27 +2,29 @@
2
2
 
3
3
  VALUE ray_cIntArray = Qnil;
4
4
 
5
- say_array *ray_rb2int_array(VALUE obj) {
5
+ mo_array *ray_rb2int_array(VALUE obj) {
6
6
  if (!rb_obj_is_kind_of(obj, rb_path2class("Ray::GL::IntArray"))) {
7
7
  rb_raise(rb_eTypeError, "can't convert %s into Ray::GL::IntArray",
8
8
  RAY_OBJ_CLASSNAME(obj));
9
9
  }
10
10
 
11
- say_array *ptr = NULL;
12
- Data_Get_Struct(obj, say_array, ptr);
11
+ mo_array *ptr = NULL;
12
+ Data_Get_Struct(obj, mo_array, ptr);
13
13
 
14
14
  return ptr;
15
15
  }
16
16
 
17
17
  static
18
18
  void ray_int_set_to_zero(void *elem) {
19
- *(int*)elem = 0;
19
+ *(GLint*)elem = 0;
20
20
  }
21
21
 
22
22
  static
23
23
  VALUE ray_int_array_alloc(VALUE self) {
24
- say_array *obj = say_array_create(sizeof(int), NULL, ray_int_set_to_zero);
25
- return Data_Wrap_Struct(self, NULL, say_array_free, obj);
24
+ mo_array *obj = mo_array_create(sizeof(GLint));
25
+ obj->init = ray_int_set_to_zero;
26
+
27
+ return Data_Wrap_Struct(self, NULL, mo_array_free, obj);
26
28
  }
27
29
 
28
30
  /*
@@ -31,11 +33,11 @@ VALUE ray_int_array_alloc(VALUE self) {
31
33
  */
32
34
  static
33
35
  VALUE ray_int_array_init(int argc, VALUE *argv, VALUE self) {
34
- say_array *ary = ray_rb2int_array(self);
36
+ mo_array *ary = ray_rb2int_array(self);
35
37
 
36
38
  for (int i = 0; i < argc; i++) {
37
- int val = NUM2INT(argv[i]);
38
- say_array_push(ary, &val);
39
+ GLint val = NUM2INT(argv[i]);
40
+ mo_array_push(ary, &val);
39
41
  }
40
42
 
41
43
  return self;
@@ -43,7 +45,7 @@ VALUE ray_int_array_init(int argc, VALUE *argv, VALUE self) {
43
45
 
44
46
  static
45
47
  VALUE ray_int_array_init_copy(VALUE self, VALUE orig) {
46
- say_array_copy(ray_rb2int_array(self), ray_rb2int_array(orig));
48
+ mo_array_copy(ray_rb2int_array(self), ray_rb2int_array(orig));
47
49
  return self;
48
50
  }
49
51
 
@@ -56,10 +58,10 @@ static
56
58
  VALUE ray_int_array_push(VALUE self, VALUE val) {
57
59
  rb_check_frozen(self);
58
60
 
59
- say_array *ary = ray_rb2int_array(self);
60
- int e = NUM2INT(val);
61
+ mo_array *ary = ray_rb2int_array(self);
62
+ GLint e = NUM2INT(val);
61
63
 
62
- say_array_push(ary, &e);
64
+ mo_array_push(ary, &e);
63
65
 
64
66
  return self;
65
67
  }
@@ -71,10 +73,10 @@ VALUE ray_int_array_push(VALUE self, VALUE val) {
71
73
  */
72
74
  static
73
75
  VALUE ray_int_array_get(VALUE self, VALUE i) {
74
- say_array *ary = ray_rb2int_array(self);
76
+ mo_array *ary = ray_rb2int_array(self);
75
77
  size_t idx = NUM2ULONG(i);
76
78
 
77
- int *elem = say_array_get(ary, idx);
79
+ GLint *elem = mo_array_get_ptr(ary, idx, GLint);
78
80
 
79
81
  if (elem) {
80
82
  return INT2FIX(*elem);
@@ -92,13 +94,13 @@ static
92
94
  VALUE ray_int_array_set(VALUE self, VALUE i, VALUE val) {
93
95
  rb_check_frozen(self);
94
96
 
95
- say_array *ary = ray_rb2int_array(self);
96
- size_t idx = NUM2ULONG(i);
97
+ mo_array *ary = ray_rb2int_array(self);
98
+ size_t idx = NUM2ULONG(i);
97
99
 
98
- if (say_array_get_size(ary) <= idx)
99
- say_array_resize(ary, idx + 1);
100
+ if (ary->size <= idx)
101
+ mo_array_resize(ary, idx + 1);
100
102
 
101
- *(int*)say_array_get(ary, idx) = NUM2INT(val);
103
+ mo_array_get_as(ary, idx, GLint) = NUM2INT(val);
102
104
 
103
105
  return val;
104
106
  }
@@ -106,13 +108,13 @@ VALUE ray_int_array_set(VALUE self, VALUE i, VALUE val) {
106
108
  /* @return [Integer] size of the array */
107
109
  static
108
110
  VALUE ray_int_array_size(VALUE self) {
109
- return INT2FIX(say_array_get_size(ray_rb2int_array(self)));
111
+ return INT2FIX(ray_rb2int_array(self)->size);
110
112
  }
111
113
 
112
114
  /* Removes all the elements from the array */
113
115
  static
114
116
  VALUE ray_int_array_clear(VALUE self) {
115
- say_array_resize(ray_rb2int_array(self), 0);
117
+ mo_array_resize(ray_rb2int_array(self), 0);
116
118
  return self;
117
119
  }
118
120
 
@@ -1,6 +1,8 @@
1
1
  #include "ray.h"
2
2
 
3
- VALUE ray_cGLVertex = Qnil;
3
+ VALUE ray_cGLVertex = Qnil;
4
+ VALUE ray_cGLInstance = Qnil;
5
+
4
6
  static VALUE ray_gl_vertex_types = Qnil;
5
7
 
6
8
  VALUE ray_get_vertex_class(size_t id) {
@@ -19,6 +21,55 @@ size_t ray_get_vtype(VALUE class) {
19
21
  }
20
22
  }
21
23
 
24
+ VALUE ray_get_vertex_element(void *data, VALUE type) {
25
+ switch (NUM2INT(rb_hash_aref(ray_gl_vertex_types, type))) {
26
+ case SAY_FLOAT:
27
+ return rb_float_new(*(GLfloat*)data);
28
+ case SAY_INT:
29
+ return INT2FIX(*(GLint*)data);
30
+ case SAY_UBYTE:
31
+ return INT2FIX(*(GLubyte*)data);
32
+ case SAY_BOOL:
33
+ return (*(GLint*)data) ? Qtrue : Qfalse;
34
+
35
+ case SAY_COLOR:
36
+ return ray_col2rb(*(say_color*)data);
37
+ case SAY_VECTOR2:
38
+ return ray_vector2_to_rb(*(say_vector2*)data);
39
+ case SAY_VECTOR3:
40
+ return ray_vector3_to_rb(*(say_vector3*)data);
41
+ }
42
+
43
+ return Qnil;
44
+ }
45
+
46
+ void ray_set_vertex_element(void *data, VALUE type, VALUE val) {
47
+ switch (NUM2INT(rb_hash_aref(ray_gl_vertex_types, type))) {
48
+ case SAY_FLOAT:
49
+ *(GLfloat*)data = NUM2DBL(val);
50
+ break;
51
+ case SAY_INT:
52
+ *(GLint*)data = NUM2INT(val);
53
+ break;
54
+ case SAY_UBYTE:
55
+ *(GLubyte*)data = ray_byte_clamp(NUM2INT(val));
56
+ break;
57
+ case SAY_BOOL:
58
+ (*(GLint*)data) = RTEST(val);
59
+ break;
60
+
61
+ case SAY_COLOR:
62
+ *(say_color*)data = ray_rb2col(val);
63
+ break;
64
+ case SAY_VECTOR2:
65
+ *(say_vector2*)data = ray_convert_to_vector2(val);
66
+ break;
67
+ case SAY_VECTOR3:
68
+ *(say_vector3*)data = ray_convert_to_vector3(val);
69
+ break;
70
+ }
71
+ }
72
+
22
73
  VALUE ray_gl_vertex_alloc(VALUE self) {
23
74
  size_t size = NUM2ULONG(rb_iv_get(self, "@vertex_type_size"));
24
75
 
@@ -26,6 +77,13 @@ VALUE ray_gl_vertex_alloc(VALUE self) {
26
77
  return Data_Wrap_Struct(self, NULL, free, vertex);
27
78
  }
28
79
 
80
+ VALUE ray_gl_instance_alloc(VALUE self) {
81
+ size_t size = NUM2ULONG(rb_iv_get(self, "@vertex_instance_size"));
82
+
83
+ void *instance = malloc(size);
84
+ return Data_Wrap_Struct(self, NULL, free, instance);
85
+ }
86
+
29
87
  static
30
88
  VALUE ray_gl_vertex_make_type(VALUE self, VALUE types) {
31
89
  size_t size = RARRAY_LEN(types);
@@ -42,11 +100,13 @@ VALUE ray_gl_vertex_make_type(VALUE self, VALUE types) {
42
100
  VALUE name = RAY_ARRAY_AT(element, 0);
43
101
  VALUE type = RAY_ARRAY_AT(element, 1);
44
102
 
45
- char *c_name = StringValuePtr(name);
103
+ VALUE per_instance = RAY_ARRAY_AT(element, 2);
104
+
105
+ char *c_name = say_strdup(StringValuePtr(name));
46
106
  say_vertex_elem_type c_type = NUM2INT(rb_hash_aref(ray_gl_vertex_types,
47
107
  type));
48
108
 
49
- say_vertex_elem c_elem = {c_type, c_name};
109
+ say_vertex_elem c_elem = {c_type, c_name, RTEST(per_instance)};
50
110
  say_vertex_type_push(vtype, c_elem);
51
111
  }
52
112
 
@@ -65,31 +125,18 @@ VALUE ray_gl_vertex_size(VALUE self, VALUE vtype) {
65
125
  return INT2FIX(say_vertex_type_get_size(type));
66
126
  }
67
127
 
128
+ static
129
+ VALUE ray_gl_vertex_instance_size(VALUE self, VALUE vtype) {
130
+ say_vertex_type *type = say_get_vertex_type(NUM2ULONG(vtype));
131
+ return INT2FIX(say_vertex_type_get_instance_size(type));
132
+ }
133
+
68
134
  VALUE ray_gl_vertex_element(VALUE self, VALUE offset, VALUE type) {
69
135
  uint8_t *data = NULL;
70
136
  Data_Get_Struct(self, uint8_t, data);
71
137
 
72
138
  data += NUM2ULONG(offset);
73
-
74
- switch (NUM2INT(rb_hash_aref(ray_gl_vertex_types, type))) {
75
- case SAY_FLOAT:
76
- return rb_float_new(*(GLfloat*)data);
77
- case SAY_INT:
78
- return INT2FIX((*(GLint*)data));
79
- case SAY_UBYTE:
80
- return INT2FIX((*(GLubyte*)data));
81
- case SAY_BOOL:
82
- return (*(GLint*)data) ? Qtrue : Qfalse;
83
-
84
- case SAY_COLOR:
85
- return ray_col2rb(*(say_color*)data);
86
- case SAY_VECTOR2:
87
- return ray_vector2_to_rb(*(say_vector2*)data);
88
- case SAY_VECTOR3:
89
- return ray_vector3_to_rb(*(say_vector3*)data);
90
- }
91
-
92
- return Qnil;
139
+ return ray_get_vertex_element(data, type);
93
140
  }
94
141
 
95
142
  VALUE ray_gl_vertex_set_element(VALUE self, VALUE offset, VALUE type,
@@ -98,33 +145,9 @@ VALUE ray_gl_vertex_set_element(VALUE self, VALUE offset, VALUE type,
98
145
  Data_Get_Struct(self, uint8_t, data);
99
146
 
100
147
  data += NUM2ULONG(offset);
148
+ ray_set_vertex_element(data, type, val);
101
149
 
102
- switch (NUM2INT(rb_hash_aref(ray_gl_vertex_types, type))) {
103
- case SAY_FLOAT:
104
- (*(GLfloat*)data) = NUM2DBL(val);
105
- break;
106
- case SAY_INT:
107
- ((*(GLint*)data)) = NUM2INT(val);
108
- break;
109
- case SAY_UBYTE:
110
- ((*(GLubyte*)data)) = ray_byte_clamp(NUM2INT(val));
111
- break;
112
- case SAY_BOOL:
113
- (*(GLint*)data) = RTEST(val);
114
- break;
115
-
116
- case SAY_COLOR:
117
- ((*(say_color*)data)) = ray_rb2col(val);
118
- break;
119
- case SAY_VECTOR2:
120
- ((*(say_vector2*)data)) = ray_convert_to_vector2(val);
121
- break;
122
- case SAY_VECTOR3:
123
- ((*(say_vector3*)data)) = ray_convert_to_vector3(val);
124
- break;
125
- }
126
-
127
- return type;
150
+ return val;
128
151
  }
129
152
 
130
153
  void Init_ray_gl_vertex() {
@@ -137,6 +160,8 @@ void Init_ray_gl_vertex() {
137
160
  ray_gl_vertex_offset_of, 2);
138
161
  rb_define_singleton_method(ray_cGLVertex, "size",
139
162
  ray_gl_vertex_size, 1);
163
+ rb_define_singleton_method(ray_cGLVertex, "instance_size",
164
+ ray_gl_vertex_instance_size, 1);
140
165
 
141
166
  rb_define_private_method(ray_cGLVertex, "element", ray_gl_vertex_element, 2);
142
167
  rb_define_private_method(ray_cGLVertex, "set_element",
@@ -154,4 +179,14 @@ void Init_ray_gl_vertex() {
154
179
  rb_hash_aset(ray_gl_vertex_types, RAY_SYM("vector3"), INT2FIX(SAY_VECTOR3));
155
180
 
156
181
  rb_define_const(ray_cGLVertex, "TypeMap", ray_gl_vertex_types);
182
+
183
+ ray_cGLInstance = rb_define_class_under(ray_cGLVertex, "Instance",
184
+ rb_cObject);
185
+ rb_define_alloc_func(ray_cGLInstance, ray_gl_instance_alloc);
186
+
187
+ rb_define_private_method(ray_cGLInstance, "element", ray_gl_vertex_element,
188
+ 2);
189
+ rb_define_private_method(ray_cGLInstance, "set_element",
190
+ ray_gl_vertex_set_element, 3);
191
+
157
192
  }