bevy 1.0.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 (93) hide show
  1. checksums.yaml +7 -0
  2. data/Cargo.lock +4279 -0
  3. data/Cargo.toml +36 -0
  4. data/README.md +226 -0
  5. data/crates/bevy/Cargo.toml +52 -0
  6. data/crates/bevy/src/app.rs +43 -0
  7. data/crates/bevy/src/component.rs +111 -0
  8. data/crates/bevy/src/entity.rs +30 -0
  9. data/crates/bevy/src/error.rs +32 -0
  10. data/crates/bevy/src/event.rs +190 -0
  11. data/crates/bevy/src/input_bridge.rs +300 -0
  12. data/crates/bevy/src/lib.rs +42 -0
  13. data/crates/bevy/src/mesh_renderer.rs +328 -0
  14. data/crates/bevy/src/query.rs +53 -0
  15. data/crates/bevy/src/render_app.rs +689 -0
  16. data/crates/bevy/src/resource.rs +28 -0
  17. data/crates/bevy/src/schedule.rs +186 -0
  18. data/crates/bevy/src/sprite_renderer.rs +355 -0
  19. data/crates/bevy/src/system.rs +44 -0
  20. data/crates/bevy/src/text_renderer.rs +258 -0
  21. data/crates/bevy/src/types/color.rs +114 -0
  22. data/crates/bevy/src/types/dynamic.rs +131 -0
  23. data/crates/bevy/src/types/math.rs +260 -0
  24. data/crates/bevy/src/types/mod.rs +9 -0
  25. data/crates/bevy/src/types/transform.rs +166 -0
  26. data/crates/bevy/src/world.rs +163 -0
  27. data/crates/bevy_ruby_render/Cargo.toml +22 -0
  28. data/crates/bevy_ruby_render/src/asset.rs +360 -0
  29. data/crates/bevy_ruby_render/src/audio.rs +511 -0
  30. data/crates/bevy_ruby_render/src/camera.rs +365 -0
  31. data/crates/bevy_ruby_render/src/gamepad.rs +398 -0
  32. data/crates/bevy_ruby_render/src/lib.rs +26 -0
  33. data/crates/bevy_ruby_render/src/material.rs +310 -0
  34. data/crates/bevy_ruby_render/src/mesh.rs +491 -0
  35. data/crates/bevy_ruby_render/src/sprite.rs +289 -0
  36. data/ext/bevy/Cargo.toml +20 -0
  37. data/ext/bevy/extconf.rb +6 -0
  38. data/ext/bevy/src/conversions.rs +137 -0
  39. data/ext/bevy/src/lib.rs +29 -0
  40. data/ext/bevy/src/ruby_app.rs +65 -0
  41. data/ext/bevy/src/ruby_color.rs +149 -0
  42. data/ext/bevy/src/ruby_component.rs +189 -0
  43. data/ext/bevy/src/ruby_entity.rs +33 -0
  44. data/ext/bevy/src/ruby_math.rs +384 -0
  45. data/ext/bevy/src/ruby_query.rs +64 -0
  46. data/ext/bevy/src/ruby_render_app.rs +779 -0
  47. data/ext/bevy/src/ruby_system.rs +122 -0
  48. data/ext/bevy/src/ruby_world.rs +107 -0
  49. data/lib/bevy/animation.rb +597 -0
  50. data/lib/bevy/app.rb +675 -0
  51. data/lib/bevy/asset.rb +613 -0
  52. data/lib/bevy/audio.rb +545 -0
  53. data/lib/bevy/audio_effects.rb +224 -0
  54. data/lib/bevy/camera.rb +412 -0
  55. data/lib/bevy/component.rb +91 -0
  56. data/lib/bevy/diagnostics.rb +227 -0
  57. data/lib/bevy/ecs_advanced.rb +296 -0
  58. data/lib/bevy/event.rb +199 -0
  59. data/lib/bevy/gizmos.rb +158 -0
  60. data/lib/bevy/gltf.rb +227 -0
  61. data/lib/bevy/hierarchy.rb +444 -0
  62. data/lib/bevy/input.rb +514 -0
  63. data/lib/bevy/lighting.rb +369 -0
  64. data/lib/bevy/material.rb +248 -0
  65. data/lib/bevy/mesh.rb +257 -0
  66. data/lib/bevy/navigation.rb +344 -0
  67. data/lib/bevy/networking.rb +335 -0
  68. data/lib/bevy/particle.rb +337 -0
  69. data/lib/bevy/physics.rb +396 -0
  70. data/lib/bevy/plugins/default_plugins.rb +34 -0
  71. data/lib/bevy/plugins/input_plugin.rb +49 -0
  72. data/lib/bevy/reflect.rb +361 -0
  73. data/lib/bevy/render_graph.rb +210 -0
  74. data/lib/bevy/resource.rb +185 -0
  75. data/lib/bevy/scene.rb +254 -0
  76. data/lib/bevy/shader.rb +319 -0
  77. data/lib/bevy/shape.rb +195 -0
  78. data/lib/bevy/skeletal.rb +248 -0
  79. data/lib/bevy/sprite.rb +152 -0
  80. data/lib/bevy/sprite_sheet.rb +444 -0
  81. data/lib/bevy/state.rb +277 -0
  82. data/lib/bevy/system.rb +206 -0
  83. data/lib/bevy/text.rb +99 -0
  84. data/lib/bevy/text_advanced.rb +455 -0
  85. data/lib/bevy/timer.rb +147 -0
  86. data/lib/bevy/transform.rb +158 -0
  87. data/lib/bevy/ui.rb +454 -0
  88. data/lib/bevy/ui_advanced.rb +568 -0
  89. data/lib/bevy/version.rb +5 -0
  90. data/lib/bevy/visibility.rb +250 -0
  91. data/lib/bevy/window.rb +302 -0
  92. data/lib/bevy.rb +390 -0
  93. metadata +150 -0
