Created
June 18, 2019 12:07
-
-
Save rust-play/dc30943fc81ab854a9196635c4a72d7f to your computer and use it in GitHub Desktop.
Code shared from the Rust Playground
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use std::any::{Any, TypeId}; | |
use std::collections::HashMap; | |
use std::vec::Vec; | |
pub struct World { | |
components: HashMap<TypeId, Box<dyn Any>>, | |
next_entity_id: Entity, | |
entities: Vec<EntityData>, | |
} | |
impl World { | |
pub fn register_component_with_storage<C: 'static>(&mut self) { | |
self.components | |
.insert(TypeId::of::<C>(), Box::new(Vec::<C>::new())); | |
} | |
pub fn add_component_to_storage<C: 'static>(&mut self, component: C) -> usize { | |
let storage = self | |
.components | |
.get_mut(&TypeId::of::<C>()) | |
.unwrap() | |
.downcast_mut::<Vec<C>>() | |
.unwrap(); | |
storage.push(component); | |
return storage.len() - 1; | |
} | |
fn get_component<C: 'static>(&self, index: usize) -> &C { | |
let storage = self.components[&TypeId::of::<C>()] | |
.downcast_ref::<Vec<C>>() | |
.unwrap(); | |
&storage[index] | |
} | |
pub fn create_entity(&mut self) -> Entity { | |
let e = self.next_entity_id; | |
self.entities.push(EntityData { | |
components: Vec::new(), | |
}); | |
self.next_entity_id += 1; | |
return e; | |
} | |
pub fn add_component_to_entity<C: 'static>(&mut self, entity: Entity, component: C) { | |
let index = self.add_component_to_storage(component); | |
let entity_data = self.entities.get_mut(entity).unwrap(); | |
let ec = EntityComponent { | |
component_type: TypeId::of::<C>(), | |
component_index: index, | |
}; | |
entity_data.components.push(ec); | |
} | |
fn get_component_for_entity<C: 'static>(&self, entity: Entity) -> Option<&C> { | |
let entity_data = &self.entities[entity]; | |
for entity_component in &entity_data.components { | |
if entity_component.component_type == TypeId::of::<C>() { | |
let index = entity_component.component_index; | |
return Some(self.get_component::<C>(index)); | |
} | |
} | |
return None; | |
} | |
} | |
type Entity = usize; | |
pub struct EntityComponent { | |
component_type: TypeId, | |
component_index: usize, | |
} | |
pub struct EntityData { | |
components: Vec<EntityComponent>, | |
} | |
#[derive(Debug)] | |
pub struct ImageComponent { | |
x: f32, | |
y: f32, | |
} | |
#[derive(Debug)] | |
pub struct GravityComponent { | |
speed: f32, | |
} | |
fn main() { | |
println!("Starting up"); | |
let mut world = World { | |
components: HashMap::new(), | |
next_entity_id: 0, | |
entities: Vec::new(), | |
}; | |
world.register_component_with_storage::<ImageComponent>(); | |
world.register_component_with_storage::<GravityComponent>(); | |
let ic_1 = ImageComponent { x: 10.0, y: 10.0 }; | |
let ic_2 = ImageComponent { x: 50.0, y: 50.0 }; | |
let gc_1 = GravityComponent { speed: 9.8 }; | |
//let ic_index = world.add_component_to_storage(ic); | |
//dbg!(world.get_component::<ImageComponent>(ic_index)); | |
let entity_1 = world.create_entity(); | |
world.add_component_to_entity(entity_1, ic_1); | |
let entity_2 = world.create_entity(); | |
world.add_component_to_entity(entity_2, ic_2); | |
world.add_component_to_entity(entity_2, gc_1); | |
let e1_ic = world.get_component_for_entity::<ImageComponent>(entity_1); | |
dbg!(e1_ic); | |
let e1_gc = world.get_component_for_entity::<GravityComponent>(entity_1); | |
dbg!(e1_gc); | |
let e2_ic = world.get_component_for_entity::<ImageComponent>(entity_2); | |
dbg!(e2_ic); | |
let e2_gc = world.get_component_for_entity::<GravityComponent>(entity_2); | |
dbg!(e2_gc); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment