Skip to content
This repository has been archived by the owner on Nov 29, 2022. It is now read-only.

Commit

Permalink
feat: expose CollisionData in Collisions component (#234)
Browse files Browse the repository at this point in the history
  • Loading branch information
agg23 committed Apr 14, 2022
1 parent b193422 commit 96525d8
Show file tree
Hide file tree
Showing 2 changed files with 46 additions and 13 deletions.
55 changes: 44 additions & 11 deletions core/src/collisions.rs
@@ -1,10 +1,10 @@
use bevy::{prelude::*, utils::HashSet};
use bevy::{prelude::*, utils::HashMap};

use crate::{CollisionEvent, RigidBody};
use crate::{CollisionData, CollisionEvent, RigidBody};

/// Component which will be filled (if present) with a list of entities with which the current entity is currently in contact.
#[derive(Component, Default, Reflect)]
pub struct Collisions(HashSet<Entity>);
pub struct Collisions(HashMap<Entity, CollisionData>);

impl Collisions {
/// Returns the number of colliding entities.
Expand All @@ -22,12 +22,24 @@ impl Collisions {
/// Returns `true` if the collisions contains the specified entity.
#[must_use]
pub fn contains(&self, entity: &Entity) -> bool {
self.0.contains(entity)
self.0.contains_key(entity)
}

/// An iterator visiting all colliding entities in arbitrary order.
#[deprecated(note = "Please use `entities()` instead")]
#[doc(hidden)]
pub fn iter(&self) -> impl Iterator<Item = Entity> + '_ {
self.0.iter().copied()
self.entities()
}

/// An iterator visiting all colliding entities in arbitrary order.
pub fn entities(&self) -> impl Iterator<Item = Entity> + '_ {
self.0.keys().copied()
}

/// An iterator visiting all data from colliding entities in arbitrary order.
pub fn collision_data(&self) -> impl Iterator<Item = &CollisionData> + '_ {
self.0.values()
}
}

Expand All @@ -38,13 +50,14 @@ pub(super) fn update_collisions_system(
mut collisions: Query<'_, '_, &mut Collisions>,
) {
for event in collision_events.iter() {
let (entity1, entity2) = event.rigid_body_entities();
let (data1, data2) = event.clone().data();
let (entity1, entity2) = (data1.rigid_body_entity(), data2.rigid_body_entity());
if event.is_started() {
if let Ok(mut entities) = collisions.get_mut(entity1) {
entities.0.insert(entity2);
entities.0.insert(entity2, data2);
}
if let Ok(mut entities) = collisions.get_mut(entity2) {
entities.0.insert(entity1);
entities.0.insert(entity1, data1);
}
} else {
if let Ok(mut entities) = collisions.get_mut(entity1) {
Expand Down Expand Up @@ -106,19 +119,31 @@ mod tests {
let collisions1 = app.world.entity(entity1).get::<Collisions>().unwrap();
assert_eq!(collisions1.len(), 1, "There should be one colliding entity");
assert_eq!(
collisions1.iter().next().unwrap(),
collisions1.entities().next().unwrap(),
entity2,
"Colliding entity should be equal to the second entity"
);

assert_eq!(
collisions1.collision_data().next().unwrap(),
&collision_data2,
"Colliding entity data should be equal to the second collision data"
);

let collisions2 = app.world.entity(entity2).get::<Collisions>().unwrap();
assert_eq!(collisions2.len(), 1, "There should be one colliding entity");
assert_eq!(
collisions2.iter().next().unwrap(),
collisions2.entities().next().unwrap(),
entity1,
"Colliding entity should be equal to the first entity"
);

assert_eq!(
collisions2.collision_data().next().unwrap(),
&collision_data1,
"Colliding entity data should be equal to the first collision data"
);

let mut collision_events = app
.world
.get_resource_mut::<Events<CollisionEvent>>()
Expand Down Expand Up @@ -148,7 +173,15 @@ mod tests {

let removing_entity = app.world.spawn().insert(RigidBody::Static).id();
let mut collisions = Collisions::default();
collisions.0.insert(removing_entity);
collisions.0.insert(
removing_entity,
CollisionData::new(
removing_entity,
Entity::from_raw(0),
CollisionLayers::default(),
[],
),
);
let entity = app.world.spawn().insert(collisions).id();

app.update();
Expand Down
4 changes: 2 additions & 2 deletions core/src/events.rs
@@ -1,4 +1,4 @@
use bevy::{ecs::entity::Entity, math::Vec2};
use bevy::{ecs::entity::Entity, math::Vec2, prelude::Reflect};
use smallvec::SmallVec;

use crate::CollisionLayers;
Expand Down Expand Up @@ -33,7 +33,7 @@ pub enum CollisionEvent {
}

/// Collision data concerning one of the two entity that collided
#[derive(Debug, Clone)]
#[derive(Debug, Clone, PartialEq, Reflect)]
pub struct CollisionData {
rigid_body_entity: Entity,
collision_shape_entity: Entity,
Expand Down

0 comments on commit 96525d8

Please sign in to comment.