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.
- data/README.md +9 -6
- data/Rakefile +1 -5
- data/ext/audio.c +25 -19
- data/ext/audio_source.c +67 -39
- data/ext/color.c +19 -19
- data/ext/drawable.c +190 -31
- data/ext/extconf.rb +16 -14
- data/ext/gl.c +310 -30
- data/ext/gl_buffer.c +223 -2
- data/ext/gl_index_buffer.c +11 -0
- data/ext/gl_int_array.c +24 -22
- data/ext/gl_vertex.c +84 -49
- data/ext/image.c +115 -51
- data/ext/image_target.c +58 -10
- data/ext/input.c +73 -6
- data/ext/mo.c +583 -0
- data/ext/mo.h +189 -0
- data/ext/music.c +9 -8
- data/ext/pixel_bus.c +349 -0
- data/ext/polygon.c +68 -45
- data/ext/ray.c +1 -0
- data/ext/ray.h +19 -1
- data/ext/rect.c +9 -47
- data/ext/say.h +1 -2
- data/ext/say_all.h +6 -0
- data/ext/say_audio.h +3 -0
- data/ext/say_audio_context.c +1 -4
- data/ext/say_basic_type.c +24 -0
- data/ext/say_basic_type.h +4 -0
- data/ext/say_buffer.c +217 -88
- data/ext/say_buffer.h +20 -5
- data/ext/say_buffer_renderer.c +10 -7
- data/ext/say_buffer_renderer.h +1 -1
- data/ext/say_buffer_slice.c +70 -76
- data/ext/say_context.c +109 -22
- data/ext/say_context.h +14 -0
- data/ext/say_drawable.c +113 -25
- data/ext/say_drawable.h +23 -2
- data/ext/say_error.c +7 -2
- data/ext/say_font.c +30 -27
- data/ext/say_font.h +3 -6
- data/ext/say_get_proc.c +35 -0
- data/ext/say_image.c +102 -27
- data/ext/say_image.h +11 -4
- data/ext/say_image_target.c +88 -34
- data/ext/say_image_target.h +3 -2
- data/ext/say_index_buffer.c +31 -19
- data/ext/say_index_buffer.h +4 -2
- data/ext/say_index_buffer_slice.c +78 -70
- data/ext/say_music.c +4 -2
- data/ext/say_osx.h +3 -2
- data/ext/say_osx_context.h +37 -4
- data/ext/say_osx_window.h +32 -37
- data/ext/say_pixel_bus.c +163 -0
- data/ext/say_pixel_bus.h +44 -0
- data/ext/say_polygon.c +2 -2
- data/ext/say_shader.c +66 -62
- data/ext/say_shader.h +2 -0
- data/ext/say_sprite.c +1 -2
- data/ext/say_target.c +14 -23
- data/ext/say_target.h +3 -1
- data/ext/say_text.c +45 -7
- data/ext/say_text.h +12 -3
- data/ext/say_thread.c +13 -6
- data/ext/say_thread.h +1 -1
- data/ext/say_thread_variable.c +5 -5
- data/ext/say_vertex_type.c +79 -41
- data/ext/say_vertex_type.h +6 -2
- data/ext/say_view.c +10 -31
- data/ext/say_view.h +1 -5
- data/ext/say_win.h +2 -2
- data/ext/say_win_context.h +49 -11
- data/ext/say_win_window.h +30 -27
- data/ext/say_window.c +3 -3
- data/ext/say_x11.h +3 -1
- data/ext/say_x11_context.h +64 -10
- data/ext/say_x11_window.h +22 -17
- data/ext/shader.c +9 -0
- data/ext/sprite.c +7 -1
- data/ext/target.c +80 -28
- data/ext/text.c +43 -1
- data/ext/view.c +53 -1
- data/ext/window.c +4 -0
- data/lib/ray/animation_list.rb +17 -2
- data/lib/ray/audio_source.rb +11 -0
- data/lib/ray/color.rb +14 -0
- data/lib/ray/drawable.rb +23 -0
- data/lib/ray/dsl/event.rb +1 -9
- data/lib/ray/dsl/event_runner.rb +3 -4
- data/lib/ray/dsl/matcher.rb +20 -1
- data/lib/ray/effect.rb +116 -0
- data/lib/ray/effect/black_and_white.rb +38 -0
- data/lib/ray/effect/color_inversion.rb +16 -0
- data/lib/ray/effect/generator.rb +145 -0
- data/lib/ray/effect/grayscale.rb +32 -0
- data/lib/ray/game.rb +25 -5
- data/lib/ray/gl/vertex.rb +105 -26
- data/lib/ray/helper.rb +5 -0
- data/lib/ray/image.rb +54 -13
- data/lib/ray/image_target.rb +7 -0
- data/lib/ray/matrix.rb +26 -0
- data/lib/ray/music.rb +4 -0
- data/lib/ray/pixel_bus.rb +22 -0
- data/lib/ray/polygon.rb +17 -0
- data/lib/ray/pp.rb +28 -0
- data/lib/ray/ray.rb +7 -1
- data/lib/ray/rect.rb +7 -13
- data/lib/ray/scene.rb +24 -5
- data/lib/ray/scene_list.rb +9 -0
- data/lib/ray/shader.rb +11 -2
- data/lib/ray/sound.rb +4 -0
- data/lib/ray/sprite.rb +23 -62
- data/lib/ray/target.rb +25 -0
- data/lib/ray/text.rb +10 -0
- data/lib/ray/turtle.rb +9 -3
- data/lib/ray/vector.rb +18 -0
- data/lib/ray/vertex.rb +6 -0
- data/lib/ray/view.rb +22 -0
- data/samples/animation/sprite_motion.rb +0 -60
- data/samples/audio/{spacial.rb → spatial.rb} +1 -1
- data/samples/buffer/buffer.rb +1 -0
- data/samples/buffer/index_buffer.rb +2 -0
- data/samples/cptn_ruby/cptn_ruby.rb +6 -7
- data/samples/effects/effect.rb +39 -0
- data/samples/effects/grayscale.rb +27 -0
- data/samples/opengl/image.rb +7 -5
- data/samples/opengl/instancing.rb +159 -0
- data/samples/opengl/instancing.rbc +3231 -0
- data/samples/opengl/obj_loader.rb +9 -8
- data/samples/opengl/shader.rb +1 -3
- data/samples/shaders/geometry.rb +108 -38
- data/samples/shaders/geometry.rbc +2074 -0
- data/samples/shaders/shape.rb +2 -2
- data/samples/starfighter/starfighter.rb +5 -5
- data/samples/window/get_pixel.rb +1 -1
- data/test/animation_list_test.rb +18 -4
- data/test/drawable_test.rb +70 -1
- data/test/effect_generator_test.rb +63 -0
- data/test/effect_test.rb +61 -0
- data/test/game_test.rb +18 -0
- data/test/gl_buffer_test.rb +43 -1
- data/test/gl_index_buffer_test.rb +5 -0
- data/test/gl_vertex_test.rb +28 -1
- data/test/image_test.rb +5 -5
- data/test/input_test.rb +49 -0
- data/test/pixel_bus_test.rb +28 -0
- data/test/rect_test.rb +4 -0
- data/{samples/_media → test/res}/Beep.wav +0 -0
- data/samples/_media/CptnRuby Gem.png b/data/test/res/CptnRuby → Gem.png +0 -0
- data/samples/_media/CptnRuby Map.txt b/data/test/res/CptnRuby → Map.txt +0 -0
- data/samples/_media/CptnRuby Tileset.png b/data/test/res/CptnRuby → Tileset.png +0 -0
- data/{samples/_media → test/res}/CptnRuby.png +0 -0
- data/{samples/_media → test/res}/Space.png +0 -0
- data/{samples/_media → test/res}/Star.png +0 -0
- data/{samples/_media → test/res}/Starfighter.png +0 -0
- data/test/res/cube.obj +28 -0
- data/test/res/light3d.c +2 -2
- data/test/res/stone.png +0 -0
- data/test/scene_test.rb +3 -0
- data/test/sprite_test.rb +10 -0
- data/test/text_test.rb +31 -2
- data/test/view_test.rb +13 -1
- metadata +38 -17
- data/ext/say_array.c +0 -124
- data/ext/say_array.h +0 -34
- data/ext/say_table.c +0 -86
- data/ext/say_table.h +0 -24
data/ext/mo.h
ADDED
@@ -0,0 +1,189 @@
|
|
1
|
+
#ifndef MY_OWN_HEADER_GUARD
|
2
|
+
#define MY_OWN_HEADER_GUARD 1
|
3
|
+
|
4
|
+
/**
|
5
|
+
* My Own utilities.
|
6
|
+
* (Depending on My Own mood, may mean "Mon_Ouie's utilities")
|
7
|
+
*
|
8
|
+
* Includes the data stuctures that I usually need when programming in C.
|
9
|
+
*/
|
10
|
+
|
11
|
+
#include <stdlib.h>
|
12
|
+
#include <stdint.h>
|
13
|
+
#include <stdbool.h>
|
14
|
+
#include <assert.h>
|
15
|
+
#include <string.h>
|
16
|
+
#include <stdio.h>
|
17
|
+
|
18
|
+
/**
|
19
|
+
* Function pointer types
|
20
|
+
*/
|
21
|
+
|
22
|
+
typedef void (*mo_init)(void *dst);
|
23
|
+
typedef void (*mo_release)(void *dst);
|
24
|
+
typedef void (*mo_copy)(void *dst, void *src);
|
25
|
+
typedef int (*mo_cmp)(const void *a, const void *b);
|
26
|
+
typedef int (*mo_hash_func)(void *obj);
|
27
|
+
|
28
|
+
/**
|
29
|
+
* Dynamic array.
|
30
|
+
*/
|
31
|
+
|
32
|
+
typedef struct mo_array {
|
33
|
+
void *buffer;
|
34
|
+
size_t size;
|
35
|
+
size_t capa;
|
36
|
+
size_t el_size;
|
37
|
+
|
38
|
+
mo_init init;
|
39
|
+
mo_release release;
|
40
|
+
mo_copy copy;
|
41
|
+
} mo_array;
|
42
|
+
|
43
|
+
mo_array *mo_array_create(size_t el_size);
|
44
|
+
void mo_array_free(mo_array *ary);
|
45
|
+
|
46
|
+
void mo_array_init(mo_array *ary, size_t el_size);
|
47
|
+
void mo_array_release(mo_array *ary);
|
48
|
+
|
49
|
+
void *mo_array_quick_at(mo_array *ary, size_t i);
|
50
|
+
void *mo_array_at(mo_array *ary, size_t i);
|
51
|
+
|
52
|
+
#define mo_array_get_ptr(ary, i, type) ( (type*)mo_array_at(ary, i))
|
53
|
+
#define mo_array_get_as(ary, i, type) (*(type*)mo_array_at(ary, i))
|
54
|
+
|
55
|
+
void *mo_array_begin(mo_array *ary);
|
56
|
+
void *mo_array_end(mo_array *ary);
|
57
|
+
|
58
|
+
void mo_array_next(mo_array *ary, void **ptr);
|
59
|
+
|
60
|
+
void mo_array_set(mo_array *ary, size_t i, void *obj);
|
61
|
+
|
62
|
+
void mo_array_insert(mo_array *ary, size_t i, void *obj);
|
63
|
+
void mo_array_push(mo_array *ary, void *obj);
|
64
|
+
void mo_array_delete(mo_array *ary, size_t i);
|
65
|
+
|
66
|
+
mo_array mo_array_dup(mo_array *ary);
|
67
|
+
void mo_array_copy(mo_array *dst, mo_array *src);
|
68
|
+
|
69
|
+
mo_array *mo_array_qsort(mo_array *ary, mo_cmp cmp);
|
70
|
+
|
71
|
+
void mo_array_resize(mo_array *ary, size_t size);
|
72
|
+
void mo_array_reserve(mo_array *ary, size_t size);
|
73
|
+
void mo_array_shrink(mo_array *ary);
|
74
|
+
|
75
|
+
/**
|
76
|
+
* Doubly linked list.
|
77
|
+
*/
|
78
|
+
|
79
|
+
typedef struct mo_list {
|
80
|
+
struct mo_list *prev, *next;
|
81
|
+
|
82
|
+
mo_release release;
|
83
|
+
mo_copy copy;
|
84
|
+
|
85
|
+
size_t el_size;
|
86
|
+
uint8_t data[];
|
87
|
+
} mo_list;
|
88
|
+
|
89
|
+
mo_list *mo_list_create(size_t el_size);
|
90
|
+
void mo_list_free(mo_list *list);
|
91
|
+
|
92
|
+
mo_list *mo_list_prepend(mo_list *list, void *data);
|
93
|
+
mo_list *mo_list_insert(mo_list *list, void *data);
|
94
|
+
mo_list *mo_list_delete(mo_list *list);
|
95
|
+
|
96
|
+
void mo_list_set(mo_list *list, void *data);
|
97
|
+
|
98
|
+
#define mo_list_data_ptr(list, type) ( (type*)list->data)
|
99
|
+
#define mo_list_data_as(list, type) (*(type*)list->data)
|
100
|
+
|
101
|
+
/**
|
102
|
+
* Hash table.
|
103
|
+
*/
|
104
|
+
|
105
|
+
typedef struct mo_hash {
|
106
|
+
mo_array buffer;
|
107
|
+
|
108
|
+
mo_release release;
|
109
|
+
mo_copy copy;
|
110
|
+
|
111
|
+
mo_release key_release;
|
112
|
+
mo_copy key_copy;
|
113
|
+
mo_cmp key_cmp;
|
114
|
+
|
115
|
+
size_t size;
|
116
|
+
|
117
|
+
size_t el_size;
|
118
|
+
size_t key_size;
|
119
|
+
|
120
|
+
mo_hash_func hash_of;
|
121
|
+
} mo_hash;
|
122
|
+
|
123
|
+
typedef struct mo_hash_it {
|
124
|
+
mo_hash *hash;
|
125
|
+
mo_list *list;
|
126
|
+
size_t id;
|
127
|
+
} mo_hash_it;
|
128
|
+
|
129
|
+
int mo_hash_of_pointer(void *ptr);
|
130
|
+
int mo_hash_pointer_cmp(const void *a, const void *b);
|
131
|
+
|
132
|
+
int mo_hash_of_u32(void *ptr);
|
133
|
+
int mo_hash_u32_cmp(const void *a, const void *b);
|
134
|
+
|
135
|
+
int mo_hash_of_size(void *ptr);
|
136
|
+
int mo_hash_size_cmp(const void *a, const void *b);
|
137
|
+
|
138
|
+
mo_hash *mo_hash_create(size_t key_size, size_t el_size);
|
139
|
+
void mo_hash_free(mo_hash *hash);
|
140
|
+
|
141
|
+
bool mo_hash_has_key(mo_hash *hash, void *key);
|
142
|
+
|
143
|
+
void *mo_hash_get(mo_hash *hash, void *key);
|
144
|
+
void mo_hash_set(mo_hash *hash, void *key, void *data);
|
145
|
+
void mo_hash_del(mo_hash *hash, void *key);
|
146
|
+
|
147
|
+
#define mo_hash_get_ptr(hash, key, type) ( (type*)mo_hash_get(hash, key))
|
148
|
+
#define mo_hash_get_as(hash, key, type) (*(type*)mo_hash_get(hash, key))
|
149
|
+
|
150
|
+
mo_hash_it mo_hash_begin(mo_hash *hash);
|
151
|
+
|
152
|
+
bool mo_hash_it_is_end(mo_hash_it *it);
|
153
|
+
|
154
|
+
void *mo_hash_it_key(mo_hash_it *it);
|
155
|
+
void *mo_hash_it_val(mo_hash_it *it);
|
156
|
+
|
157
|
+
#define mo_hash_it_key_ptr(it, type) ( (type*)mo_hash_it_key(it))
|
158
|
+
#define mo_hash_it_key_as(it, type) (*(type*)mo_hash_it_key(it))
|
159
|
+
|
160
|
+
#define mo_hash_it_val_ptr(it, type) ( (type*)mo_hash_it_val(it))
|
161
|
+
#define mo_hash_it_val_as(it, type) (*(type*)mo_hash_it_val(it))
|
162
|
+
|
163
|
+
void mo_hash_it_next(mo_hash_it *it);
|
164
|
+
|
165
|
+
/**
|
166
|
+
* Set (macros atop a hash table).
|
167
|
+
*/
|
168
|
+
|
169
|
+
typedef mo_hash mo_set;
|
170
|
+
typedef mo_hash_it mo_set_it;
|
171
|
+
|
172
|
+
#define mo_set_create(size) mo_hash_create(size, 0)
|
173
|
+
#define mo_set_free(set) mo_hash_delete(set)
|
174
|
+
|
175
|
+
#define mo_set_includes(set) mo_hash_has_key(set)
|
176
|
+
|
177
|
+
#define mo_set_add(set, el) mo_hash_set(set, el, NULL)
|
178
|
+
#define mo_set_del(set, el) mo_hash_del(set, el)
|
179
|
+
|
180
|
+
#define mo_set_begin(set) mo_hash_begin(set)
|
181
|
+
|
182
|
+
#define mo_set_it_is_end(it) mo_hash_it_is_end(it)
|
183
|
+
#define mo_set_it_val(it) mo_hash_it_key(it)
|
184
|
+
#define mo_set_it_next(it) mo_hash_it_next(it)
|
185
|
+
|
186
|
+
#define mo_set_it_val_ptr(it, type) mo_hash_it_key_ptr(it, type)
|
187
|
+
#define mo_set_it_val_as(it, type) mo_hash_it_key_as(it, type)
|
188
|
+
|
189
|
+
#endif /* MY OWN HEADER'S GUARD! */
|
data/ext/music.c
CHANGED
@@ -21,9 +21,9 @@ VALUE ray_music_alloc(VALUE self) {
|
|
21
21
|
}
|
22
22
|
|
23
23
|
/*
|
24
|
-
|
25
|
-
|
26
|
-
*/
|
24
|
+
* @overload open(filename)
|
25
|
+
* @param [String] filename Name of the file containing the music to load.
|
26
|
+
*/
|
27
27
|
static
|
28
28
|
VALUE ray_music_open(VALUE self, VALUE arg) {
|
29
29
|
say_music *music = ray_rb2music(self);
|
@@ -48,10 +48,10 @@ VALUE ray_music_set_looping(VALUE self, VALUE val) {
|
|
48
48
|
}
|
49
49
|
|
50
50
|
/*
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
*/
|
51
|
+
* @overload seek(time)
|
52
|
+
* Seeks to a specific time in the music
|
53
|
+
* @param [Float] time Time in seconds
|
54
|
+
*/
|
55
55
|
static
|
56
56
|
VALUE ray_music_seek(VALUE self, VALUE time) {
|
57
57
|
say_music_seek(ray_rb2music(self), NUM2DBL(time));
|
@@ -64,7 +64,8 @@ VALUE ray_music_time(VALUE self) {
|
|
64
64
|
return rb_float_new(say_music_get_time(ray_rb2music(self)));
|
65
65
|
}
|
66
66
|
|
67
|
-
/*
|
67
|
+
/*
|
68
|
+
* @return [Float] Duration of the music. 0 when no buffer is attached to the
|
68
69
|
* music.
|
69
70
|
*/
|
70
71
|
static
|
data/ext/pixel_bus.c
ADDED
@@ -0,0 +1,349 @@
|
|
1
|
+
#include "ray.h"
|
2
|
+
|
3
|
+
VALUE ray_cPixelBus = Qnil;
|
4
|
+
|
5
|
+
say_pixel_bus *ray_rb2pixel_bus(VALUE obj) {
|
6
|
+
if (!rb_obj_is_kind_of(obj, rb_path2class("Ray::PixelBus"))) {
|
7
|
+
rb_raise(rb_eTypeError, "can't convert %s into Ray::PixelBus",
|
8
|
+
RAY_OBJ_CLASSNAME(obj));
|
9
|
+
}
|
10
|
+
|
11
|
+
say_pixel_bus **ptr = NULL;
|
12
|
+
Data_Get_Struct(obj, say_pixel_bus*, ptr);
|
13
|
+
|
14
|
+
if (!*ptr)
|
15
|
+
rb_raise(rb_eRuntimeError, "trying to use uninitialized pixel bus");
|
16
|
+
|
17
|
+
return *ptr;
|
18
|
+
}
|
19
|
+
|
20
|
+
static
|
21
|
+
void ray_pixel_bus_free(say_pixel_bus **ptr) {
|
22
|
+
if (*ptr) say_pixel_bus_free(*ptr);
|
23
|
+
}
|
24
|
+
|
25
|
+
static
|
26
|
+
VALUE ray_pixel_bus_alloc(VALUE self) {
|
27
|
+
say_pixel_bus **obj = malloc(sizeof(say_pixel_bus*));
|
28
|
+
*obj = NULL;
|
29
|
+
|
30
|
+
return Data_Wrap_Struct(self, NULL, ray_pixel_bus_free, obj);
|
31
|
+
}
|
32
|
+
|
33
|
+
/*
|
34
|
+
* @overload initialize(type = :stream)
|
35
|
+
* @param type (see Ray::BufferRenderer#initialize)
|
36
|
+
*/
|
37
|
+
static
|
38
|
+
VALUE ray_pixel_bus_init(int argc, VALUE *argv, VALUE self) {
|
39
|
+
if (!say_pixel_bus_is_available())
|
40
|
+
rb_raise(rb_eRuntimeError, "pixel buses aren't available on this platform");
|
41
|
+
|
42
|
+
GLenum mode = SAY_STREAM;
|
43
|
+
|
44
|
+
VALUE rb_mode = Qnil;
|
45
|
+
rb_scan_args(argc, argv, "01", &rb_mode);
|
46
|
+
|
47
|
+
if (!NIL_P(rb_mode)) mode = ray_buf_type(rb_mode);
|
48
|
+
|
49
|
+
say_pixel_bus **ptr = NULL;
|
50
|
+
Data_Get_Struct(self, say_pixel_bus*, ptr);
|
51
|
+
|
52
|
+
*ptr = say_pixel_bus_create(mode);
|
53
|
+
|
54
|
+
return self;
|
55
|
+
}
|
56
|
+
|
57
|
+
/*
|
58
|
+
* @return [Boolean] True if pixel buses are available on this platform
|
59
|
+
*/
|
60
|
+
static
|
61
|
+
VALUE ray_pixel_bus_available(VALUE self) {
|
62
|
+
return say_pixel_bus_is_available() ? Qtrue : Qfalse;
|
63
|
+
}
|
64
|
+
|
65
|
+
/*
|
66
|
+
* @return [Integer] The capacity of the pixel bus, in pixels
|
67
|
+
*/
|
68
|
+
static
|
69
|
+
VALUE ray_pixel_bus_size(VALUE self) {
|
70
|
+
return ULONG2NUM(say_pixel_bus_get_size(ray_rb2pixel_bus(self)));
|
71
|
+
}
|
72
|
+
|
73
|
+
/*
|
74
|
+
* @overload resize(new_size)
|
75
|
+
* Changes the capacity of the buffer
|
76
|
+
*
|
77
|
+
* This method needs to copy the buffers content onto client memory, and is
|
78
|
+
* thus signinficantly slower than {#resize!}. It should not be called if the
|
79
|
+
* current content of the buffer doesn't need to be read anymore.
|
80
|
+
*
|
81
|
+
* @param [Integer] new_size New capacity of the buffer
|
82
|
+
* @see PixelBus#resize!
|
83
|
+
*/
|
84
|
+
static
|
85
|
+
VALUE ray_pixel_bus_resize(VALUE self, VALUE size) {
|
86
|
+
say_pixel_bus_resize(ray_rb2pixel_bus(self), NUM2ULONG(size));
|
87
|
+
return self;
|
88
|
+
}
|
89
|
+
|
90
|
+
/*
|
91
|
+
* @overload resize!(new_size)
|
92
|
+
* Changes the capacity of the buffer without preserving content
|
93
|
+
*
|
94
|
+
* This method allows to quickly resize the buffer used by the pixel bus. The
|
95
|
+
* content of the buffer is however undefined after this call.
|
96
|
+
*
|
97
|
+
* @param new_size (see #resize)
|
98
|
+
* @see PixelBus#resize
|
99
|
+
*/
|
100
|
+
static
|
101
|
+
VALUE ray_pixel_bus_resize_fast(VALUE self, VALUE size) {
|
102
|
+
say_pixel_bus_resize_fast(ray_rb2pixel_bus(self), NUM2ULONG(size));
|
103
|
+
return self;
|
104
|
+
}
|
105
|
+
|
106
|
+
/*
|
107
|
+
* @overload pull(object, opts = {})
|
108
|
+
* Pulls data from an object
|
109
|
+
*
|
110
|
+
* This method reads a rectangle from an image on a target and stores it in
|
111
|
+
* the buffer, at a given offset. A rect can optionally be specified for
|
112
|
+
* targets. Otherwise, the whole object will be copied.
|
113
|
+
*
|
114
|
+
* @param [Ray::Image, Ray::Target] object Object to read pixels from
|
115
|
+
* @option opts [Integer] :offset (0) Offset from the buffer
|
116
|
+
* @option opts [Ray::Rect, nil] :rect Rect of pixels to read for targets
|
117
|
+
*
|
118
|
+
* @raise [RangeError] If this method attempts to write outside of the buffer
|
119
|
+
* boundaries.
|
120
|
+
*
|
121
|
+
* @return [Integer] Offset of the last read element, plus one.
|
122
|
+
*/
|
123
|
+
static
|
124
|
+
VALUE ray_pixel_bus_pull(int argc, VALUE *argv, VALUE self) {
|
125
|
+
say_pixel_bus *bus = ray_rb2pixel_bus(self);
|
126
|
+
|
127
|
+
VALUE object, opts = Qnil;
|
128
|
+
rb_scan_args(argc, argv, "11", &object, &opts);
|
129
|
+
|
130
|
+
say_rect rect = say_make_rect(0, 0, 0, 0);
|
131
|
+
size_t offset = 0;
|
132
|
+
|
133
|
+
say_target *target = NULL;
|
134
|
+
say_image *image = NULL;
|
135
|
+
|
136
|
+
if (RAY_IS_A(object, rb_path2class("Ray::Target")))
|
137
|
+
target = ray_rb2target(object);
|
138
|
+
else
|
139
|
+
image = ray_rb2image(object);
|
140
|
+
|
141
|
+
say_vector2 size;
|
142
|
+
|
143
|
+
if (target)
|
144
|
+
size = say_target_get_size(target);
|
145
|
+
else
|
146
|
+
size = say_image_get_size(image);
|
147
|
+
|
148
|
+
if (!NIL_P(opts)) {
|
149
|
+
if (!RAY_IS_A(opts, rb_cHash)) {
|
150
|
+
rb_raise(rb_eTypeError, "can't convert %s into Hash",
|
151
|
+
RAY_OBJ_CLASSNAME(opts));
|
152
|
+
}
|
153
|
+
|
154
|
+
VALUE rb_rect = rb_hash_aref(opts, RAY_SYM("rect"));
|
155
|
+
VALUE rb_offset = rb_hash_aref(opts, RAY_SYM("offset"));
|
156
|
+
|
157
|
+
if (target) {
|
158
|
+
if (!NIL_P(rb_rect))
|
159
|
+
rect = ray_convert_to_rect(rb_rect);
|
160
|
+
else
|
161
|
+
rect = say_make_rect(0, 0, size.x, size.y);
|
162
|
+
}
|
163
|
+
|
164
|
+
if (!NIL_P(rb_offset))
|
165
|
+
offset = NUM2ULONG(rb_offset);
|
166
|
+
}
|
167
|
+
else if (target) {
|
168
|
+
say_vector2 size = say_target_get_size(target);
|
169
|
+
rect = say_make_rect(0, 0, size.x, size.y);
|
170
|
+
}
|
171
|
+
|
172
|
+
size_t ret = offset + (size_t)size.x * (size_t)size.y;
|
173
|
+
if (ret > say_pixel_bus_get_size(bus))
|
174
|
+
rb_raise(rb_eRangeError, "trying to write outside of buffer boundaries");
|
175
|
+
|
176
|
+
if (target) {
|
177
|
+
say_pixel_bus_pull_target(bus, target, offset,
|
178
|
+
rect.x, rect.y, rect.w, rect.h);
|
179
|
+
}
|
180
|
+
else {
|
181
|
+
say_pixel_bus_pull_image(bus, image, offset);
|
182
|
+
}
|
183
|
+
|
184
|
+
return ULONG2NUM(ret);
|
185
|
+
}
|
186
|
+
|
187
|
+
/*
|
188
|
+
* @overload push(image, opts = {})
|
189
|
+
* Pushes data from the buffer onto an image
|
190
|
+
*
|
191
|
+
* This method reads pixels from the buffer at a given offset, and copies them
|
192
|
+
* onto an image. A rect of pixels that must be replaced can be
|
193
|
+
* specifed. Otherwise, the whole texture will be replaced.
|
194
|
+
*
|
195
|
+
* @param [Ray::Image] image Image to copy the rect to
|
196
|
+
* @option opts :offset (see #pull)
|
197
|
+
* @option opts [Ray::Rect] :rect Rect of pixels to replace in the image
|
198
|
+
*
|
199
|
+
* @return [Ray::PixelBus] self
|
200
|
+
*
|
201
|
+
* @raise [RangeError] If this method tries to read pixels outside of the
|
202
|
+
* buffer boundaries or to write oustide of the image boundaries.
|
203
|
+
*/
|
204
|
+
static
|
205
|
+
VALUE ray_pixel_bus_push(int argc, VALUE *argv, VALUE self) {
|
206
|
+
say_pixel_bus *bus = ray_rb2pixel_bus(self);
|
207
|
+
|
208
|
+
VALUE object, opts = Qnil;
|
209
|
+
rb_scan_args(argc, argv, "11", &object, &opts);
|
210
|
+
|
211
|
+
say_image *image = ray_rb2image(object);
|
212
|
+
|
213
|
+
say_vector2 size = say_image_get_size(image);
|
214
|
+
|
215
|
+
size_t offset = 0;
|
216
|
+
say_rect rect = say_make_rect(0, 0, size.x, size.y);
|
217
|
+
|
218
|
+
if (!NIL_P(opts)) {
|
219
|
+
if (!RAY_IS_A(opts, rb_cHash)) {
|
220
|
+
rb_raise(rb_eTypeError, "can't convert %s into Hash",
|
221
|
+
RAY_OBJ_CLASSNAME(opts));
|
222
|
+
}
|
223
|
+
|
224
|
+
VALUE rb_rect = rb_hash_aref(opts, RAY_SYM("rect"));
|
225
|
+
VALUE rb_offset = rb_hash_aref(opts, RAY_SYM("offset"));
|
226
|
+
|
227
|
+
if (!NIL_P(rb_rect))
|
228
|
+
rect = ray_convert_to_rect(rb_rect);
|
229
|
+
|
230
|
+
if (!NIL_P(rb_offset))
|
231
|
+
offset = NUM2ULONG(rb_offset);
|
232
|
+
}
|
233
|
+
|
234
|
+
size_t ret = offset + ((size_t)rect.w * (size_t)rect.h);
|
235
|
+
if (ret > say_pixel_bus_get_size(bus))
|
236
|
+
rb_raise(rb_eRangeError, "trying to read outside of pixel bus boundaries");
|
237
|
+
|
238
|
+
if (rect.x + rect.w > size.x || rect.y + rect.h > size.y)
|
239
|
+
rb_raise(rb_eRangeError, "trying to write outsied of image boundaries");
|
240
|
+
|
241
|
+
say_pixel_bus_push_image(bus, image, offset, rect.x, rect.y, rect.w, rect.h);
|
242
|
+
return self;
|
243
|
+
}
|
244
|
+
|
245
|
+
/*
|
246
|
+
* Binds the pixel bus for packing and unpacking
|
247
|
+
*/
|
248
|
+
static
|
249
|
+
VALUE ray_pixel_bus_bind(VALUE self) {
|
250
|
+
say_pixel_bus_bind(ray_rb2pixel_bus(self));
|
251
|
+
return self;
|
252
|
+
}
|
253
|
+
|
254
|
+
/*
|
255
|
+
* Binds the pixel bus for packing
|
256
|
+
*/
|
257
|
+
static
|
258
|
+
VALUE ray_pixel_bus_bind_pack(VALUE self) {
|
259
|
+
say_pixel_bus_bind_pack(ray_rb2pixel_bus(self));
|
260
|
+
return self;
|
261
|
+
}
|
262
|
+
|
263
|
+
/*
|
264
|
+
* Binds the pixel bus for unpacking
|
265
|
+
*/
|
266
|
+
static
|
267
|
+
VALUE ray_pixel_bus_bind_unpack(VALUE self) {
|
268
|
+
say_pixel_bus_bind_unpack(ray_rb2pixel_bus(self));
|
269
|
+
return self;
|
270
|
+
}
|
271
|
+
|
272
|
+
/*
|
273
|
+
* Unbinds any pixel bus bound for either packing or unpacking
|
274
|
+
*/
|
275
|
+
static
|
276
|
+
VALUE ray_pixel_bus_unbind(VALUE self) {
|
277
|
+
say_pixel_bus_unbind();
|
278
|
+
return Qnil;
|
279
|
+
}
|
280
|
+
|
281
|
+
/*
|
282
|
+
* Unbinds any pixel bus bound for packing
|
283
|
+
*/
|
284
|
+
static
|
285
|
+
VALUE ray_pixel_bus_unbind_pack(VALUE self) {
|
286
|
+
say_pixel_bus_unbind_pack();
|
287
|
+
return Qnil;
|
288
|
+
}
|
289
|
+
|
290
|
+
/*
|
291
|
+
* Unbinds any pixel bus bound for unpacking
|
292
|
+
*/
|
293
|
+
static
|
294
|
+
VALUE ray_pixel_bus_unbind_unpack(VALUE self) {
|
295
|
+
say_pixel_bus_unbind_unpack();
|
296
|
+
return Qnil;
|
297
|
+
}
|
298
|
+
|
299
|
+
/*
|
300
|
+
* @return [Integer] The identifier of the OpenGL buffer used by the PixelBus.
|
301
|
+
*/
|
302
|
+
static
|
303
|
+
VALUE ray_pixel_bus_pbo(VALUE self) {
|
304
|
+
return ULONG2NUM(say_pixel_bus_get_pbo(ray_rb2pixel_bus(self)));
|
305
|
+
}
|
306
|
+
|
307
|
+
/*
|
308
|
+
* Document-class: Ray::PixelBus
|
309
|
+
*
|
310
|
+
* Pixel buses are a way to copy pixels from a target or an image onto an image
|
311
|
+
* without having to copy them to client memory, and possibly
|
312
|
+
* asynchronously. They may unfortunately not be available on some platforms.
|
313
|
+
*
|
314
|
+
* Notice that pixels are stored from bottom to top in the buffer. You may have
|
315
|
+
* to rely on this when computing offsets manually.
|
316
|
+
*/
|
317
|
+
void Init_ray_pixel_bus() {
|
318
|
+
ray_cPixelBus = rb_define_class_under(ray_mRay, "PixelBus", rb_cObject);
|
319
|
+
|
320
|
+
rb_define_alloc_func(ray_cPixelBus, ray_pixel_bus_alloc);
|
321
|
+
rb_define_method(ray_cPixelBus, "initialize", ray_pixel_bus_init, -1);
|
322
|
+
|
323
|
+
rb_define_singleton_method(ray_cPixelBus, "available?",
|
324
|
+
ray_pixel_bus_available, 0);
|
325
|
+
|
326
|
+
/* @group Manipulating buffer size */
|
327
|
+
rb_define_method(ray_cPixelBus, "size", ray_pixel_bus_size, 0);
|
328
|
+
rb_define_method(ray_cPixelBus, "resize", ray_pixel_bus_resize, 1);
|
329
|
+
rb_define_method(ray_cPixelBus, "resize!", ray_pixel_bus_resize_fast, 1);
|
330
|
+
/* @endgroup */
|
331
|
+
|
332
|
+
/* @group Copying data */
|
333
|
+
rb_define_method(ray_cPixelBus, "pull", ray_pixel_bus_pull, -1);
|
334
|
+
rb_define_method(ray_cPixelBus, "push", ray_pixel_bus_push, -1);
|
335
|
+
/* @endgroup */
|
336
|
+
|
337
|
+
/* @group OpenGL access */
|
338
|
+
rb_define_method(ray_cPixelBus, "bind", ray_pixel_bus_bind, 0);
|
339
|
+
rb_define_method(ray_cPixelBus, "bind_pack", ray_pixel_bus_bind_pack, 0);
|
340
|
+
rb_define_method(ray_cPixelBus, "bind_unpack", ray_pixel_bus_bind_unpack, 0);
|
341
|
+
rb_define_method(ray_cPixelBus, "pbo", ray_pixel_bus_pbo, 0);
|
342
|
+
|
343
|
+
rb_define_singleton_method(ray_cPixelBus, "unbind", ray_pixel_bus_unbind, 0);
|
344
|
+
rb_define_singleton_method(ray_cPixelBus, "unbind_pack",
|
345
|
+
ray_pixel_bus_unbind_pack, 0);
|
346
|
+
rb_define_singleton_method(ray_cPixelBus, "unbind_unpack",
|
347
|
+
ray_pixel_bus_unbind_unpack, 0);
|
348
|
+
/* @endgroup */
|
349
|
+
}
|