summaryrefslogtreecommitdiff
path: root/ecs/src/relationship.rs
diff options
context:
space:
mode:
Diffstat (limited to 'ecs/src/relationship.rs')
-rw-r--r--ecs/src/relationship.rs52
1 files changed, 35 insertions, 17 deletions
diff --git a/ecs/src/relationship.rs b/ecs/src/relationship.rs
index 4db29da..9f2a81e 100644
--- a/ecs/src/relationship.rs
+++ b/ecs/src/relationship.rs
@@ -1,24 +1,24 @@
use std::any::{type_name, Any};
use std::marker::PhantomData;
+use std::sync::LazyLock;
use crate::component::storage::Storage as ComponentStorage;
use crate::component::{
Component,
FromOptional as FromOptionalComponent,
FromOptionalMut as FromOptionalMutComponent,
- Id as ComponentId,
};
-use crate::entity::Uid as EntityUid;
use crate::lock::ReadGuard;
use crate::system::{ComponentRef, ComponentRefMut, Input as SystemInput};
use crate::type_name::TypeName;
+use crate::uid::{Kind as UidKind, Uid};
use crate::World;
/// A relationship to one or more targets.
#[derive(Debug)]
pub struct Relationship<Kind, ComponentT: Component>
{
- entity_uid: SingleOrMultiple<EntityUid>,
+ entity_uid: SingleOrMultiple<Uid>,
_pd: PhantomData<(Kind, ComponentT)>,
}
@@ -28,8 +28,10 @@ where
{
/// Creates a new `Relationship` with a single target.
#[must_use]
- pub fn new(entity_uid: EntityUid) -> Self
+ pub fn new(entity_uid: Uid) -> Self
{
+ debug_assert_eq!(entity_uid.kind(), UidKind::Entity);
+
Self {
entity_uid: SingleOrMultiple::Single(entity_uid),
_pd: PhantomData,
@@ -38,15 +40,24 @@ where
/// Creates a new `Relationship` with multiple targets.
#[must_use]
- pub fn new_multiple(entity_uids: impl IntoIterator<Item = EntityUid>) -> Self
+ pub fn new_multiple(entity_uids: impl IntoIterator<Item = Uid>) -> Self
{
+ let uids = entity_uids.into_iter().collect::<Vec<_>>();
+
+ for euid in &uids {
+ debug_assert_eq!(euid.kind(), UidKind::Entity);
+ }
+
Self {
- entity_uid: SingleOrMultiple::Multiple(entity_uids.into_iter().collect()),
+ entity_uid: SingleOrMultiple::Multiple(uids),
_pd: PhantomData,
}
}
}
+static COMPONENT_EUID: LazyLock<Uid> =
+ LazyLock::new(|| Uid::new_unique(UidKind::Component));
+
impl<Kind, ComponentT> Component for Relationship<Kind, ComponentT>
where
Kind: 'static,
@@ -56,9 +67,16 @@ where
type Ref<'component> = Relation<'component, Kind, ComponentT>;
type RefMut<'component> = RelationMut<'component, Kind, ComponentT>;
- fn id(&self) -> ComponentId
+ fn id() -> Uid
+ where
+ Self: Sized,
{
- ComponentId::of::<Self>()
+ *COMPONENT_EUID
+ }
+
+ fn self_id(&self) -> Uid
+ {
+ Self::id()
}
fn as_any_mut(&mut self) -> &mut dyn Any
@@ -151,8 +169,7 @@ where
.get_entity(*target)
.expect("Target entity is gone from archetype");
- let component_index =
- archetype.get_index_for_component(&ComponentId::of::<ComponentT>())?;
+ let component_index = archetype.get_index_for_component(&ComponentT::id())?;
let component = ComponentRefMut::new(
entity
@@ -172,7 +189,7 @@ where
/// Returns a reference to the target at the specified index.
#[must_use]
- pub fn get_target(&self, index: usize) -> Option<&EntityUid>
+ pub fn get_target(&self, index: usize) -> Option<&Uid>
{
match &self.relationship_comp.entity_uid {
SingleOrMultiple::Single(entity_uid) if index == 0 => Some(entity_uid),
@@ -183,7 +200,7 @@ where
/// Returns a mutable reference to the target at the specified index.
#[must_use]
- pub fn get_target_mut(&mut self, index: usize) -> Option<&mut EntityUid>
+ pub fn get_target_mut(&mut self, index: usize) -> Option<&mut Uid>
{
match &mut self.relationship_comp.entity_uid {
SingleOrMultiple::Single(entity_uid) if index == 0 => Some(entity_uid),
@@ -193,8 +210,10 @@ where
}
/// Adds a target to the relationship.
- pub fn add_target(&mut self, entity_uid: EntityUid)
+ pub fn add_target(&mut self, entity_uid: Uid)
{
+ debug_assert_eq!(entity_uid.kind(), UidKind::Entity);
+
match &mut self.relationship_comp.entity_uid {
SingleOrMultiple::Single(prev_entity_uid) => {
self.relationship_comp.entity_uid =
@@ -205,7 +224,7 @@ where
}
/// Removes a target to the relationship, returning it.
- pub fn remove_target(&mut self, index: usize) -> Option<EntityUid>
+ pub fn remove_target(&mut self, index: usize) -> Option<Uid>
{
match &mut self.relationship_comp.entity_uid {
SingleOrMultiple::Single(entity_uid) => {
@@ -354,8 +373,7 @@ where
.get_entity(*target)
.expect("Target entity is gone from archetype");
- let component_index =
- archetype.get_index_for_component(&ComponentId::of::<ComponentT>())?;
+ let component_index = archetype.get_index_for_component(&ComponentT::id())?;
let component = ComponentRef::new(
entity
@@ -375,7 +393,7 @@ where
/// Returns a reference to the target at the specified index.
#[must_use]
- pub fn get_target(&self, index: usize) -> Option<&EntityUid>
+ pub fn get_target(&self, index: usize) -> Option<&Uid>
{
match &self.relationship_comp.entity_uid {
SingleOrMultiple::Single(entity_uid) if index == 0 => Some(entity_uid),