@@ -0,0 +1,258 @@
1
+ //! Text renderer module for synchronizing Ruby text entities with Bevy.
2
+
3
+ use std::collections::HashMap;
4
+
5
+ #[cfg(feature = "rendering")]
6
+ use bevy_color::Color;
7
+ #[cfg(feature = "rendering")]
8
+ use bevy_ecs::entity::Entity;
9
+ #[cfg(feature = "rendering")]
10
+ use bevy_ecs::world::World;
11
+ #[cfg(feature = "rendering")]
12
+ use bevy_render::view::{InheritedVisibility, ViewVisibility, Visibility};
13
+ #[cfg(feature = "rendering")]
14
+ use bevy_text::{Text2d, TextColor, TextFont};
15
+ #[cfg(feature = "rendering")]
16
+ use bevy_transform::components::{GlobalTransform, Transform};
17
+
18
+ #[derive(Debug, Clone)]
19
+ pub struct TextData {
20
+ pub content: String,
21
+ pub font_size: f32,
22
+ pub color_r: f32,
23
+ pub color_g: f32,
24
+ pub color_b: f32,
25
+ pub color_a: f32,
26
+ }
27
+
28
+ impl Default for TextData {
29
+ fn default() -> Self {
30
+ Self {
31
+ content: String::new(),
32
+ font_size: 24.0,
33
+ color_r: 1.0,
34
+ color_g: 1.0,
35
+ color_b: 1.0,
36
+ color_a: 1.0,
37
+ }
38
+ }
39
+ }
40
+
41
+ #[derive(Debug, Clone)]
42
+ pub struct TextTransformData {
43
+ pub translation_x: f32,
44
+ pub translation_y: f32,
45
+ pub translation_z: f32,
46
+ pub scale_x: f32,
47
+ pub scale_y: f32,
48
+ pub scale_z: f32,
49
+ }
50
+
51
+ impl Default for TextTransformData {
52
+ fn default() -> Self {
53
+ Self {
54
+ translation_x: 0.0,
55
+ translation_y: 0.0,
56
+ translation_z: 0.0,
57
+ scale_x: 1.0,
58
+ scale_y: 1.0,
59
+ scale_z: 1.0,
60
+ }
61
+ }
62
+ }
63
+
64
+ #[derive(Debug, Clone)]
65
+ pub enum TextOperation {
66
+ Sync {
67
+ ruby_entity_id: u64,
68
+ text_data: TextData,
69
+ transform_data: TextTransformData,
70
+ },
71
+ Remove {
72
+ ruby_entity_id: u64,
73
+ },
74
+ Clear,
75
+ }
76
+
77
+ pub struct TextSync {
78
+ entity_map: HashMap<u64, TextEntityData>,
79
+ pub pending_operations: Vec<TextOperation>,
80
+ }
81
+
82
+ struct TextEntityData {
83
+ #[cfg(feature = "rendering")]
84
+ bevy_entity: Entity,
85
+ #[cfg(not(feature = "rendering"))]
86
+ _phantom: (),
87
+ }
88
+
89
+ impl TextSync {
90
+ pub fn new() -> Self {
91
+ Self {
92
+ entity_map: HashMap::new(),
93
+ pending_operations: Vec::new(),
94
+ }
95
+ }
96
+
97
+ pub fn sync_text_standalone(
98
+ &mut self,
99
+ ruby_entity_id: u64,
100
+ text_data: &TextData,
101
+ transform_data: &TextTransformData,
102
+ ) {
103
+ self.pending_operations.push(TextOperation::Sync {
104
+ ruby_entity_id,
105
+ text_data: text_data.clone(),
106
+ transform_data: transform_data.clone(),
107
+ });
108
+ }
109
+
110
+ pub fn remove_text_standalone(&mut self, ruby_entity_id: u64) {
111
+ self.pending_operations
112
+ .push(TextOperation::Remove { ruby_entity_id });
113
+ }
114
+
115
+ pub fn clear_standalone(&mut self) {
116
+ self.pending_operations.push(TextOperation::Clear);
117
+ }
118
+
119
+ #[cfg(feature = "rendering")]
120
+ pub fn apply_pending(&mut self, world: &mut World) {
121
+ let ops: Vec<_> = self.pending_operations.drain(..).collect();
122
+ for op in ops {
123
+ match op {
124
+ TextOperation::Sync {
125
+ ruby_entity_id,
126
+ text_data,
127
+ transform_data,
128
+ } => {
129
+ self.sync_text(world, ruby_entity_id, &text_data, &transform_data);
130
+ }
131
+ TextOperation::Remove { ruby_entity_id } => {
132
+ self.remove_text(world, ruby_entity_id);
133
+ }
134
+ TextOperation::Clear => {
135
+ self.clear(world);
136
+ }
137
+ }
138
+ }
139
+ }
140
+
141
+ #[cfg(not(feature = "rendering"))]
142
+ pub fn apply_pending(&mut self, _world: &mut ()) {
143
+ self.pending_operations.clear();
144
+ }
145
+
146
+ #[cfg(feature = "rendering")]
147
+ pub fn sync_text(
148
+ &mut self,
149
+ world: &mut World,
150
+ ruby_entity_id: u64,
151
+ text_data: &TextData,
152
+ transform_data: &TextTransformData,
153
+ ) {
154
+ let color = Color::srgba(
155
+ text_data.color_r,
156
+ text_data.color_g,
157
+ text_data.color_b,
158
+ text_data.color_a,
159
+ );
160
+
161
+ let transform = Transform {
162
+ translation: bevy_math::Vec3::new(
163
+ transform_data.translation_x,
164
+ transform_data.translation_y,
165
+ transform_data.translation_z,
166
+ ),
167
+ rotation: bevy_math::Quat::IDENTITY,
168
+ scale: bevy_math::Vec3::new(
169
+ transform_data.scale_x,
170
+ transform_data.scale_y,
171
+ transform_data.scale_z,
172
+ ),
173
+ };
174
+
175
+ if let Some(entity_data) = self.entity_map.get(&ruby_entity_id) {
176
+ let bevy_entity = entity_data.bevy_entity;
177
+
178
+ if let Some(mut text) = world.get_mut::<Text2d>(bevy_entity) {
179
+ **text = text_data.content.clone();
180
+ }
181
+
182
+ if let Some(mut text_color) = world.get_mut::<TextColor>(bevy_entity) {
183
+ text_color.0 = color;
184
+ }
185
+
186
+ if let Some(mut font) = world.get_mut::<TextFont>(bevy_entity) {
187
+ font.font_size = text_data.font_size;
188
+ }
189
+
190
+ if let Some(mut t) = world.get_mut::<Transform>(bevy_entity) {
191
+ *t = transform;
192
+ }
193
+ } else {
194
+ let bevy_entity = world
195
+ .spawn((
196
+ Text2d::new(text_data.content.clone()),
197
+ TextFont {
198
+ font_size: text_data.font_size,
199
+ ..Default::default()
200
+ },
201
+ TextColor(color),
202
+ transform,
203
+ GlobalTransform::default(),
204
+ Visibility::default(),
205
+ InheritedVisibility::default(),
206
+ ViewVisibility::default(),
207
+ ))
208
+ .id();
209
+
210
+ self.entity_map
211
+ .insert(ruby_entity_id, TextEntityData { bevy_entity });
212
+ }
213
+ }
214
+
215
+ #[cfg(feature = "rendering")]
216
+ pub fn remove_text(&mut self, world: &mut World, ruby_entity_id: u64) {
217
+ if let Some(entity_data) = self.entity_map.remove(&ruby_entity_id) {
218
+ world.despawn(entity_data.bevy_entity);
219
+ }
220
+ }
221
+
222
+ #[cfg(feature = "rendering")]
223
+ pub fn clear(&mut self, world: &mut World) {
224
+ for (_, entity_data) in self.entity_map.drain() {
225
+ world.despawn(entity_data.bevy_entity);
226
+ }
227
+ }
228
+
229
+ pub fn len(&self) -> usize {
230
+ self.entity_map.len()
231
+ }
232
+
233
+ pub fn is_empty(&self) -> bool {
234
+ self.entity_map.is_empty()
235
+ }
236
+
237
+ #[cfg(not(feature = "rendering"))]
238
+ pub fn sync_text(
239
+ &mut self,
240
+ _world: &mut (),
241
+ _ruby_entity_id: u64,
242
+ _text_data: &TextData,
243
+ _transform_data: &TextTransformData,
244
+ ) {
245
+ }
246
+
247
+ #[cfg(not(feature = "rendering"))]
248
+ pub fn remove_text(&mut self, _world: &mut (), _ruby_entity_id: u64) {}
249
+
250
+ #[cfg(not(feature = "rendering"))]
251
+ pub fn clear(&mut self, _world: &mut ()) {}
252
+ }
253
+
254
+ impl Default for TextSync {
255
+ fn default() -> Self {
256
+ Self::new()
257
+ }
258
+ }
@@ -0,0 +1,114 @@
1
+ use bevy_color::{Alpha, Color, Srgba};
2
+
3
+ #[derive(Debug, Clone, Copy)]
4
+ pub struct RubyColor {
5
+ inner: Srgba,
6
+ }
7
+
8
+ impl RubyColor {
9
+ pub fn new(r: f32, g: f32, b: f32, a: f32) -> Self {
10
+ Self {
11
+ inner: Srgba::new(r, g, b, a),
12
+ }
13
+ }
14
+
15
+ pub fn rgb(r: f32, g: f32, b: f32) -> Self {
16
+ Self::new(r, g, b, 1.0)
17
+ }
18
+
19
+ pub fn rgba(r: f32, g: f32, b: f32, a: f32) -> Self {
20
+ Self::new(r, g, b, a)
21
+ }
22
+
23
+ pub fn from_hex(hex: &str) -> Option<Self> {
24
+ Srgba::hex(hex).ok().map(|c| Self { inner: c })
25
+ }
26
+
27
+ pub fn white() -> Self {
28
+ Self::new(1.0, 1.0, 1.0, 1.0)
29
+ }
30
+
31
+ pub fn black() -> Self {
32
+ Self::new(0.0, 0.0, 0.0, 1.0)
33
+ }
34
+
35
+ pub fn red() -> Self {
36
+ Self::new(1.0, 0.0, 0.0, 1.0)
37
+ }
38
+
39
+ pub fn green() -> Self {
40
+ Self::new(0.0, 1.0, 0.0, 1.0)
41
+ }
42
+
43
+ pub fn blue() -> Self {
44
+ Self::new(0.0, 0.0, 1.0, 1.0)
45
+ }
46
+
47
+ pub fn transparent() -> Self {
48
+ Self::new(0.0, 0.0, 0.0, 0.0)
49
+ }
50
+
51
+ pub fn r(&self) -> f32 {
52
+ self.inner.red
53
+ }
54
+
55
+ pub fn g(&self) -> f32 {
56
+ self.inner.green
57
+ }
58
+
59
+ pub fn b(&self) -> f32 {
60
+ self.inner.blue
61
+ }
62
+
63
+ pub fn a(&self) -> f32 {
64
+ self.inner.alpha
65
+ }
66
+
67
+ pub fn set_r(&mut self, r: f32) {
68
+ self.inner.red = r;
69
+ }
70
+
71
+ pub fn set_g(&mut self, g: f32) {
72
+ self.inner.green = g;
73
+ }
74
+
75
+ pub fn set_b(&mut self, b: f32) {
76
+ self.inner.blue = b;
77
+ }
78
+
79
+ pub fn set_a(&mut self, a: f32) {
80
+ self.inner.alpha = a;
81
+ }
82
+
83
+ pub fn with_alpha(&self, alpha: f32) -> Self {
84
+ Self {
85
+ inner: self.inner.with_alpha(alpha),
86
+ }
87
+ }
88
+
89
+ pub fn to_bevy(&self) -> Color {
90
+ Color::Srgba(self.inner)
91
+ }
92
+
93
+ pub fn to_srgba(&self) -> Srgba {
94
+ self.inner
95
+ }
96
+
97
+ pub fn to_array(&self) -> [f32; 4] {
98
+ [self.inner.red, self.inner.green, self.inner.blue, self.inner.alpha]
99
+ }
100
+ }
101
+
102
+ impl From<Srgba> for RubyColor {
103
+ fn from(color: Srgba) -> Self {
104
+ Self { inner: color }
105
+ }
106
+ }
107
+
108
+ impl From<Color> for RubyColor {
109
+ fn from(color: Color) -> Self {
110
+ Self {
111
+ inner: color.to_srgba(),
112
+ }
113
+ }
114
+ }
@@ -0,0 +1,131 @@
1
+ use bevy_ecs::component::Component;
2
+ use std::collections::HashMap;
3
+
4
+ #[derive(Debug, Clone, PartialEq)]
5
+ pub enum DynamicValue {
6
+ Nil,
7
+ Boolean(bool),
8
+ Integer(i64),
9
+ Float(f64),
10
+ String(String),
11
+ Symbol(String),
12
+ Array(Vec<DynamicValue>),
13
+ Hash(HashMap<String, DynamicValue>),
14
+ }
15
+
16
+ impl DynamicValue {
17
+ pub fn as_bool(&self) -> Option<bool> {
18
+ match self {
19
+ DynamicValue::Boolean(v) => Some(*v),
20
+ _ => None,
21
+ }
22
+ }
23
+
24
+ pub fn as_i64(&self) -> Option<i64> {
25
+ match self {
26
+ DynamicValue::Integer(v) => Some(*v),
27
+ _ => None,
28
+ }
29
+ }
30
+
31
+ pub fn as_f64(&self) -> Option<f64> {
32
+ match self {
33
+ DynamicValue::Float(v) => Some(*v),
34
+ DynamicValue::Integer(v) => Some(*v as f64),
35
+ _ => None,
36
+ }
37
+ }
38
+
39
+ pub fn as_str(&self) -> Option<&str> {
40
+ match self {
41
+ DynamicValue::String(v) => Some(v),
42
+ DynamicValue::Symbol(v) => Some(v),
43
+ _ => None,
44
+ }
45
+ }
46
+ }
47
+
48
+ #[derive(Debug, Clone)]
49
+ pub struct DynamicComponent {
50
+ pub type_name: String,
51
+ pub data: HashMap<String, DynamicValue>,
52
+ }
53
+
54
+ impl DynamicComponent {
55
+ pub fn new(type_name: &str) -> Self {
56
+ Self {
57
+ type_name: type_name.to_string(),
58
+ data: HashMap::new(),
59
+ }
60
+ }
61
+
62
+ pub fn with_field(mut self, name: &str, value: DynamicValue) -> Self {
63
+ self.data.insert(name.to_string(), value);
64
+ self
65
+ }
66
+
67
+ pub fn set(&mut self, name: &str, value: DynamicValue) {
68
+ self.data.insert(name.to_string(), value);
69
+ }
70
+
71
+ pub fn get(&self, name: &str) -> Option<&DynamicValue> {
72
+ self.data.get(name)
73
+ }
74
+
75
+ pub fn type_name(&self) -> &str {
76
+ &self.type_name
77
+ }
78
+ }
79
+
80
+ #[derive(Debug, Clone, Component, Default)]
81
+ pub struct DynamicComponents {
82
+ components: Vec<DynamicComponent>,
83
+ }
84
+
85
+ impl DynamicComponents {
86
+ pub fn new() -> Self {
87
+ Self {
88
+ components: Vec::new(),
89
+ }
90
+ }
91
+
92
+ pub fn add(&mut self, component: DynamicComponent) {
93
+ let type_name = component.type_name.clone();
94
+ self.components.retain(|c| c.type_name != type_name);
95
+ self.components.push(component);
96
+ }
97
+
98
+ pub fn get(&self, type_name: &str) -> Option<&DynamicComponent> {
99
+ self.components.iter().find(|c| c.type_name == type_name)
100
+ }
101
+
102
+ pub fn get_mut(&mut self, type_name: &str) -> Option<&mut DynamicComponent> {
103
+ self.components
104
+ .iter_mut()
105
+ .find(|c| c.type_name == type_name)
106
+ }
107
+
108
+ pub fn has(&self, type_name: &str) -> bool {
109
+ self.components.iter().any(|c| c.type_name == type_name)
110
+ }
111
+
112
+ pub fn has_all(&self, type_names: &[&str]) -> bool {
113
+ type_names.iter().all(|name| self.has(name))
114
+ }
115
+
116
+ pub fn remove(&mut self, type_name: &str) -> Option<DynamicComponent> {
117
+ let pos = self
118
+ .components
119
+ .iter()
120
+ .position(|c| c.type_name == type_name)?;
121
+ Some(self.components.remove(pos))
122
+ }
123
+
124
+ pub fn iter(&self) -> impl Iterator<Item = &DynamicComponent> {
125
+ self.components.iter()
126
+ }
127
+
128
+ pub fn type_names(&self) -> Vec<&str> {
129
+ self.components.iter().map(|c| c.type_name.as_str()).collect()
130
+ }
131
+ }