diff options
| author | mat <git@matdoes.dev> | 2025-09-27 18:41:36 -1030 |
|---|---|---|
| committer | mat <git@matdoes.dev> | 2025-09-27 20:26:41 -0845 |
| commit | 74dcb7b37d953ec4d45dd6aac4c8e598c87def7d (patch) | |
| tree | 22e6ab1849ee01d40f3d484ea0c8db52aa6649b5 /azalea-physics/src/collision/entity_collisions.rs | |
| parent | 63bef6486dc1f3c9ef4b4f0d71e139d7035b6432 (diff) | |
| download | azalea-drasl-74dcb7b37d953ec4d45dd6aac4c8e598c87def7d.tar.xz | |
allow picking other bots in hit results
Diffstat (limited to 'azalea-physics/src/collision/entity_collisions.rs')
| -rw-r--r-- | azalea-physics/src/collision/entity_collisions.rs | 53 |
1 files changed, 37 insertions, 16 deletions
diff --git a/azalea-physics/src/collision/entity_collisions.rs b/azalea-physics/src/collision/entity_collisions.rs index 1300cf34..af2db1f0 100644 --- a/azalea-physics/src/collision/entity_collisions.rs +++ b/azalea-physics/src/collision/entity_collisions.rs @@ -1,13 +1,14 @@ -use azalea_core::aabb::AABB; +use azalea_core::aabb::Aabb; use azalea_entity::{ - LocalEntity, Physics, + Physics, metadata::{AbstractBoat, Shulker}, }; use azalea_world::Instance; use bevy_ecs::{ + component::Component, entity::Entity, - query::{Or, With, Without}, - system::Query, + query::{Changed, Or, With}, + system::{Commands, Query}, }; use tracing::error; @@ -26,14 +27,34 @@ pub type CollidableEntityQuery<'world, 'state> = Query<'world, 'state, (), Colli /// this. pub type CollidableEntityFilter = Or<(With<AbstractBoat>, With<Shulker>)>; -pub type PhysicsQuery<'world, 'state, 'a> = - Query<'world, 'state, &'a Physics, Without<LocalEntity>>; +/// A component that mirrors the Physics::bounding_box of every entity, but is +/// updated before client-side physics is done. +#[derive(Component)] +pub struct LastBoundingBox(pub Aabb); + +pub type AabbQuery<'world, 'state, 'a> = Query<'world, 'state, &'a LastBoundingBox>; + +/// Update the [`LastBoundingBox`] for every entity. +pub fn update_last_bounding_box( + mut commands: Commands, + mut query: Query<(Entity, Option<&mut LastBoundingBox>, &Physics), Changed<Physics>>, +) { + for (entity, mut last_bounding_box, physics) in &mut query { + if let Some(last_bounding_box) = last_bounding_box.as_mut() { + last_bounding_box.0 = physics.bounding_box; + } else { + commands + .entity(entity) + .insert(LastBoundingBox(physics.bounding_box)); + } + } +} pub fn get_entity_collisions( world: &Instance, - aabb: &AABB, + aabb: &Aabb, source_entity: Option<Entity>, - physics_query: &PhysicsQuery, + aabb_query: &AabbQuery, collidable_entity_query: &CollidableEntityQuery, ) -> Vec<VoxelShape> { if aabb.size() < 1.0E-7 { @@ -47,7 +68,7 @@ pub fn get_entity_collisions( source_entity, &aabb.inflate_all(1.0E-7), &collision_predicate, - physics_query, + aabb_query, ); collidable_entities @@ -64,10 +85,10 @@ pub fn get_entity_collisions( pub fn get_entities( world: &Instance, source_entity: Option<Entity>, - aabb: &AABB, + aabb: &Aabb, predicate: &dyn Fn(Entity) -> bool, - physics_query: &PhysicsQuery, -) -> Vec<(Entity, AABB)> { + aabb_query: &AabbQuery, +) -> Vec<(Entity, Aabb)> { let mut matches = Vec::new(); super::world_collisions::for_entities_in_chunks_colliding_with( @@ -77,16 +98,16 @@ pub fn get_entities( // now check if the entity itself collides for &candidate in entities_in_chunk { if Some(candidate) != source_entity && predicate(candidate) { - let Ok(physics) = physics_query.get(candidate) else { + let Ok(candidate_aabb) = aabb_query.get(candidate) else { error!( "Entity {candidate} (found from for_entities_in_chunks_colliding_with) is missing required components." ); continue; }; + let candidate_aabb = &candidate_aabb.0; - let candidate_aabb = physics.bounding_box; - if aabb.intersects_aabb(&candidate_aabb) { - matches.push((candidate, physics.bounding_box)); + if aabb.intersects_aabb(candidate_aabb) { + matches.push((candidate, candidate_aabb.to_owned())); } } } |
