From 27bcbeb76e0d33dc9a03a1c89f83a2b4d451b174 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Mon, 3 Feb 2025 18:01:05 +0100 Subject: [PATCH 01/10] wip uber physics context --- src/lib.rs | 3 + src/physics_context.rs | 82 ++++++++++ src/pipeline/physics_pipeline.rs | 248 +++++++++---------------------- 3 files changed, 154 insertions(+), 179 deletions(-) create mode 100644 src/physics_context.rs diff --git a/src/lib.rs b/src/lib.rs index 8a78e88d9..0f92fbda6 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -139,6 +139,8 @@ pub mod geometry; pub mod pipeline; pub mod utils; +mod physics_context; + /// Elementary mathematical entities (vectors, matrices, isometries, etc). pub mod math { pub use parry::math::*; @@ -215,6 +217,7 @@ pub mod prelude { pub use crate::dynamics::*; pub use crate::geometry::*; pub use crate::math::*; + pub use crate::physics_context::PhysicsContext; pub use crate::pipeline::*; pub use na::{point, vector, DMatrix, DVector}; pub extern crate nalgebra; diff --git a/src/physics_context.rs b/src/physics_context.rs new file mode 100644 index 000000000..42463f9d7 --- /dev/null +++ b/src/physics_context.rs @@ -0,0 +1,82 @@ +use crate::prelude::*; + +/// Contains all arguments to be passed to [`PhysicsPipeline::step`] +#[allow(missing_docs)] +pub struct PhysicsContext { + pub gravity: Vector, + pub integration_parameters: IntegrationParameters, + pub physics_pipeline: PhysicsPipeline, + pub island_manager: IslandManager, + pub broad_phase: DefaultBroadPhase, + pub narrow_phase: NarrowPhase, + pub bodies: RigidBodySet, + pub colliders: ColliderSet, + pub impulse_joint_set: ImpulseJointSet, + pub multibody_joint_set: MultibodyJointSet, + pub ccd_solver: CCDSolver, + pub query_pipeline: Option, + pub hooks: PH, + pub events: EV, +} + +impl Default for PhysicsContext { + fn default() -> Self { + Self { + gravity: Vector::::default(), + integration_parameters: IntegrationParameters::default(), + physics_pipeline: PhysicsPipeline::new(), + island_manager: IslandManager::new(), + broad_phase: BroadPhaseMultiSap::new(), + narrow_phase: NarrowPhase::new(), + bodies: RigidBodySet::new(), + colliders: ColliderSet::new(), + impulse_joint_set: ImpulseJointSet::new(), + multibody_joint_set: MultibodyJointSet::new(), + ccd_solver: CCDSolver::new(), + query_pipeline: Some(QueryPipeline::new()), + hooks: PH::default(), + events: EV::default(), + } + } +} + +impl PhysicsContext { + /// Create a new physics context with given hooks and event handling. + pub fn default_with(hooks: PH, events: EV) -> Self { + Self { + gravity: Vector::::default(), + integration_parameters: IntegrationParameters::default(), + physics_pipeline: PhysicsPipeline::new(), + island_manager: IslandManager::new(), + broad_phase: DefaultBroadPhase::new(), + narrow_phase: NarrowPhase::new(), + bodies: RigidBodySet::new(), + colliders: ColliderSet::new(), + impulse_joint_set: ImpulseJointSet::new(), + multibody_joint_set: MultibodyJointSet::new(), + ccd_solver: CCDSolver::new(), + query_pipeline: Some(QueryPipeline::new()), + hooks, + events, + } + } + + /// Shortcut to [`PhysicsPipeline::step`] + pub fn step(&mut self) { + self.physics_pipeline.step( + &self.gravity, + &self.integration_parameters, + &mut self.island_manager, + &mut self.broad_phase, + &mut self.narrow_phase, + &mut self.bodies, + &mut self.colliders, + &mut self.impulse_joint_set, + &mut self.multibody_joint_set, + &mut self.ccd_solver, + self.query_pipeline.as_mut(), + &mut self.hooks, + &mut self.events, + ); + } +} diff --git a/src/pipeline/physics_pipeline.rs b/src/pipeline/physics_pipeline.rs index 91a737c90..f10ab5e7f 100644 --- a/src/pipeline/physics_pipeline.rs +++ b/src/pipeline/physics_pipeline.rs @@ -671,106 +671,67 @@ mod test { use na::point; use crate::dynamics::{ - CCDSolver, ImpulseJointSet, IntegrationParameters, IslandManager, RigidBodyBuilder, - RigidBodySet, + ImpulseJointSet, IntegrationParameters, IslandManager, RigidBodyBuilder, RigidBodySet, }; - use crate::geometry::{BroadPhaseMultiSap, ColliderBuilder, ColliderSet, NarrowPhase}; + use crate::geometry::{ColliderBuilder, ColliderSet}; use crate::math::Vector; - use crate::pipeline::PhysicsPipeline; use crate::prelude::{MultibodyJointSet, RevoluteJointBuilder, RigidBodyType}; #[test] fn kinematic_and_fixed_contact_crash() { - let mut colliders = ColliderSet::new(); - let mut impulse_joints = ImpulseJointSet::new(); - let mut multibody_joints = MultibodyJointSet::new(); - let mut pipeline = PhysicsPipeline::new(); - let mut bf = BroadPhaseMultiSap::new(); - let mut nf = NarrowPhase::new(); - let mut bodies = RigidBodySet::new(); - let mut islands = IslandManager::new(); + let mut pc = crate::prelude::PhysicsContext::<(), ()> { + query_pipeline: None, + ..crate::prelude::PhysicsContext::default() + }; let rb = RigidBodyBuilder::fixed().build(); - let h1 = bodies.insert(rb.clone()); + let h1 = pc.bodies.insert(rb.clone()); let co = ColliderBuilder::ball(10.0).build(); - colliders.insert_with_parent(co.clone(), h1, &mut bodies); + pc.colliders + .insert_with_parent(co.clone(), h1, &mut pc.bodies); // The same but with a kinematic body. let rb = RigidBodyBuilder::kinematic_position_based().build(); - let h2 = bodies.insert(rb.clone()); - colliders.insert_with_parent(co, h2, &mut bodies); + let h2 = pc.bodies.insert(rb.clone()); + pc.colliders.insert_with_parent(co, h2, &mut pc.bodies); - pipeline.step( - &Vector::zeros(), - &IntegrationParameters::default(), - &mut islands, - &mut bf, - &mut nf, - &mut bodies, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, - &mut CCDSolver::new(), - None, - &(), - &(), - ); + pc.step(); } #[test] fn rigid_body_removal_before_step() { - let mut colliders = ColliderSet::new(); - let mut impulse_joints = ImpulseJointSet::new(); - let mut multibody_joints = MultibodyJointSet::new(); - let mut pipeline = PhysicsPipeline::new(); - let mut bf = BroadPhaseMultiSap::new(); - let mut nf = NarrowPhase::new(); - let mut islands = IslandManager::new(); - - let mut bodies = RigidBodySet::new(); + let mut pc = crate::prelude::PhysicsContext::<(), ()> { + query_pipeline: None, + ..crate::prelude::PhysicsContext::default() + }; // Check that removing the body right after inserting it works. // We add two dynamic bodies, one kinematic body and one fixed body before removing // them. This include a non-regression test where deleting a kinematic body crashes. let rb = RigidBodyBuilder::dynamic().build(); - let h1 = bodies.insert(rb.clone()); - let h2 = bodies.insert(rb.clone()); + let h1 = pc.bodies.insert(rb.clone()); + let h2 = pc.bodies.insert(rb.clone()); // The same but with a kinematic body. let rb = RigidBodyBuilder::kinematic_position_based().build(); - let h3 = bodies.insert(rb.clone()); + let h3 = pc.bodies.insert(rb.clone()); // The same but with a fixed body. let rb = RigidBodyBuilder::fixed().build(); - let h4 = bodies.insert(rb.clone()); + let h4 = pc.bodies.insert(rb.clone()); let to_delete = [h1, h2, h3, h4]; for h in &to_delete { - bodies.remove( + pc.bodies.remove( *h, - &mut islands, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, + &mut pc.island_manager, + &mut pc.colliders, + &mut pc.impulse_joint_set, + &mut pc.multibody_joint_set, true, ); } - - pipeline.step( - &Vector::zeros(), - &IntegrationParameters::default(), - &mut islands, - &mut bf, - &mut nf, - &mut bodies, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, - &mut CCDSolver::new(), - None, - &(), - &(), - ); + pc.step(); } #[cfg(feature = "serde-serialize")] @@ -830,139 +791,87 @@ mod test { #[test] fn collider_removal_before_step() { - let mut pipeline = PhysicsPipeline::new(); - let gravity = Vector::y() * -9.81; - let integration_parameters = IntegrationParameters::default(); - let mut broad_phase = BroadPhaseMultiSap::new(); - let mut narrow_phase = NarrowPhase::new(); - let mut bodies = RigidBodySet::new(); - let mut colliders = ColliderSet::new(); - let mut ccd = CCDSolver::new(); - let mut impulse_joints = ImpulseJointSet::new(); - let mut multibody_joints = MultibodyJointSet::new(); - let mut islands = IslandManager::new(); - let physics_hooks = (); - let event_handler = (); + let mut pc = crate::prelude::PhysicsContext::<(), ()> { + query_pipeline: None, + gravity: Vector::y() * -9.81, + ..crate::prelude::PhysicsContext::default() + }; let body = RigidBodyBuilder::dynamic().build(); - let b_handle = bodies.insert(body); + let b_handle = pc.bodies.insert(body); let collider = ColliderBuilder::ball(1.0).build(); - let c_handle = colliders.insert_with_parent(collider, b_handle, &mut bodies); - colliders.remove(c_handle, &mut islands, &mut bodies, true); - bodies.remove( + let c_handle = pc + .colliders + .insert_with_parent(collider, b_handle, &mut pc.bodies); + pc.colliders + .remove(c_handle, &mut pc.island_manager, &mut pc.bodies, true); + pc.bodies.remove( b_handle, - &mut islands, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, + &mut pc.island_manager, + &mut pc.colliders, + &mut pc.impulse_joint_set, + &mut pc.multibody_joint_set, true, ); for _ in 0..10 { - pipeline.step( - &gravity, - &integration_parameters, - &mut islands, - &mut broad_phase, - &mut narrow_phase, - &mut bodies, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, - &mut ccd, - None, - &physics_hooks, - &event_handler, - ); + pc.step(); } } #[test] fn rigid_body_type_changed_dynamic_is_in_active_set() { - let mut colliders = ColliderSet::new(); - let mut impulse_joints = ImpulseJointSet::new(); - let mut multibody_joints = MultibodyJointSet::new(); - let mut pipeline = PhysicsPipeline::new(); - let mut bf = BroadPhaseMultiSap::new(); - let mut nf = NarrowPhase::new(); - let mut islands = IslandManager::new(); - - let mut bodies = RigidBodySet::new(); + let mut pc = crate::prelude::PhysicsContext::<(), ()> { + query_pipeline: None, + gravity: Vector::y() * -9.81, + ..crate::prelude::PhysicsContext::default() + }; // Initialize body as kinematic with mass let rb = RigidBodyBuilder::kinematic_position_based() .additional_mass(1.0) .build(); - let h = bodies.insert(rb.clone()); + let h = pc.bodies.insert(rb.clone()); // Step once - let gravity = Vector::y() * -9.81; - pipeline.step( - &gravity, - &IntegrationParameters::default(), - &mut islands, - &mut bf, - &mut nf, - &mut bodies, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, - &mut CCDSolver::new(), - None, - &(), - &(), - ); + pc.step(); // Switch body type to Dynamic - bodies + pc.bodies .get_mut(h) .unwrap() .set_body_type(RigidBodyType::Dynamic, true); // Step again - pipeline.step( - &gravity, - &IntegrationParameters::default(), - &mut islands, - &mut bf, - &mut nf, - &mut bodies, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, - &mut CCDSolver::new(), - None, - &(), - &(), - ); + pc.step(); - let body = bodies.get(h).unwrap(); + let body = pc.bodies.get(h).unwrap(); let h_y = body.pos.position.translation.y; // Expect gravity to be applied on second step after switching to Dynamic assert!(h_y < 0.0); // Expect body to now be in active_dynamic_set - assert!(islands.active_dynamic_set.contains(&h)); + assert!(pc.island_manager.active_dynamic_set.contains(&h)); } #[test] fn joint_step_delta_time_0() { - let mut colliders = ColliderSet::new(); - let mut impulse_joints = ImpulseJointSet::new(); - let mut multibody_joints = MultibodyJointSet::new(); - let mut pipeline = PhysicsPipeline::new(); - let mut bf = BroadPhaseMultiSap::new(); - let mut nf = NarrowPhase::new(); - let mut islands = IslandManager::new(); - - let mut bodies = RigidBodySet::new(); + let mut pc = crate::prelude::PhysicsContext::<(), ()> { + query_pipeline: None, + gravity: Vector::y() * -9.81, + integration_parameters: IntegrationParameters { + dt: 0.0, + ..Default::default() + }, + ..crate::prelude::PhysicsContext::default() + }; // Initialize bodies let rb = RigidBodyBuilder::fixed().additional_mass(1.0).build(); - let h = bodies.insert(rb.clone()); + let h = pc.bodies.insert(rb.clone()); let rb_dynamic = RigidBodyBuilder::dynamic().additional_mass(1.0).build(); - let h_dynamic = bodies.insert(rb_dynamic.clone()); + let h_dynamic = pc.bodies.insert(rb_dynamic.clone()); // Add joint #[cfg(feature = "dim2")] @@ -973,31 +882,12 @@ mod test { let joint = RevoluteJointBuilder::new(Vector::z_axis()) .local_anchor1(point![0.0, 1.0, 0.0]) .local_anchor2(point![0.0, -3.0, 0.0]); - impulse_joints.insert(h, h_dynamic, joint, true); + pc.impulse_joint_set.insert(h, h_dynamic, joint, true); - let parameters = IntegrationParameters { - dt: 0.0, - ..Default::default() - }; // Step once - let gravity = Vector::y() * -9.81; - pipeline.step( - &gravity, - ¶meters, - &mut islands, - &mut bf, - &mut nf, - &mut bodies, - &mut colliders, - &mut impulse_joints, - &mut multibody_joints, - &mut CCDSolver::new(), - None, - &(), - &(), - ); - let translation = bodies[h_dynamic].translation(); - let rotation = bodies[h_dynamic].rotation(); + pc.step(); + let translation = pc.bodies[h_dynamic].translation(); + let rotation = pc.bodies[h_dynamic].rotation(); assert!(translation.x.is_finite()); assert!(translation.y.is_finite()); #[cfg(feature = "dim2")] From c6484df77ff6f6f3a6c473554b76d09673823ef3 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Mon, 3 Feb 2025 18:08:50 +0100 Subject: [PATCH 02/10] fix clippy --- src/physics_context.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/physics_context.rs b/src/physics_context.rs index 42463f9d7..22305f1f8 100644 --- a/src/physics_context.rs +++ b/src/physics_context.rs @@ -75,8 +75,8 @@ impl PhysicsContext { &mut self.multibody_joint_set, &mut self.ccd_solver, self.query_pipeline.as_mut(), - &mut self.hooks, - &mut self.events, + &self.hooks, + &self.events, ); } } From 69922aa8c98920a3f7576739d861fe43cbb73209 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Tue, 18 Feb 2025 16:26:32 +0100 Subject: [PATCH 03/10] implement physicsContext collider, rigidbody and query pipeline method shortcuts --- CHANGELOG.md | 9 +- src/physics_context.rs | 281 ++++++++++++++++++++++++++++--- src/pipeline/physics_pipeline.rs | 22 +-- 3 files changed, 274 insertions(+), 38 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f00bb2f28..4c79e65ba 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,11 @@ +# Changelog + +## Unreleased + +### Added + +- Add a `PhysicsContext` struct containing top level rapier structs to help with reducing boilerplate. + ## v0.23.0 (08 Jan 2025) ### Fix @@ -16,7 +24,6 @@ - `RigidBodySet` and `ColliderSet` have a new constructor `with_capacity`. - Use `profiling` crate to provide helpful profiling information in different tools. - The testbeds have been updated to use `puffin_egui` - ### Modified - `InteractionGroups` default value for `memberships` is now `GROUP_1` (#706) diff --git a/src/physics_context.rs b/src/physics_context.rs index 22305f1f8..8c9602420 100644 --- a/src/physics_context.rs +++ b/src/physics_context.rs @@ -1,8 +1,10 @@ +use parry::query::{NonlinearRigidMotion, ShapeCastOptions}; + use crate::prelude::*; /// Contains all arguments to be passed to [`PhysicsPipeline::step`] #[allow(missing_docs)] -pub struct PhysicsContext { +pub struct PhysicsContext { pub gravity: Vector, pub integration_parameters: IntegrationParameters, pub physics_pipeline: PhysicsPipeline, @@ -15,11 +17,9 @@ pub struct PhysicsContext { pub multibody_joint_set: MultibodyJointSet, pub ccd_solver: CCDSolver, pub query_pipeline: Option, - pub hooks: PH, - pub events: EV, } -impl Default for PhysicsContext { +impl Default for PhysicsContext { fn default() -> Self { Self { gravity: Vector::::default(), @@ -34,35 +34,21 @@ impl Default for Physics multibody_joint_set: MultibodyJointSet::new(), ccd_solver: CCDSolver::new(), query_pipeline: Some(QueryPipeline::new()), - hooks: PH::default(), - events: EV::default(), } } } -impl PhysicsContext { - /// Create a new physics context with given hooks and event handling. - pub fn default_with(hooks: PH, events: EV) -> Self { +impl PhysicsContext { + /// Creates a default physics context without a query pipeline. + pub fn default_without_query_pipeline() -> Self { Self { - gravity: Vector::::default(), - integration_parameters: IntegrationParameters::default(), - physics_pipeline: PhysicsPipeline::new(), - island_manager: IslandManager::new(), - broad_phase: DefaultBroadPhase::new(), - narrow_phase: NarrowPhase::new(), - bodies: RigidBodySet::new(), - colliders: ColliderSet::new(), - impulse_joint_set: ImpulseJointSet::new(), - multibody_joint_set: MultibodyJointSet::new(), - ccd_solver: CCDSolver::new(), - query_pipeline: Some(QueryPipeline::new()), - hooks, - events, + query_pipeline: None, + ..PhysicsContext::default() } } /// Shortcut to [`PhysicsPipeline::step`] - pub fn step(&mut self) { + pub fn step(&mut self, hooks: &dyn PhysicsHooks, events: &dyn EventHandler) { self.physics_pipeline.step( &self.gravity, &self.integration_parameters, @@ -75,8 +61,251 @@ impl PhysicsContext { &mut self.multibody_joint_set, &mut self.ccd_solver, self.query_pipeline.as_mut(), - &self.hooks, - &self.events, + hooks, + events, + ); + } + + /// Shortcut to [`ColliderSet::insert_with_parent`] + pub fn insert_rigidbody( + &mut self, + parent_handle: RigidBodyHandle, + collider: impl Into, + ) -> ColliderHandle { + self.colliders + .insert_with_parent(collider, parent_handle, &mut self.bodies) + } + + /// Shortcut to [`RigidBodySet::insert`] and [`ColliderSet::insert_with_parent`] + pub fn insert_body_and_collider( + &mut self, + collider: impl Into, + rb: impl Into, + ) -> (RigidBodyHandle, ColliderHandle) { + let parent_handle = self.bodies.insert(rb); + ( + parent_handle, + self.colliders + .insert_with_parent(collider, parent_handle, &mut self.bodies), + ) + } +} + +/// Shortcuts to [`QueryPipeline`] +impl PhysicsContext { + /// Shortcut to [`QueryPipeline::update_incremental`] + pub fn update_incremental( + &mut self, + modified_colliders: &[ColliderHandle], + removed_colliders: &[ColliderHandle], + refit_and_rebalance: bool, + ) { + let Some(query_pipeline) = &mut self.query_pipeline else { + return; + }; + query_pipeline.update_incremental( + &self.colliders, + modified_colliders, + removed_colliders, + refit_and_rebalance, ); } + + /// Shortcut to [`QueryPipeline::update`] + pub fn update(&mut self) { + let Some(query_pipeline) = &mut self.query_pipeline else { + return; + }; + query_pipeline.update(&self.colliders) + } + + /// Shortcut to [`QueryPipeline::cast_ray`] + pub fn cast_ray( + &self, + ray: &Ray, + max_toi: Real, + solid: bool, + filter: QueryFilter, + ) -> Option<(ColliderHandle, Real)> { + let Some(query_pipeline) = &self.query_pipeline else { + return None; + }; + query_pipeline.cast_ray(&self.bodies, &self.colliders, ray, max_toi, solid, filter) + } + + /// Shortcut to [`QueryPipeline::cast_ray_and_get_normal`] + pub fn cast_ray_and_get_normal( + &self, + ray: &Ray, + max_toi: Real, + solid: bool, + filter: QueryFilter, + ) -> Option<(ColliderHandle, RayIntersection)> { + let Some(query_pipeline) = &self.query_pipeline else { + return None; + }; + query_pipeline.cast_ray_and_get_normal( + &self.bodies, + &self.colliders, + ray, + max_toi, + solid, + filter, + ) + } + + /// Shortcut to [`QueryPipeline::intersections_with_ray`] + pub fn intersections_with_ray<'a>( + &self, + ray: &Ray, + max_toi: Real, + solid: bool, + filter: QueryFilter, + callback: impl FnMut(ColliderHandle, RayIntersection) -> bool, + ) { + let Some(query_pipeline) = &self.query_pipeline else { + return; + }; + query_pipeline.intersections_with_ray( + &self.bodies, + &self.colliders, + ray, + max_toi, + solid, + filter, + callback, + ) + } + + /// Shortcut to [`QueryPipeline::intersection_with_shape`] + pub fn intersection_with_shape( + &self, + shape_pos: &Isometry, + shape: &dyn Shape, + filter: QueryFilter, + ) -> Option { + let Some(query_pipeline) = &self.query_pipeline else { + return None; + }; + query_pipeline.intersection_with_shape( + &self.bodies, + &self.colliders, + shape_pos, + shape, + filter, + ) + } + + /// Shortcut to [`QueryPipeline::project_point`] + pub fn project_point( + &self, + point: &Point, + solid: bool, + filter: QueryFilter, + ) -> Option<(ColliderHandle, PointProjection)> { + let Some(query_pipeline) = &self.query_pipeline else { + return None; + }; + query_pipeline.project_point(&self.bodies, &self.colliders, point, solid, filter) + } + + /// Shortcut to [`QueryPipeline::intersections_with_point`] + pub fn intersections_with_point( + &self, + point: &Point, + filter: QueryFilter, + callback: impl FnMut(ColliderHandle) -> bool, + ) { + let Some(query_pipeline) = &self.query_pipeline else { + return; + }; + query_pipeline.intersections_with_point( + &self.bodies, + &self.colliders, + point, + filter, + callback, + ) + } + + /// Shortcut to [`QueryPipeline::project_point_and_get_feature`] + pub fn project_point_and_get_feature( + &self, + point: &Point, + filter: QueryFilter, + ) -> Option<(ColliderHandle, PointProjection, FeatureId)> { + let Some(query_pipeline) = &self.query_pipeline else { + return None; + }; + query_pipeline.project_point_and_get_feature(&self.bodies, &self.colliders, point, filter) + } + + /// Shortcut to [`QueryPipeline::cast_shape`] + pub fn cast_shape( + &self, + shape_pos: &Isometry, + shape_vel: &Vector, + shape: &dyn Shape, + options: ShapeCastOptions, + filter: QueryFilter, + ) -> Option<(ColliderHandle, ShapeCastHit)> { + let Some(query_pipeline) = &self.query_pipeline else { + return None; + }; + query_pipeline.cast_shape( + &self.bodies, + &self.colliders, + shape_pos, + shape_vel, + shape, + options, + filter, + ) + } + + /// Shortcut to [`QueryPipeline::nonlinear_cast_shape`] + pub fn nonlinear_cast_shape( + &self, + shape_motion: &NonlinearRigidMotion, + shape: &dyn Shape, + start_time: Real, + end_time: Real, + stop_at_penetration: bool, + filter: QueryFilter, + ) -> Option<(ColliderHandle, ShapeCastHit)> { + let Some(query_pipeline) = &self.query_pipeline else { + return None; + }; + query_pipeline.nonlinear_cast_shape( + &self.bodies, + &self.colliders, + shape_motion, + shape, + start_time, + end_time, + stop_at_penetration, + filter, + ) + } + + /// Shortcut to [`QueryPipeline::intersections_with_shape`] + pub fn intersections_with_shape( + &self, + shape_pos: &Isometry, + shape: &dyn Shape, + filter: QueryFilter, + callback: impl FnMut(ColliderHandle) -> bool, + ) { + let Some(query_pipeline) = &self.query_pipeline else { + return; + }; + query_pipeline.intersections_with_shape( + &self.bodies, + &self.colliders, + shape_pos, + shape, + filter, + callback, + ) + } } diff --git a/src/pipeline/physics_pipeline.rs b/src/pipeline/physics_pipeline.rs index f10ab5e7f..da2a24fe0 100644 --- a/src/pipeline/physics_pipeline.rs +++ b/src/pipeline/physics_pipeline.rs @@ -679,7 +679,7 @@ mod test { #[test] fn kinematic_and_fixed_contact_crash() { - let mut pc = crate::prelude::PhysicsContext::<(), ()> { + let mut pc = crate::prelude::PhysicsContext { query_pipeline: None, ..crate::prelude::PhysicsContext::default() }; @@ -695,12 +695,12 @@ mod test { let h2 = pc.bodies.insert(rb.clone()); pc.colliders.insert_with_parent(co, h2, &mut pc.bodies); - pc.step(); + pc.step(&(), &()); } #[test] fn rigid_body_removal_before_step() { - let mut pc = crate::prelude::PhysicsContext::<(), ()> { + let mut pc = crate::prelude::PhysicsContext { query_pipeline: None, ..crate::prelude::PhysicsContext::default() }; @@ -731,7 +731,7 @@ mod test { true, ); } - pc.step(); + pc.step(&(), &()); } #[cfg(feature = "serde-serialize")] @@ -791,7 +791,7 @@ mod test { #[test] fn collider_removal_before_step() { - let mut pc = crate::prelude::PhysicsContext::<(), ()> { + let mut pc = crate::prelude::PhysicsContext { query_pipeline: None, gravity: Vector::y() * -9.81, ..crate::prelude::PhysicsContext::default() @@ -815,13 +815,13 @@ mod test { ); for _ in 0..10 { - pc.step(); + pc.step(&(), &()); } } #[test] fn rigid_body_type_changed_dynamic_is_in_active_set() { - let mut pc = crate::prelude::PhysicsContext::<(), ()> { + let mut pc = crate::prelude::PhysicsContext { query_pipeline: None, gravity: Vector::y() * -9.81, ..crate::prelude::PhysicsContext::default() @@ -834,7 +834,7 @@ mod test { let h = pc.bodies.insert(rb.clone()); // Step once - pc.step(); + pc.step(&(), &()); // Switch body type to Dynamic pc.bodies @@ -843,7 +843,7 @@ mod test { .set_body_type(RigidBodyType::Dynamic, true); // Step again - pc.step(); + pc.step(&(), &()); let body = pc.bodies.get(h).unwrap(); let h_y = body.pos.position.translation.y; @@ -857,7 +857,7 @@ mod test { #[test] fn joint_step_delta_time_0() { - let mut pc = crate::prelude::PhysicsContext::<(), ()> { + let mut pc = crate::prelude::PhysicsContext { query_pipeline: None, gravity: Vector::y() * -9.81, integration_parameters: IntegrationParameters { @@ -885,7 +885,7 @@ mod test { pc.impulse_joint_set.insert(h, h_dynamic, joint, true); // Step once - pc.step(); + pc.step(&(), &()); let translation = pc.bodies[h_dynamic].translation(); let rotation = pc.bodies[h_dynamic].rotation(); assert!(translation.x.is_finite()); From 488cda352e4336be95aaaadb7202aeb9628397a9 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Tue, 18 Feb 2025 16:44:36 +0100 Subject: [PATCH 04/10] update testbed code to use new PhysicsContext --- src/physics_context.rs | 12 +-- src/pipeline/physics_pipeline.rs | 10 +- src_testbed/debug_render.rs | 10 +- src_testbed/harness/mod.rs | 46 ++++----- src_testbed/physics/mod.rs | 27 +---- src_testbed/testbed.rs | 168 ++++++++++++++++++------------- 6 files changed, 133 insertions(+), 140 deletions(-) diff --git a/src/physics_context.rs b/src/physics_context.rs index 8c9602420..392c84470 100644 --- a/src/physics_context.rs +++ b/src/physics_context.rs @@ -13,8 +13,8 @@ pub struct PhysicsContext { pub narrow_phase: NarrowPhase, pub bodies: RigidBodySet, pub colliders: ColliderSet, - pub impulse_joint_set: ImpulseJointSet, - pub multibody_joint_set: MultibodyJointSet, + pub impulse_joints: ImpulseJointSet, + pub multibody_joints: MultibodyJointSet, pub ccd_solver: CCDSolver, pub query_pipeline: Option, } @@ -30,8 +30,8 @@ impl Default for PhysicsContext { narrow_phase: NarrowPhase::new(), bodies: RigidBodySet::new(), colliders: ColliderSet::new(), - impulse_joint_set: ImpulseJointSet::new(), - multibody_joint_set: MultibodyJointSet::new(), + impulse_joints: ImpulseJointSet::new(), + multibody_joints: MultibodyJointSet::new(), ccd_solver: CCDSolver::new(), query_pipeline: Some(QueryPipeline::new()), } @@ -57,8 +57,8 @@ impl PhysicsContext { &mut self.narrow_phase, &mut self.bodies, &mut self.colliders, - &mut self.impulse_joint_set, - &mut self.multibody_joint_set, + &mut self.impulse_joints, + &mut self.multibody_joints, &mut self.ccd_solver, self.query_pipeline.as_mut(), hooks, diff --git a/src/pipeline/physics_pipeline.rs b/src/pipeline/physics_pipeline.rs index da2a24fe0..e8a76e34a 100644 --- a/src/pipeline/physics_pipeline.rs +++ b/src/pipeline/physics_pipeline.rs @@ -726,8 +726,8 @@ mod test { *h, &mut pc.island_manager, &mut pc.colliders, - &mut pc.impulse_joint_set, - &mut pc.multibody_joint_set, + &mut pc.impulse_joints, + &mut pc.multibody_joints, true, ); } @@ -809,8 +809,8 @@ mod test { b_handle, &mut pc.island_manager, &mut pc.colliders, - &mut pc.impulse_joint_set, - &mut pc.multibody_joint_set, + &mut pc.impulse_joints, + &mut pc.multibody_joints, true, ); @@ -882,7 +882,7 @@ mod test { let joint = RevoluteJointBuilder::new(Vector::z_axis()) .local_anchor1(point![0.0, 1.0, 0.0]) .local_anchor2(point![0.0, -3.0, 0.0]); - pc.impulse_joint_set.insert(h, h_dynamic, joint, true); + pc.impulse_joints.insert(h, h_dynamic, joint, true); // Step once pc.step(&(), &()); diff --git a/src_testbed/debug_render.rs b/src_testbed/debug_render.rs index 6bd538b85..aae99b1ea 100644 --- a/src_testbed/debug_render.rs +++ b/src_testbed/debug_render.rs @@ -74,11 +74,11 @@ fn debug_render_scene( let mut backend = BevyLinesRenderBackend { gizmos }; debug_render.pipeline.render( &mut backend, - &harness.physics.bodies, - &harness.physics.colliders, - &harness.physics.impulse_joints, - &harness.physics.multibody_joints, - &harness.physics.narrow_phase, + &harness.physics.context.bodies, + &harness.physics.context.colliders, + &harness.physics.context.impulse_joints, + &harness.physics.context.multibody_joints, + &harness.physics.context.narrow_phase, ); } } diff --git a/src_testbed/harness/mod.rs b/src_testbed/harness/mod.rs index 734625b4c..06dc27d96 100644 --- a/src_testbed/harness/mod.rs +++ b/src_testbed/harness/mod.rs @@ -132,7 +132,7 @@ impl Harness { } pub fn integration_parameters_mut(&mut self) -> &mut IntegrationParameters { - &mut self.physics.integration_parameters + &mut self.physics.context.integration_parameters } pub fn clear_callbacks(&mut self) { @@ -171,22 +171,22 @@ impl Harness { ) { // println!("Num bodies: {}", bodies.len()); // println!("Num impulse_joints: {}", impulse_joints.len()); - self.physics.gravity = gravity; - self.physics.bodies = bodies; - self.physics.colliders = colliders; - self.physics.impulse_joints = impulse_joints; - self.physics.multibody_joints = multibody_joints; + self.physics.context.gravity = gravity; + self.physics.context.bodies = bodies; + self.physics.context.colliders = colliders; + self.physics.context.impulse_joints = impulse_joints; + self.physics.context.multibody_joints = multibody_joints; self.physics.hooks = Box::new(hooks); - self.physics.islands = IslandManager::new(); - self.physics.broad_phase = DefaultBroadPhase::new(); - self.physics.narrow_phase = NarrowPhase::new(); + self.physics.context.island_manager = IslandManager::new(); + self.physics.context.broad_phase = DefaultBroadPhase::new(); + self.physics.context.narrow_phase = NarrowPhase::new(); self.state.timestep_id = 0; self.state.time = 0.0; - self.physics.ccd_solver = CCDSolver::new(); - self.physics.query_pipeline = QueryPipeline::new(); - self.physics.pipeline = PhysicsPipeline::new(); - self.physics.pipeline.counters.enable(); + self.physics.context.ccd_solver = CCDSolver::new(); + self.physics.context.query_pipeline = Some(QueryPipeline::new()); + self.physics.context.physics_pipeline = PhysicsPipeline::new(); + self.physics.context.physics_pipeline.counters.enable(); } pub fn add_plugin(&mut self, plugin: impl HarnessPlugin + 'static) { @@ -232,21 +232,9 @@ impl Harness { } #[cfg(not(feature = "parallel"))] - self.physics.pipeline.step( - &self.physics.gravity, - &self.physics.integration_parameters, - &mut self.physics.islands, - &mut self.physics.broad_phase, - &mut self.physics.narrow_phase, - &mut self.physics.bodies, - &mut self.physics.colliders, - &mut self.physics.impulse_joints, - &mut self.physics.multibody_joints, - &mut self.physics.ccd_solver, - Some(&mut self.physics.query_pipeline), - &*self.physics.hooks, - &self.event_handler, - ); + self.physics + .context + .step(&*self.physics.hooks, &self.event_handler); for plugin in &mut self.plugins { plugin.step(&mut self.physics, &self.state) @@ -267,7 +255,7 @@ impl Harness { self.events.poll_all(); - self.state.time += self.physics.integration_parameters.dt as f32; + self.state.time += self.physics.context.integration_parameters.dt as f32; self.state.timestep_id += 1; } diff --git a/src_testbed/physics/mod.rs b/src_testbed/physics/mod.rs index b08d7f57d..2e7c1c886 100644 --- a/src_testbed/physics/mod.rs +++ b/src_testbed/physics/mod.rs @@ -8,6 +8,7 @@ use rapier::geometry::{ }; use rapier::math::{Real, Vector}; use rapier::pipeline::{PhysicsHooks, PhysicsPipeline, QueryPipeline}; +use rapier::prelude::PhysicsContext; pub struct PhysicsSnapshot { timestep_id: usize, @@ -88,18 +89,7 @@ impl PhysicsSnapshot { } pub struct PhysicsState { - pub islands: IslandManager, - pub broad_phase: DefaultBroadPhase, - pub narrow_phase: NarrowPhase, - pub bodies: RigidBodySet, - pub colliders: ColliderSet, - pub impulse_joints: ImpulseJointSet, - pub multibody_joints: MultibodyJointSet, - pub ccd_solver: CCDSolver, - pub pipeline: PhysicsPipeline, - pub query_pipeline: QueryPipeline, - pub integration_parameters: IntegrationParameters, - pub gravity: Vector, + pub context: PhysicsContext, pub hooks: Box, } @@ -112,18 +102,7 @@ impl Default for PhysicsState { impl PhysicsState { pub fn new() -> Self { Self { - islands: IslandManager::new(), - broad_phase: DefaultBroadPhase::new(), - narrow_phase: NarrowPhase::new(), - bodies: RigidBodySet::new(), - colliders: ColliderSet::new(), - impulse_joints: ImpulseJointSet::new(), - multibody_joints: MultibodyJointSet::new(), - ccd_solver: CCDSolver::new(), - pipeline: PhysicsPipeline::new(), - query_pipeline: QueryPipeline::new(), - integration_parameters: IntegrationParameters::default(), - gravity: Vector::y() * -9.81, + context: PhysicsContext::default(), hooks: Box::new(()), } } diff --git a/src_testbed/testbed.rs b/src_testbed/testbed.rs index 37b571013..4c59f5828 100644 --- a/src_testbed/testbed.rs +++ b/src_testbed/testbed.rs @@ -339,6 +339,7 @@ impl TestbedApp { self.state.selected_backend = backend_id; self.harness .physics + .context .integration_parameters .num_solver_iterations = NonZeroUsize::new(4).unwrap(); @@ -364,12 +365,12 @@ impl TestbedApp { { if self.state.selected_backend == BOX2D_BACKEND { self.other_backends.box2d.as_mut().unwrap().step( - &mut self.harness.physics.pipeline.counters, - &self.harness.physics.integration_parameters, + &mut self.harness.physics.context.physics_pipeline.counters, + &self.harness.physics.context.integration_parameters, ); self.other_backends.box2d.as_mut().unwrap().sync( - &mut self.harness.physics.bodies, - &mut self.harness.physics.colliders, + &mut self.harness.physics.context.bodies, + &mut self.harness.physics.context.colliders, ); } } @@ -381,12 +382,12 @@ impl TestbedApp { { // println!("Step"); self.other_backends.physx.as_mut().unwrap().step( - &mut self.harness.physics.pipeline.counters, - &self.harness.physics.integration_parameters, + &mut self.harness.physics.context.physics_pipeline.counters, + &self.harness.physics.context.integration_parameters, ); self.other_backends.physx.as_mut().unwrap().sync( - &mut self.harness.physics.bodies, - &mut self.harness.physics.colliders, + &mut self.harness.physics.context.bodies, + &mut self.harness.physics.context.colliders, ); } } @@ -394,8 +395,15 @@ impl TestbedApp { // Skip the first update. if k > 0 { - timings - .push(self.harness.physics.pipeline.counters.step_time.time_ms()); + timings.push( + self.harness + .physics + .context + .physics_pipeline + .counters + .step_time + .time_ms(), + ); } } results.push(timings); @@ -555,7 +563,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { } pub fn integration_parameters_mut(&mut self) -> &mut IntegrationParameters { - &mut self.harness.physics.integration_parameters + &mut self.harness.physics.context.integration_parameters } pub fn physics_state_mut(&mut self) -> &mut PhysicsState { @@ -757,10 +765,16 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { wheels[1].steering = steering_angle; vehicle.update_vehicle( - self.harness.physics.integration_parameters.dt, - &mut self.harness.physics.bodies, - &self.harness.physics.colliders, - &self.harness.physics.query_pipeline, + self.harness.physics.context.integration_parameters.dt, + &mut self.harness.physics.context.bodies, + &self.harness.physics.context.colliders, + &self + .harness + .physics + .context + .query_pipeline + .as_ref() + .unwrap(), QueryFilter::exclude_dynamic().exclude_rigid_body(vehicle.chassis), ); } @@ -844,16 +858,16 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let controller = self.state.character_controller.unwrap_or_default(); let phx = &mut self.harness.physics; - let character_body = &phx.bodies[character_handle]; - let character_collider = &phx.colliders[character_body.colliders()[0]]; + let character_body = &phx.context.bodies[character_handle]; + let character_collider = &phx.context.colliders[character_body.colliders()[0]]; let character_mass = character_body.mass(); let mut collisions = vec![]; let mvt = controller.move_shape( - phx.integration_parameters.dt, - &phx.bodies, - &phx.colliders, - &phx.query_pipeline, + phx.context.integration_parameters.dt, + &phx.context.bodies, + &phx.context.colliders, + &phx.context.query_pipeline.as_ref().unwrap(), character_collider.shape(), character_collider.position(), desired_movement.cast::(), @@ -876,17 +890,17 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { } } controller.solve_character_collision_impulses( - phx.integration_parameters.dt, - &mut phx.bodies, - &phx.colliders, - &phx.query_pipeline, + phx.context.integration_parameters.dt, + &mut phx.context.bodies, + &phx.context.colliders, + &phx.context.query_pipeline.as_ref().unwrap(), character_collider.shape(), character_mass, &*collisions, QueryFilter::new().exclude_rigid_body(character_handle), ); - let character_body = &mut phx.bodies[character_handle]; + let character_body = &mut phx.context.bodies[character_handle]; let pos = character_body.position(); character_body.set_next_kinematic_translation(pos.translation.vector + mvt.translation); // character_body.set_translation(pos.translation.vector + mvt.translation, false); @@ -917,6 +931,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let mut colliders: Vec<_> = self .harness .physics + .context .bodies .iter() .filter(|e| e.1.is_dynamic()) @@ -928,12 +943,15 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let num_to_delete = (colliders.len() / 10).max(0); for to_delete in &colliders[..num_to_delete] { if let Some(graphics) = self.graphics.as_mut() { - graphics.remove_collider(to_delete[0], &self.harness.physics.colliders); + graphics.remove_collider( + to_delete[0], + &self.harness.physics.context.colliders, + ); } - self.harness.physics.colliders.remove( + self.harness.physics.context.colliders.remove( to_delete[0], - &mut self.harness.physics.islands, - &mut self.harness.physics.bodies, + &mut self.harness.physics.context.island_manager, + &mut self.harness.physics.context.bodies, true, ); } @@ -943,6 +961,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let dynamic_bodies: Vec<_> = self .harness .physics + .context .bodies .iter() .filter(|e| e.1.is_dynamic()) @@ -953,12 +972,12 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { if let Some(graphics) = self.graphics.as_mut() { graphics.remove_body(*to_delete); } - self.harness.physics.bodies.remove( + self.harness.physics.context.bodies.remove( *to_delete, - &mut self.harness.physics.islands, - &mut self.harness.physics.colliders, - &mut self.harness.physics.impulse_joints, - &mut self.harness.physics.multibody_joints, + &mut self.harness.physics.context.island_manager, + &mut self.harness.physics.context.colliders, + &mut self.harness.physics.context.impulse_joints, + &mut self.harness.physics.context.multibody_joints, true, ); } @@ -968,13 +987,18 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let impulse_joints: Vec<_> = self .harness .physics + .context .impulse_joints .iter() .map(|e| e.0) .collect(); let num_to_delete = (impulse_joints.len() / 10).max(0); for to_delete in &impulse_joints[..num_to_delete] { - self.harness.physics.impulse_joints.remove(*to_delete, true); + self.harness + .physics + .context + .impulse_joints + .remove(*to_delete, true); } } KeyCode::KeyA => { @@ -982,6 +1006,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let multibody_joints: Vec<_> = self .harness .physics + .context .multibody_joints .iter() .map(|e| e.0) @@ -990,6 +1015,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { for to_delete in &multibody_joints[..num_to_delete] { self.harness .physics + .context .multibody_joints .remove(*to_delete, true); } @@ -999,6 +1025,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let to_delete = self .harness .physics + .context .multibody_joints .iter() .next() @@ -1006,6 +1033,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { if let Some(to_delete) = to_delete { self.harness .physics + .context .multibody_joints .remove_multibody_articulations(to_delete, true); } @@ -1331,13 +1359,13 @@ fn update_testbed( .set(TestbedActionFlags::TAKE_SNAPSHOT, false); state.snapshot = PhysicsSnapshot::new( harness.state.timestep_id, - &harness.physics.broad_phase, - &harness.physics.narrow_phase, - &harness.physics.islands, - &harness.physics.bodies, - &harness.physics.colliders, - &harness.physics.impulse_joints, - &harness.physics.multibody_joints, + &harness.physics.context.broad_phase, + &harness.physics.context.narrow_phase, + &harness.physics.context.island_manager, + &harness.physics.context.bodies, + &harness.physics.context.colliders, + &harness.physics.context.impulse_joints, + &harness.physics.context.multibody_joints, ) .ok(); @@ -1372,14 +1400,14 @@ fn update_testbed( } harness.state.timestep_id = timestep_id; - harness.physics.broad_phase = broad_phase; - harness.physics.narrow_phase = narrow_phase; - harness.physics.islands = island_manager; - harness.physics.bodies = bodies; - harness.physics.colliders = colliders; - harness.physics.impulse_joints = impulse_joints; - harness.physics.multibody_joints = multibody_joints; - harness.physics.query_pipeline = QueryPipeline::new(); + harness.physics.context.broad_phase = broad_phase; + harness.physics.context.narrow_phase = narrow_phase; + harness.physics.context.island_manager = island_manager; + harness.physics.context.bodies = bodies; + harness.physics.context.colliders = colliders; + harness.physics.context.impulse_joints = impulse_joints; + harness.physics.context.multibody_joints = multibody_joints; + harness.physics.context.query_pipeline = Some(QueryPipeline::new()); state .action_flags @@ -1395,25 +1423,25 @@ fn update_testbed( state .action_flags .set(TestbedActionFlags::RESET_WORLD_GRAPHICS, false); - for (handle, _) in harness.physics.bodies.iter() { + for (handle, _) in harness.physics.context.bodies.iter() { graphics.add_body_colliders( &mut commands, meshes, materials, &mut gfx_components, handle, - &harness.physics.bodies, - &harness.physics.colliders, + &harness.physics.context.bodies, + &harness.physics.context.colliders, ); } - for (handle, _) in harness.physics.colliders.iter() { + for (handle, _) in harness.physics.context.colliders.iter() { graphics.add_collider( &mut commands, meshes, materials, handle, - &harness.physics.colliders, + &harness.physics.context.colliders, ); } @@ -1434,7 +1462,7 @@ fn update_testbed( != state.flags.contains(TestbedStateFlags::WIREFRAME) { graphics.toggle_wireframe_mode( - &harness.physics.colliders, + &harness.physics.context.colliders, state.flags.contains(TestbedStateFlags::WIREFRAME), ) } @@ -1443,14 +1471,14 @@ fn update_testbed( != state.flags.contains(TestbedStateFlags::SLEEP) { if state.flags.contains(TestbedStateFlags::SLEEP) { - for (_, body) in harness.physics.bodies.iter_mut() { + for (_, body) in harness.physics.context.bodies.iter_mut() { body.activation_mut().normalized_linear_threshold = RigidBodyActivation::default_normalized_linear_threshold(); body.activation_mut().angular_threshold = RigidBodyActivation::default_angular_threshold(); } } else { - for (_, body) in harness.physics.bodies.iter_mut() { + for (_, body) in harness.physics.context.bodies.iter_mut() { body.wake_up(true); body.activation_mut().normalized_linear_threshold = -1.0; } @@ -1544,8 +1572,8 @@ fn update_testbed( }; graphics.draw( - &harness.physics.bodies, - &harness.physics.colliders, + &harness.physics.context.bodies, + &harness.physics.context.colliders, &mut gfx_components, &mut *materials, ); @@ -1562,7 +1590,10 @@ fn update_testbed( } if state.flags.contains(TestbedStateFlags::CONTACT_POINTS) { - draw_contacts(&harness.physics.narrow_phase, &harness.physics.colliders); + draw_contacts( + &harness.physics.context.narrow_phase, + &harness.physics.context.colliders, + ); } if state.running == RunMode::Step { @@ -1630,17 +1661,12 @@ fn highlight_hovered_body( let ray_dir = Vector3::new(ray_dir.x as Real, ray_dir.y as Real, ray_dir.z as Real); let ray = Ray::new(ray_origin, ray_dir); - let hit = physics.query_pipeline.cast_ray( - &physics.bodies, - &physics.colliders, - &ray, - Real::MAX, - true, - QueryFilter::only_dynamic(), - ); + let hit = physics + .context + .cast_ray(&ray, Real::MAX, true, QueryFilter::only_dynamic()); if let Some((handle, _)) = hit { - let collider = &physics.colliders[handle]; + let collider = &physics.context.colliders[handle]; if let Some(parent_handle) = collider.parent() { testbed_state.highlighted_body = Some(parent_handle); From 69c2c79c5febe04305a3bf344d92aef0761e6649 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Tue, 18 Feb 2025 16:45:47 +0100 Subject: [PATCH 05/10] fix clippy --- src/physics_context.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/physics_context.rs b/src/physics_context.rs index 392c84470..1e79ecc62 100644 --- a/src/physics_context.rs +++ b/src/physics_context.rs @@ -155,7 +155,7 @@ impl PhysicsContext { } /// Shortcut to [`QueryPipeline::intersections_with_ray`] - pub fn intersections_with_ray<'a>( + pub fn intersections_with_ray( &self, ray: &Ray, max_toi: Real, From d06cabbe204ae74cceb91a8e81cc0b81517bc619 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Mon, 24 Feb 2025 10:52:04 +0100 Subject: [PATCH 06/10] fix clippy --- examples2d/add_remove2.rs | 22 ++++------ examples2d/ccd2.rs | 2 + examples2d/character_controller2.rs | 2 +- examples2d/debug_compression2.rs | 4 +- examples2d/debug_intersection2.rs | 8 ++-- examples2d/drum2.rs | 6 ++- examples2d/inverse_kinematics2.rs | 4 +- examples2d/one_way_platforms2.rs | 17 ++++---- examples2d/platform2.rs | 14 +++++-- examples2d/sensor2.rs | 8 +++- examples3d-f64/debug_serialized3.rs | 8 ++-- examples3d/ccd3.rs | 2 + examples3d/character_controller3.rs | 2 +- examples3d/debug_add_remove_collider3.rs | 14 ++++--- examples3d/debug_deserialize3.rs | 11 ++--- examples3d/debug_dynamic_collider_add3.rs | 30 +++++++------- examples3d/debug_rollback3.rs | 2 +- examples3d/debug_shape_modification3.rs | 9 ++-- examples3d/fountain3.rs | 33 ++++++--------- examples3d/inverse_kinematics3.rs | 4 +- examples3d/joint_motor_position3.rs | 11 +++-- examples3d/one_way_platforms3.rs | 18 ++++---- examples3d/platform3.rs | 14 +++++-- examples3d/sensor3.rs | 8 +++- examples3d/vehicle_joints3.rs | 2 + src/counters/ccd_counters.rs | 2 +- src/counters/collision_detection_counters.rs | 2 +- src/counters/solver_counters.rs | 2 +- src/counters/stages_counters.rs | 2 +- src/physics_context.rs | 25 +++++++++++- src_testbed/harness/mod.rs | 43 ++++++++++++-------- src_testbed/ui.rs | 38 ++++++++++------- 32 files changed, 217 insertions(+), 152 deletions(-) diff --git a/examples2d/add_remove2.rs b/examples2d/add_remove2.rs index b8aef26b0..0366c3193 100644 --- a/examples2d/add_remove2.rs +++ b/examples2d/add_remove2.rs @@ -26,7 +26,7 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |mut graphics, physics, _, state| { let rot = state.time * -1.0; for rb_handle in &platform_handles { - let rb = physics.bodies.get_mut(*rb_handle).unwrap(); + let rb = physics.context.bodies.get_mut(*rb_handle).unwrap(); rb.set_next_kinematic_rotation(UnitComplex::new(rot)); } @@ -34,32 +34,24 @@ pub fn init_world(testbed: &mut Testbed) { let x = rand::random::() * 10.0 - 5.0; let y = rand::random::() * 10.0 + 10.0; let rigid_body = RigidBodyBuilder::dynamic().translation(vector![x, y]); - let handle = physics.bodies.insert(rigid_body); - let collider = ColliderBuilder::cuboid(rad, rad); - physics - .colliders - .insert_with_parent(collider, handle, &mut physics.bodies); + let (handle, _) = physics + .context + .insert_body_and_collider(rigid_body, ColliderBuilder::cuboid(rad, rad)); if let Some(graphics) = &mut graphics { - graphics.add_body(handle, &physics.bodies, &physics.colliders); + graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); } } let to_remove: Vec<_> = physics + .context .bodies .iter() .filter(|(_, b)| b.position().translation.vector.y < -10.0) .map(|e| e.0) .collect(); for handle in to_remove { - physics.bodies.remove( - handle, - &mut physics.islands, - &mut physics.colliders, - &mut physics.impulse_joints, - &mut physics.multibody_joints, - true, - ); + physics.context.remove_rigidbody(handle, true); if let Some(graphics) = &mut graphics { graphics.remove_body(handle); diff --git a/examples2d/ccd2.rs b/examples2d/ccd2.rs index 12468dc1d..b8c8251ac 100644 --- a/examples2d/ccd2.rs +++ b/examples2d/ccd2.rs @@ -95,12 +95,14 @@ pub fn init_world(testbed: &mut Testbed) { }; let parent_handle1 = physics + .context .colliders .get(prox.collider1()) .unwrap() .parent() .unwrap(); let parent_handle2 = physics + .context .colliders .get(prox.collider2()) .unwrap() diff --git a/examples2d/character_controller2.rs b/examples2d/character_controller2.rs index 2acf50ffa..55c0bac70 100644 --- a/examples2d/character_controller2.rs +++ b/examples2d/character_controller2.rs @@ -153,7 +153,7 @@ pub fn init_world(testbed: &mut Testbed) { // let angvel = run_state.time.sin() * 0.5; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics.bodies.get_mut(platform_handle) { + if let Some(platform) = physics.context.bodies.get_mut(platform_handle) { platform.set_linvel(linvel, true); // NOTE: interaction with rotating platforms isn’t handled very well yet. // platform.set_angvel(angvel, true); diff --git a/examples2d/debug_compression2.rs b/examples2d/debug_compression2.rs index e0052d616..04bfce4bf 100644 --- a/examples2d/debug_compression2.rs +++ b/examples2d/debug_compression2.rs @@ -54,11 +54,11 @@ pub fn init_world(testbed: &mut Testbed) { let mut force = vector![0.0, 0.0]; testbed.add_callback(move |_, physics, _, _| { - let left_plank = &mut physics.bodies[handles[0]]; + let left_plank = &mut physics.context.bodies[handles[0]]; left_plank.reset_forces(true); left_plank.add_force(force, true); - let right_plank = &mut physics.bodies[handles[1]]; + let right_plank = &mut physics.context.bodies[handles[1]]; right_plank.reset_forces(true); right_plank.add_force(-force, true); diff --git a/examples2d/debug_intersection2.rs b/examples2d/debug_intersection2.rs index f54521a3b..f2a7339f4 100644 --- a/examples2d/debug_intersection2.rs +++ b/examples2d/debug_intersection2.rs @@ -41,20 +41,18 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |graphics, physics, _, run| { let slow_time = run.timestep_id as f32 / 3.0; - let intersection = physics.query_pipeline.intersection_with_shape( - &physics.bodies, - &physics.colliders, + let intersection = physics.context.intersection_with_shape( &Isometry::translation(slow_time.cos() * 10.0, slow_time.sin() * 10.0), &Ball::new(rad / 2.0), QueryFilter::default(), ); if let Some(graphics) = graphics { - for (handle, _) in physics.bodies.iter() { + for (handle, _) in physics.context.bodies.iter() { graphics.set_body_color(handle, [0.5, 0.5, 0.5]); } if let Some(intersection) = intersection { - let collider = physics.colliders.get(intersection).unwrap(); + let collider = physics.context.colliders.get(intersection).unwrap(); let body_handle = collider.parent().unwrap(); graphics.set_body_color(body_handle, [1.0, 0.0, 0.0]); diff --git a/examples2d/drum2.rs b/examples2d/drum2.rs index 54588c870..9a58f56ab 100644 --- a/examples2d/drum2.rs +++ b/examples2d/drum2.rs @@ -66,7 +66,11 @@ pub fn init_world(testbed: &mut Testbed) { */ testbed.add_callback(move |_, physics, _, _| { // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics.bodies.get_mut(velocity_based_platform_handle) { + if let Some(platform) = physics + .context + .bodies + .get_mut(velocity_based_platform_handle) + { platform.set_angvel(-0.15, true); } }); diff --git a/examples2d/inverse_kinematics2.rs b/examples2d/inverse_kinematics2.rs index bb6212787..34604d00e 100644 --- a/examples2d/inverse_kinematics2.rs +++ b/examples2d/inverse_kinematics2.rs @@ -57,7 +57,7 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |graphics, physics, _, _| { let Some(graphics) = graphics else { return }; - if let Some((multibody, link_id)) = physics.multibody_joints.get_mut(last_link) { + if let Some((multibody, link_id)) = physics.context.multibody_joints.get_mut(last_link) { // Ensure our displacement vector has the right number of elements. if displacements.nrows() < multibody.ndofs() { displacements = DVector::zeros(multibody.ndofs()); @@ -78,7 +78,7 @@ pub fn init_world(testbed: &mut Testbed) { }; multibody.inverse_kinematics( - &physics.bodies, + &physics.context.bodies, link_id, &options, &Isometry::from(target_point), diff --git a/examples2d/one_way_platforms2.rs b/examples2d/one_way_platforms2.rs index d16d0cc9b..da7b37e41 100644 --- a/examples2d/one_way_platforms2.rs +++ b/examples2d/one_way_platforms2.rs @@ -90,22 +90,21 @@ pub fn init_world(testbed: &mut Testbed) { * depending on their position. */ testbed.add_callback(move |graphics, physics, _, run_state| { - if run_state.timestep_id % 200 == 0 && physics.bodies.len() <= 7 { + if run_state.timestep_id % 200 == 0 && physics.context.bodies.len() <= 7 { // Spawn a new cube. let collider = ColliderBuilder::cuboid(1.5, 2.0); - let body = RigidBodyBuilder::dynamic().translation(vector![20.0, 10.0]); - let handle = physics.bodies.insert(body); - physics - .colliders - .insert_with_parent(collider, handle, &mut physics.bodies); + let (handle, _) = physics.context.insert_body_and_collider( + RigidBodyBuilder::dynamic().translation(vector![20.0, 10.0]), + collider, + ); if let Some(graphics) = graphics { - graphics.add_body(handle, &physics.bodies, &physics.colliders); + graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); } } - for handle in physics.islands.active_dynamic_bodies() { - let body = &mut physics.bodies[*handle]; + for handle in physics.context.island_manager.active_dynamic_bodies() { + let body = &mut physics.context.bodies[*handle]; if body.position().translation.y > 1.0 { body.set_gravity_scale(1.0, false); } else if body.position().translation.y < -1.0 { diff --git a/examples2d/platform2.rs b/examples2d/platform2.rs index c2405186c..18b5ee994 100644 --- a/examples2d/platform2.rs +++ b/examples2d/platform2.rs @@ -69,14 +69,22 @@ pub fn init_world(testbed: &mut Testbed) { let velocity = vector![run_state.time.sin() * 5.0, (run_state.time * 5.0).sin()]; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics.bodies.get_mut(velocity_based_platform_handle) { + if let Some(platform) = physics + .context + .bodies + .get_mut(velocity_based_platform_handle) + { platform.set_linvel(velocity, true); } // Update the position-based kinematic body by setting its next position. - if let Some(platform) = physics.bodies.get_mut(position_based_platform_handle) { + if let Some(platform) = physics + .context + .bodies + .get_mut(position_based_platform_handle) + { let mut next_tra = *platform.translation(); - next_tra += velocity * physics.integration_parameters.dt; + next_tra += velocity * physics.context.integration_parameters.dt; platform.set_next_kinematic_translation(next_tra); } }); diff --git a/examples2d/sensor2.rs b/examples2d/sensor2.rs index 595ad3b0b..2a845d87a 100644 --- a/examples2d/sensor2.rs +++ b/examples2d/sensor2.rs @@ -75,8 +75,12 @@ pub fn init_world(testbed: &mut Testbed) { [0.5, 0.5, 1.0] }; - let parent_handle1 = physics.colliders[prox.collider1()].parent().unwrap(); - let parent_handle2 = physics.colliders[prox.collider2()].parent().unwrap(); + let parent_handle1 = physics.context.colliders[prox.collider1()] + .parent() + .unwrap(); + let parent_handle2 = physics.context.colliders[prox.collider2()] + .parent() + .unwrap(); if let Some(graphics) = &mut graphics { if parent_handle1 != ground_handle && parent_handle1 != sensor_handle { diff --git a/examples3d-f64/debug_serialized3.rs b/examples3d-f64/debug_serialized3.rs index 3801d37b5..71d4364bb 100644 --- a/examples3d-f64/debug_serialized3.rs +++ b/examples3d-f64/debug_serialized3.rs @@ -26,10 +26,10 @@ pub fn init_world(testbed: &mut Testbed) { state.impulse_joints, state.multibody_joints, ); - testbed.harness_mut().physics.islands = state.islands; - testbed.harness_mut().physics.broad_phase = state.broad_phase; - testbed.harness_mut().physics.narrow_phase = state.narrow_phase; - testbed.harness_mut().physics.ccd_solver = state.ccd_solver; + testbed.harness_mut().physics.context.island_manager = state.islands; + testbed.harness_mut().physics.context.broad_phase = state.broad_phase; + testbed.harness_mut().physics.context.narrow_phase = state.narrow_phase; + testbed.harness_mut().physics.context.ccd_solver = state.ccd_solver; testbed.set_graphics_shift(vector![-541.0, -6377257.0, -61.0]); testbed.look_at(point![10.0, 10.0, 10.0], point![0.0, 0.0, 0.0]); diff --git a/examples3d/ccd3.rs b/examples3d/ccd3.rs index c1a5176a4..40e01515c 100644 --- a/examples3d/ccd3.rs +++ b/examples3d/ccd3.rs @@ -120,12 +120,14 @@ pub fn init_world(testbed: &mut Testbed) { }; let parent_handle1 = physics + .context .colliders .get(prox.collider1()) .unwrap() .parent() .unwrap(); let parent_handle2 = physics + .context .colliders .get(prox.collider2()) .unwrap() diff --git a/examples3d/character_controller3.rs b/examples3d/character_controller3.rs index ce96bf8a8..1f83e615d 100644 --- a/examples3d/character_controller3.rs +++ b/examples3d/character_controller3.rs @@ -169,7 +169,7 @@ pub fn init_world(testbed: &mut Testbed) { // let angvel = run_state.time.sin() * 0.5; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics.bodies.get_mut(platform_handle) { + if let Some(platform) = physics.context.bodies.get_mut(platform_handle) { platform.set_linvel(linvel, true); // NOTE: interaction with rotating platforms isn’t handled very well yet. // platform.set_angvel(angvel, true); diff --git a/examples3d/debug_add_remove_collider3.rs b/examples3d/debug_add_remove_collider3.rs index 25bb23a33..7ec6f274d 100644 --- a/examples3d/debug_add_remove_collider3.rs +++ b/examples3d/debug_add_remove_collider3.rs @@ -35,18 +35,20 @@ pub fn init_world(testbed: &mut Testbed) { // Remove then re-add the ground collider. let removed_collider_handle = ground_collider_handle; let coll = physics + .context .colliders .remove( removed_collider_handle, - &mut physics.islands, - &mut physics.bodies, + &mut physics.context.island_manager, + &mut physics.context.bodies, true, ) .unwrap(); - ground_collider_handle = - physics - .colliders - .insert_with_parent(coll, ground_handle, &mut physics.bodies); + ground_collider_handle = physics.context.colliders.insert_with_parent( + coll, + ground_handle, + &mut physics.context.bodies, + ); }); /* diff --git a/examples3d/debug_deserialize3.rs b/examples3d/debug_deserialize3.rs index 0762b4d1d..5aed78806 100644 --- a/examples3d/debug_deserialize3.rs +++ b/examples3d/debug_deserialize3.rs @@ -38,11 +38,12 @@ pub fn init_world(testbed: &mut Testbed) { state.impulse_joints, state.multibody_joints, ); - testbed.harness_mut().physics.islands = state.islands; - testbed.harness_mut().physics.broad_phase = state.broad_phase; - testbed.harness_mut().physics.narrow_phase = state.narrow_phase; - testbed.harness_mut().physics.integration_parameters = state.integration_parameters; - testbed.harness_mut().physics.gravity = state.gravity; + testbed.harness_mut().physics.context.island_manager = state.islands; + testbed.harness_mut().physics.context.broad_phase = state.broad_phase; + testbed.harness_mut().physics.context.narrow_phase = state.narrow_phase; + testbed.harness_mut().physics.context.integration_parameters = + state.integration_parameters; + testbed.harness_mut().physics.context.gravity = state.gravity; testbed.set_graphics_shift(vector![-541.0, -6377257.0, -61.0]); testbed.look_at(point![10.0, 10.0, 10.0], point![0.0, 0.0, 0.0]); diff --git a/examples3d/debug_dynamic_collider_add3.rs b/examples3d/debug_dynamic_collider_add3.rs index fa1054cc0..ab8801b98 100644 --- a/examples3d/debug_dynamic_collider_add3.rs +++ b/examples3d/debug_dynamic_collider_add3.rs @@ -47,19 +47,20 @@ pub fn init_world(testbed: &mut Testbed) { // Add a bigger ball collider let collider = ColliderBuilder::ball(ball_rad + 0.01 * (step as f32)).density(100.0); - let new_ball_collider_handle = - physics - .colliders - .insert_with_parent(collider, ball_handle, &mut physics.bodies); + let new_ball_collider_handle = physics.context.colliders.insert_with_parent( + collider, + ball_handle, + &mut physics.context.bodies, + ); if let Some(graphics) = &mut graphics { - graphics.add_collider(new_ball_collider_handle, &physics.colliders); + graphics.add_collider(new_ball_collider_handle, &physics.context.colliders); } extra_colliders.push(new_ball_collider_handle); // Snap the ball velocity or restore it. - let ball = physics.bodies.get_mut(ball_handle).unwrap(); + let ball = physics.context.bodies.get_mut(ball_handle).unwrap(); if step == snapped_frame { linvel = *ball.linvel(); @@ -75,12 +76,10 @@ pub fn init_world(testbed: &mut Testbed) { for handle in &extra_colliders { if let Some(graphics) = &mut graphics { - graphics.remove_collider(*handle, &physics.colliders); + graphics.remove_collider(*handle, &physics.context.colliders); } - physics - .colliders - .remove(*handle, &mut physics.islands, &mut physics.bodies, true); + physics.context.remove_collider(*handle, true); } extra_colliders.clear(); @@ -95,13 +94,14 @@ pub fn init_world(testbed: &mut Testbed) { // .unwrap(); let coll = ColliderBuilder::cuboid(ground_size, ground_height + step as f32 * 0.01, 0.4) .friction(0.15); - let new_ground_collider_handle = - physics - .colliders - .insert_with_parent(coll, ground_handle, &mut physics.bodies); + let new_ground_collider_handle = physics.context.colliders.insert_with_parent( + coll, + ground_handle, + &mut physics.context.bodies, + ); if let Some(graphics) = &mut graphics { - graphics.add_collider(new_ground_collider_handle, &physics.colliders); + graphics.add_collider(new_ground_collider_handle, &physics.context.colliders); } extra_colliders.push(new_ground_collider_handle); diff --git a/examples3d/debug_rollback3.rs b/examples3d/debug_rollback3.rs index 9936e37bc..2a63c0734 100644 --- a/examples3d/debug_rollback3.rs +++ b/examples3d/debug_rollback3.rs @@ -45,7 +45,7 @@ pub fn init_world(testbed: &mut Testbed) { step += 1; // Snap the ball velocity or restore it. - let ball = physics.bodies.get_mut(ball_handle).unwrap(); + let ball = physics.context.bodies.get_mut(ball_handle).unwrap(); if step == snapped_frame { linvel = *ball.linvel(); diff --git a/examples3d/debug_shape_modification3.rs b/examples3d/debug_shape_modification3.rs index 897421879..d092904af 100644 --- a/examples3d/debug_shape_modification3.rs +++ b/examples3d/debug_shape_modification3.rs @@ -64,7 +64,7 @@ pub fn init_world(testbed: &mut Testbed) { step += 1; // Snap the ball velocity or restore it. - let ball = physics.bodies.get_mut(ball_handle).unwrap(); + let ball = physics.context.bodies.get_mut(ball_handle).unwrap(); if step == snapped_frame { linvel = *ball.linvel(); @@ -73,6 +73,7 @@ pub fn init_world(testbed: &mut Testbed) { } let shapeshifting_coll = physics + .context .colliders .get_mut(shapeshifting_coll_handle) .unwrap(); @@ -88,12 +89,12 @@ pub fn init_world(testbed: &mut Testbed) { step = snapped_frame; } - let ball_coll = physics.colliders.get_mut(ball_coll_handle).unwrap(); + let ball_coll = physics.context.colliders.get_mut(ball_coll_handle).unwrap(); ball_coll.set_shape(SharedShape::ball(ball_rad * step as f32 * 2.0)); if let Some(gfx) = &mut gfx { - gfx.update_collider(ball_coll_handle, &physics.colliders); - gfx.update_collider(shapeshifting_coll_handle, &physics.colliders); + gfx.update_collider(ball_coll_handle, &physics.context.colliders); + gfx.update_collider(shapeshifting_coll_handle, &physics.context.colliders); } }); diff --git a/examples3d/fountain3.rs b/examples3d/fountain3.rs index 3927cac69..854a86c4e 100644 --- a/examples3d/fountain3.rs +++ b/examples3d/fountain3.rs @@ -24,24 +24,22 @@ pub fn init_world(testbed: &mut Testbed) { // Callback that will be executed on the main loop to handle proximities. testbed.add_callback(move |mut graphics, physics, _, run_state| { - let rigid_body = RigidBodyBuilder::dynamic().translation(vector![0.0, 10.0, 0.0]); - let handle = physics.bodies.insert(rigid_body); - let collider = match run_state.timestep_id % 3 { - 0 => ColliderBuilder::round_cylinder(rad, rad, rad / 10.0), - 1 => ColliderBuilder::cone(rad, rad), - _ => ColliderBuilder::cuboid(rad, rad, rad), - }; - - physics - .colliders - .insert_with_parent(collider, handle, &mut physics.bodies); + physics.context.insert_body_and_collider( + RigidBodyBuilder::dynamic().translation(vector![0.0, 10.0, 0.0]), + match run_state.timestep_id % 3 { + 0 => ColliderBuilder::round_cylinder(rad, rad, rad / 10.0), + 1 => ColliderBuilder::cone(rad, rad), + _ => ColliderBuilder::cuboid(rad, rad, rad), + }, + ); if let Some(graphics) = &mut graphics { - graphics.add_body(handle, &physics.bodies, &physics.colliders); + graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); } - if physics.bodies.len() > MAX_NUMBER_OF_BODIES { + if physics.context.bodies.len() > MAX_NUMBER_OF_BODIES { let mut to_remove: Vec<_> = physics + .context .bodies .iter() .filter(|e| e.1.is_dynamic()) @@ -57,14 +55,7 @@ pub fn init_world(testbed: &mut Testbed) { let num_to_remove = to_remove.len() - MAX_NUMBER_OF_BODIES; for (handle, _) in &to_remove[..num_to_remove] { - physics.bodies.remove( - *handle, - &mut physics.islands, - &mut physics.colliders, - &mut physics.impulse_joints, - &mut physics.multibody_joints, - true, - ); + physics.context.remove_rigidbody(*handle, true); if let Some(graphics) = &mut graphics { graphics.remove_body(*handle); diff --git a/examples3d/inverse_kinematics3.rs b/examples3d/inverse_kinematics3.rs index 50cd589b7..cf12f3c33 100644 --- a/examples3d/inverse_kinematics3.rs +++ b/examples3d/inverse_kinematics3.rs @@ -57,7 +57,7 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |graphics, physics, _, _| { let Some(graphics) = graphics else { return }; - if let Some((multibody, link_id)) = physics.multibody_joints.get_mut(last_link) { + if let Some((multibody, link_id)) = physics.context.multibody_joints.get_mut(last_link) { // Ensure our displacement vector has the right number of elements. if displacements.nrows() < multibody.ndofs() { displacements = DVector::zeros(multibody.ndofs()); @@ -85,7 +85,7 @@ pub fn init_world(testbed: &mut Testbed) { }; multibody.inverse_kinematics( - &physics.bodies, + &physics.context.bodies, link_id, &options, &Isometry::from(target_point), diff --git a/examples3d/joint_motor_position3.rs b/examples3d/joint_motor_position3.rs index f89e880b8..1d9839442 100644 --- a/examples3d/joint_motor_position3.rs +++ b/examples3d/joint_motor_position3.rs @@ -63,9 +63,14 @@ pub fn init_world(testbed: &mut Testbed) { } testbed.add_callback(move |_, physics, _, state| { - for ((_, joint), target) in physics.impulse_joints.iter().zip(target_angles.iter()) { - let rb1 = &physics.bodies[joint.body1]; - let rb2 = &physics.bodies[joint.body2]; + for ((_, joint), target) in physics + .context + .impulse_joints + .iter() + .zip(target_angles.iter()) + { + let rb1 = &physics.context.bodies[joint.body1]; + let rb2 = &physics.context.bodies[joint.body2]; let revolute = joint.data.as_revolute().unwrap(); println!( "[Step {}] rev angle: {} (target = {})", diff --git a/examples3d/one_way_platforms3.rs b/examples3d/one_way_platforms3.rs index 1a5704c7b..7a11607d9 100644 --- a/examples3d/one_way_platforms3.rs +++ b/examples3d/one_way_platforms3.rs @@ -90,22 +90,24 @@ pub fn init_world(testbed: &mut Testbed) { * depending on their position. */ testbed.add_callback(move |graphics, physics, _, run_state| { - if run_state.timestep_id % 200 == 0 && physics.bodies.len() <= 7 { + if run_state.timestep_id % 200 == 0 && physics.context.bodies.len() <= 7 { // Spawn a new cube. let collider = ColliderBuilder::cuboid(1.0, 2.0, 1.5); let body = RigidBodyBuilder::dynamic().translation(vector![0.0, 6.0, 20.0]); - let handle = physics.bodies.insert(body); - physics - .colliders - .insert_with_parent(collider, handle, &mut physics.bodies); + let handle = physics.context.bodies.insert(body); + physics.context.colliders.insert_with_parent( + collider, + handle, + &mut physics.context.bodies, + ); if let Some(graphics) = graphics { - graphics.add_body(handle, &physics.bodies, &physics.colliders); + graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); } } - for handle in physics.islands.active_dynamic_bodies() { - let body = physics.bodies.get_mut(*handle).unwrap(); + for handle in physics.context.island_manager.active_dynamic_bodies() { + let body = physics.context.bodies.get_mut(*handle).unwrap(); if body.position().translation.y > 1.0 { body.set_gravity_scale(1.0, false); } else if body.position().translation.y < -1.0 { diff --git a/examples3d/platform3.rs b/examples3d/platform3.rs index 9025afa0b..f36b10134 100644 --- a/examples3d/platform3.rs +++ b/examples3d/platform3.rs @@ -80,15 +80,23 @@ pub fn init_world(testbed: &mut Testbed) { ]; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics.bodies.get_mut(velocity_based_platform_handle) { + if let Some(platform) = physics + .context + .bodies + .get_mut(velocity_based_platform_handle) + { platform.set_linvel(velocity, true); platform.set_angvel(vector![0.0, 0.2, 0.0], true); } // Update the position-based kinematic body by setting its next position. - if let Some(platform) = physics.bodies.get_mut(position_based_platform_handle) { + if let Some(platform) = physics + .context + .bodies + .get_mut(position_based_platform_handle) + { let mut next_tra = *platform.translation(); - next_tra += velocity * physics.integration_parameters.dt; + next_tra += velocity * physics.context.integration_parameters.dt; platform.set_next_kinematic_translation(next_tra); } }); diff --git a/examples3d/sensor3.rs b/examples3d/sensor3.rs index 479b0c652..2b40ae08f 100644 --- a/examples3d/sensor3.rs +++ b/examples3d/sensor3.rs @@ -79,8 +79,12 @@ pub fn init_world(testbed: &mut Testbed) { [0.5, 0.5, 1.0] }; - let parent_handle1 = physics.colliders[prox.collider1()].parent().unwrap(); - let parent_handle2 = physics.colliders[prox.collider2()].parent().unwrap(); + let parent_handle1 = physics.context.colliders[prox.collider1()] + .parent() + .unwrap(); + let parent_handle2 = physics.context.colliders[prox.collider2()] + .parent() + .unwrap(); if let Some(graphics) = &mut graphics { if parent_handle1 != ground_handle && parent_handle1 != sensor_handle { diff --git a/examples3d/vehicle_joints3.rs b/examples3d/vehicle_joints3.rs index 517bd9cb9..cc79af8c4 100644 --- a/examples3d/vehicle_joints3.rs +++ b/examples3d/vehicle_joints3.rs @@ -166,6 +166,7 @@ pub fn init_world(testbed: &mut Testbed) { // Apply steering to the axles. for steering_handle in &steering_joints { let steering_joint = physics + .context .impulse_joints .get_mut(*steering_handle, should_wake_up) .unwrap(); @@ -191,6 +192,7 @@ pub fn init_world(testbed: &mut Testbed) { let ms = [1.0 / speed_diff, speed_diff]; for (motor_handle, &ms) in motor_joints.iter().copied().zip(ms.iter()) { let motor_joint = physics + .context .impulse_joints .get_mut(motor_handle, should_wake_up) .unwrap(); diff --git a/src/counters/ccd_counters.rs b/src/counters/ccd_counters.rs index 682adfcb7..e0ef7c79f 100644 --- a/src/counters/ccd_counters.rs +++ b/src/counters/ccd_counters.rs @@ -2,7 +2,7 @@ use crate::counters::Timer; use std::fmt::{Display, Formatter, Result}; /// Performance counters related to continuous collision detection (CCD). -#[derive(Default, Clone, Copy)] +#[derive(Default, Debug, Clone, Copy)] pub struct CCDCounters { /// The number of substeps actually performed by the CCD resolution. pub num_substeps: usize, diff --git a/src/counters/collision_detection_counters.rs b/src/counters/collision_detection_counters.rs index 1d2d28fa8..89d5b51f4 100644 --- a/src/counters/collision_detection_counters.rs +++ b/src/counters/collision_detection_counters.rs @@ -2,7 +2,7 @@ use crate::counters::Timer; use std::fmt::{Display, Formatter, Result}; /// Performance counters related to collision detection. -#[derive(Default, Clone, Copy)] +#[derive(Default, Debug, Clone, Copy)] pub struct CollisionDetectionCounters { /// Number of contact pairs detected. pub ncontact_pairs: usize, diff --git a/src/counters/solver_counters.rs b/src/counters/solver_counters.rs index aced5f396..36bda7ba3 100644 --- a/src/counters/solver_counters.rs +++ b/src/counters/solver_counters.rs @@ -2,7 +2,7 @@ use crate::counters::Timer; use std::fmt::{Display, Formatter, Result}; /// Performance counters related to constraints resolution. -#[derive(Default, Clone, Copy)] +#[derive(Default, Debug, Clone, Copy)] pub struct SolverCounters { /// Number of constraints generated. pub nconstraints: usize, diff --git a/src/counters/stages_counters.rs b/src/counters/stages_counters.rs index 313498669..af4810aff 100644 --- a/src/counters/stages_counters.rs +++ b/src/counters/stages_counters.rs @@ -2,7 +2,7 @@ use crate::counters::Timer; use std::fmt::{Display, Formatter, Result}; /// Performance counters related to each stage of the time step. -#[derive(Default, Clone, Copy)] +#[derive(Default, Debug, Clone, Copy)] pub struct StagesCounters { /// Time spent for updating the kinematic and dynamics of every body. pub update_time: Timer, diff --git a/src/physics_context.rs b/src/physics_context.rs index 1e79ecc62..44be2cb43 100644 --- a/src/physics_context.rs +++ b/src/physics_context.rs @@ -4,9 +4,11 @@ use crate::prelude::*; /// Contains all arguments to be passed to [`PhysicsPipeline::step`] #[allow(missing_docs)] +#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))] pub struct PhysicsContext { pub gravity: Vector, pub integration_parameters: IntegrationParameters, + #[cfg_attr(feature = "serde-serialize", serde(skip))] pub physics_pipeline: PhysicsPipeline, pub island_manager: IslandManager, pub broad_phase: DefaultBroadPhase, @@ -79,8 +81,8 @@ impl PhysicsContext { /// Shortcut to [`RigidBodySet::insert`] and [`ColliderSet::insert_with_parent`] pub fn insert_body_and_collider( &mut self, - collider: impl Into, rb: impl Into, + collider: impl Into, ) -> (RigidBodyHandle, ColliderHandle) { let parent_handle = self.bodies.insert(rb); ( @@ -89,6 +91,27 @@ impl PhysicsContext { .insert_with_parent(collider, parent_handle, &mut self.bodies), ) } + + /// Shortcut to [`RigidBodySet::remove`] + pub fn remove_rigidbody( + &mut self, + handle: RigidBodyHandle, + remove_attached_colliders: bool, + ) -> Option { + self.bodies.remove( + handle, + &mut self.island_manager, + &mut self.colliders, + &mut self.impulse_joints, + &mut self.multibody_joints, + remove_attached_colliders, + ) + } + /// Shortcut to [`ColliderSet::remove`] + pub fn remove_collider(&mut self, handle: ColliderHandle, wake_up: bool) -> Option { + self.colliders + .remove(handle, &mut self.island_manager, &mut self.bodies, wake_up) + } } /// Shortcuts to [`QueryPipeline`] diff --git a/src_testbed/harness/mod.rs b/src_testbed/harness/mod.rs index 06dc27d96..ef5e9f106 100644 --- a/src_testbed/harness/mod.rs +++ b/src_testbed/harness/mod.rs @@ -5,13 +5,16 @@ use crate::{ TestbedGraphics, }; use plugin::HarnessPlugin; -use rapier::dynamics::{ - CCDSolver, ImpulseJointSet, IntegrationParameters, IslandManager, MultibodyJointSet, - RigidBodySet, -}; use rapier::geometry::{ColliderSet, DefaultBroadPhase, NarrowPhase}; use rapier::math::{Real, Vector}; use rapier::pipeline::{ChannelEventCollector, PhysicsHooks, PhysicsPipeline, QueryPipeline}; +use rapier::{ + dynamics::{ + CCDSolver, ImpulseJointSet, IntegrationParameters, IslandManager, MultibodyJointSet, + RigidBodySet, + }, + prelude::PhysicsContext, +}; pub mod plugin; @@ -171,22 +174,26 @@ impl Harness { ) { // println!("Num bodies: {}", bodies.len()); // println!("Num impulse_joints: {}", impulse_joints.len()); - self.physics.context.gravity = gravity; - self.physics.context.bodies = bodies; - self.physics.context.colliders = colliders; - self.physics.context.impulse_joints = impulse_joints; - self.physics.context.multibody_joints = multibody_joints; - self.physics.hooks = Box::new(hooks); - - self.physics.context.island_manager = IslandManager::new(); - self.physics.context.broad_phase = DefaultBroadPhase::new(); - self.physics.context.narrow_phase = NarrowPhase::new(); + self.physics = PhysicsState { + context: PhysicsContext { + gravity, + integration_parameters: IntegrationParameters::default(), + physics_pipeline: PhysicsPipeline::new(), + island_manager: IslandManager::new(), + broad_phase: DefaultBroadPhase::new(), + narrow_phase: NarrowPhase::new(), + bodies, + colliders, + impulse_joints, + multibody_joints, + ccd_solver: CCDSolver::new(), + query_pipeline: Some(QueryPipeline::new()), + }, + hooks: Box::new(hooks), + }; + self.physics.context.physics_pipeline.counters.enable(); self.state.timestep_id = 0; self.state.time = 0.0; - self.physics.context.ccd_solver = CCDSolver::new(); - self.physics.context.query_pipeline = Some(QueryPipeline::new()); - self.physics.context.physics_pipeline = PhysicsPipeline::new(); - self.physics.context.physics_pipeline.counters.enable(); } pub fn add_plugin(&mut self, plugin: impl HarnessPlugin + 'static) { diff --git a/src_testbed/ui.rs b/src_testbed/ui.rs index 5945c38b2..78b9d0025 100644 --- a/src_testbed/ui.rs +++ b/src_testbed/ui.rs @@ -122,7 +122,7 @@ pub fn update_ui( }); ui.collapsing("Profile infos", |ui| { ui.horizontal_wrapped(|ui| { - profiling_ui(ui, &harness.physics.pipeline.counters); + profiling_ui(ui, &harness.physics.context.physics_pipeline.counters); }); }); ui.collapsing("Serialization infos", |ui| { @@ -134,7 +134,7 @@ pub fn update_ui( }); }); - let integration_parameters = &mut harness.physics.integration_parameters; + let integration_parameters = &mut harness.physics.context.integration_parameters; if state.selected_backend == PHYSX_BACKEND_PATCH_FRICTION || state.selected_backend == PHYSX_BACKEND_TWO_FRICTION_DIR @@ -348,9 +348,12 @@ pub fn update_ui( } fn scene_infos_ui(ui: &mut Ui, physics: &PhysicsState) { - ui.label(format!("# rigid-bodies: {}", physics.bodies.len())); - ui.label(format!("# colliders: {}", physics.colliders.len())); - ui.label(format!("# impulse joint: {}", physics.impulse_joints.len())); + ui.label(format!("# rigid-bodies: {}", physics.context.bodies.len())); + ui.label(format!("# colliders: {}", physics.context.colliders.len())); + ui.label(format!( + "# impulse joint: {}", + physics.context.impulse_joints.len() + )); // ui.label(format!( // "# multibody joint: {}", // physics.multibody_joints.len() @@ -439,26 +442,30 @@ fn profiling_ui(ui: &mut Ui, counters: &Counters) { fn serialization_string(timestep_id: usize, physics: &PhysicsState) -> String { let t = Instant::now(); // let t = Instant::now(); - let bf = bincode::serialize(&physics.broad_phase).unwrap(); + let bf = bincode::serialize(&physics.context.broad_phase).unwrap(); // println!("bf: {}", Instant::now() - t); // let t = Instant::now(); - let nf = bincode::serialize(&physics.narrow_phase).unwrap(); + let nf = bincode::serialize(&physics.context.narrow_phase).unwrap(); // println!("nf: {}", Instant::now() - t); // let t = Instant::now(); - let bs = bincode::serialize(&physics.bodies).unwrap(); + let bs = bincode::serialize(&physics.context.bodies).unwrap(); // println!("bs: {}", Instant::now() - t); // let t = Instant::now(); - let cs = bincode::serialize(&physics.colliders).unwrap(); + let cs = bincode::serialize(&physics.context.colliders).unwrap(); // println!("cs: {}", Instant::now() - t); // let t = Instant::now(); - let js = bincode::serialize(&physics.impulse_joints).unwrap(); + let ijs = bincode::serialize(&physics.context.impulse_joints).unwrap(); + // println!("cs: {}", Instant::now() - t); + // let t = Instant::now(); + let mjs = bincode::serialize(&physics.context.multibody_joints).unwrap(); // println!("js: {}", Instant::now() - t); let serialization_time = Instant::now() - t; let hash_bf = md5::compute(&bf); let hash_nf = md5::compute(&nf); let hash_bodies = md5::compute(&bs); let hash_colliders = md5::compute(&cs); - let hash_joints = md5::compute(&js); + let hash_impulse_joints = md5::compute(&ijs); + let hash_multibody_joints = md5::compute(&mjs); format!( r#"Serialization time: {:.2}ms Hashes at frame: {} @@ -466,7 +473,8 @@ Hashes at frame: {} |_ Narrow phase [{:.1}KB]: {} |_ &RigidBodySet [{:.1}KB]: {} |_ Colliders [{:.1}KB]: {} -|_ Joints [{:.1}KB]: {}"#, +|_ ImpulseJoints [{:.1}KB]: {} +|_ MultibodyJoints [{:.1}KB]: {}"#, serialization_time.as_secs_f64() * 1000.0, timestep_id, bf.len() as f32 / 1000.0, @@ -477,7 +485,9 @@ Hashes at frame: {} format!("{:?}", hash_bodies).split_at(10).0, cs.len() as f32 / 1000.0, format!("{:?}", hash_colliders).split_at(10).0, - js.len() as f32 / 1000.0, - format!("{:?}", hash_joints).split_at(10).0, + ijs.len() as f32 / 1000.0, + format!("{:?}", hash_impulse_joints).split_at(10).0, + mjs.len() as f32 / 1000.0, + format!("{:?}", hash_multibody_joints).split_at(10).0, ) } From 393900cbfc10f4606479c7fb04d86e9a817b5cd6 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Mon, 24 Feb 2025 17:16:44 +0100 Subject: [PATCH 07/10] fix clippy --- src_testbed/physics/mod.rs | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/src_testbed/physics/mod.rs b/src_testbed/physics/mod.rs index 2e7c1c886..06ea061df 100644 --- a/src_testbed/physics/mod.rs +++ b/src_testbed/physics/mod.rs @@ -1,13 +1,9 @@ use crossbeam::channel::Receiver; -use rapier::dynamics::{ - CCDSolver, ImpulseJointSet, IntegrationParameters, IslandManager, MultibodyJointSet, - RigidBodySet, -}; +use rapier::dynamics::{ImpulseJointSet, IslandManager, MultibodyJointSet, RigidBodySet}; use rapier::geometry::{ ColliderSet, CollisionEvent, ContactForceEvent, DefaultBroadPhase, NarrowPhase, }; -use rapier::math::{Real, Vector}; -use rapier::pipeline::{PhysicsHooks, PhysicsPipeline, QueryPipeline}; +use rapier::pipeline::PhysicsHooks; use rapier::prelude::PhysicsContext; pub struct PhysicsSnapshot { From f09a884b5aab2e3c1d8dee412ec50fa320549695 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Thu, 27 Feb 2025 11:57:52 +0100 Subject: [PATCH 08/10] fix compiling --- src_testbed/harness/mod.rs | 16 +--------------- 1 file changed, 1 insertion(+), 15 deletions(-) diff --git a/src_testbed/harness/mod.rs b/src_testbed/harness/mod.rs index ef5e9f106..8fe866016 100644 --- a/src_testbed/harness/mod.rs +++ b/src_testbed/harness/mod.rs @@ -220,21 +220,7 @@ impl Harness { let physics = &mut self.physics; let event_handler = &self.event_handler; self.state.thread_pool.install(|| { - physics.pipeline.step( - &physics.gravity, - &physics.integration_parameters, - &mut physics.islands, - &mut physics.broad_phase, - &mut physics.narrow_phase, - &mut physics.bodies, - &mut physics.colliders, - &mut physics.impulse_joints, - &mut physics.multibody_joints, - &mut physics.ccd_solver, - Some(&mut physics.query_pipeline), - &*physics.hooks, - event_handler, - ); + physics.context.step(&*physics.hooks, event_handler); }); } From bb410f4dadf9f300ed7f0faf4904e63924a3cf60 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Mon, 3 Mar 2025 10:05:42 +0100 Subject: [PATCH 09/10] use physics context directly rather than using an indirection --- examples2d/add_remove2.rs | 12 +- examples2d/ccd2.rs | 2 - examples2d/character_controller2.rs | 2 +- examples2d/debug_compression2.rs | 4 +- examples2d/debug_intersection2.rs | 6 +- examples2d/drum2.rs | 6 +- examples2d/inverse_kinematics2.rs | 4 +- examples2d/one_way_platforms2.rs | 10 +- examples2d/platform2.rs | 14 +- examples2d/sensor2.rs | 4 +- examples3d-f64/debug_serialized3.rs | 8 +- examples3d/ccd3.rs | 2 - examples3d/character_controller3.rs | 2 +- examples3d/debug_add_remove_collider3.rs | 14 +- examples3d/debug_deserialize3.rs | 10 +- examples3d/debug_dynamic_collider_add3.rs | 18 +-- examples3d/debug_rollback3.rs | 2 +- examples3d/debug_shape_modification3.rs | 9 +- examples3d/fountain3.rs | 9 +- examples3d/inverse_kinematics3.rs | 4 +- examples3d/joint_motor_position3.rs | 11 +- examples3d/one_way_platforms3.rs | 14 +- examples3d/platform3.rs | 14 +- examples3d/sensor3.rs | 4 +- examples3d/vehicle_joints3.rs | 2 - src_testbed/debug_render.rs | 10 +- src_testbed/harness/mod.rs | 63 ++++----- src_testbed/harness/plugin.rs | 7 +- src_testbed/lib.rs | 2 +- src_testbed/physics/mod.rs | 22 --- src_testbed/plugin.rs | 4 +- src_testbed/testbed.rs | 164 +++++++++------------- src_testbed/ui.rs | 31 ++-- 33 files changed, 201 insertions(+), 289 deletions(-) diff --git a/examples2d/add_remove2.rs b/examples2d/add_remove2.rs index 0366c3193..861ef6c8d 100644 --- a/examples2d/add_remove2.rs +++ b/examples2d/add_remove2.rs @@ -26,7 +26,7 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |mut graphics, physics, _, state| { let rot = state.time * -1.0; for rb_handle in &platform_handles { - let rb = physics.context.bodies.get_mut(*rb_handle).unwrap(); + let rb = physics.bodies.get_mut(*rb_handle).unwrap(); rb.set_next_kinematic_rotation(UnitComplex::new(rot)); } @@ -34,24 +34,22 @@ pub fn init_world(testbed: &mut Testbed) { let x = rand::random::() * 10.0 - 5.0; let y = rand::random::() * 10.0 + 10.0; let rigid_body = RigidBodyBuilder::dynamic().translation(vector![x, y]); - let (handle, _) = physics - .context - .insert_body_and_collider(rigid_body, ColliderBuilder::cuboid(rad, rad)); + let (handle, _) = + physics.insert_body_and_collider(rigid_body, ColliderBuilder::cuboid(rad, rad)); if let Some(graphics) = &mut graphics { - graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); + graphics.add_body(handle, &physics.bodies, &physics.colliders); } } let to_remove: Vec<_> = physics - .context .bodies .iter() .filter(|(_, b)| b.position().translation.vector.y < -10.0) .map(|e| e.0) .collect(); for handle in to_remove { - physics.context.remove_rigidbody(handle, true); + physics.remove_rigidbody(handle, true); if let Some(graphics) = &mut graphics { graphics.remove_body(handle); diff --git a/examples2d/ccd2.rs b/examples2d/ccd2.rs index b8c8251ac..12468dc1d 100644 --- a/examples2d/ccd2.rs +++ b/examples2d/ccd2.rs @@ -95,14 +95,12 @@ pub fn init_world(testbed: &mut Testbed) { }; let parent_handle1 = physics - .context .colliders .get(prox.collider1()) .unwrap() .parent() .unwrap(); let parent_handle2 = physics - .context .colliders .get(prox.collider2()) .unwrap() diff --git a/examples2d/character_controller2.rs b/examples2d/character_controller2.rs index 55c0bac70..2acf50ffa 100644 --- a/examples2d/character_controller2.rs +++ b/examples2d/character_controller2.rs @@ -153,7 +153,7 @@ pub fn init_world(testbed: &mut Testbed) { // let angvel = run_state.time.sin() * 0.5; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics.context.bodies.get_mut(platform_handle) { + if let Some(platform) = physics.bodies.get_mut(platform_handle) { platform.set_linvel(linvel, true); // NOTE: interaction with rotating platforms isn’t handled very well yet. // platform.set_angvel(angvel, true); diff --git a/examples2d/debug_compression2.rs b/examples2d/debug_compression2.rs index 04bfce4bf..e0052d616 100644 --- a/examples2d/debug_compression2.rs +++ b/examples2d/debug_compression2.rs @@ -54,11 +54,11 @@ pub fn init_world(testbed: &mut Testbed) { let mut force = vector![0.0, 0.0]; testbed.add_callback(move |_, physics, _, _| { - let left_plank = &mut physics.context.bodies[handles[0]]; + let left_plank = &mut physics.bodies[handles[0]]; left_plank.reset_forces(true); left_plank.add_force(force, true); - let right_plank = &mut physics.context.bodies[handles[1]]; + let right_plank = &mut physics.bodies[handles[1]]; right_plank.reset_forces(true); right_plank.add_force(-force, true); diff --git a/examples2d/debug_intersection2.rs b/examples2d/debug_intersection2.rs index f2a7339f4..c05a95091 100644 --- a/examples2d/debug_intersection2.rs +++ b/examples2d/debug_intersection2.rs @@ -41,18 +41,18 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |graphics, physics, _, run| { let slow_time = run.timestep_id as f32 / 3.0; - let intersection = physics.context.intersection_with_shape( + let intersection = physics.intersection_with_shape( &Isometry::translation(slow_time.cos() * 10.0, slow_time.sin() * 10.0), &Ball::new(rad / 2.0), QueryFilter::default(), ); if let Some(graphics) = graphics { - for (handle, _) in physics.context.bodies.iter() { + for (handle, _) in physics.bodies.iter() { graphics.set_body_color(handle, [0.5, 0.5, 0.5]); } if let Some(intersection) = intersection { - let collider = physics.context.colliders.get(intersection).unwrap(); + let collider = physics.colliders.get(intersection).unwrap(); let body_handle = collider.parent().unwrap(); graphics.set_body_color(body_handle, [1.0, 0.0, 0.0]); diff --git a/examples2d/drum2.rs b/examples2d/drum2.rs index 9a58f56ab..54588c870 100644 --- a/examples2d/drum2.rs +++ b/examples2d/drum2.rs @@ -66,11 +66,7 @@ pub fn init_world(testbed: &mut Testbed) { */ testbed.add_callback(move |_, physics, _, _| { // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics - .context - .bodies - .get_mut(velocity_based_platform_handle) - { + if let Some(platform) = physics.bodies.get_mut(velocity_based_platform_handle) { platform.set_angvel(-0.15, true); } }); diff --git a/examples2d/inverse_kinematics2.rs b/examples2d/inverse_kinematics2.rs index 34604d00e..bb6212787 100644 --- a/examples2d/inverse_kinematics2.rs +++ b/examples2d/inverse_kinematics2.rs @@ -57,7 +57,7 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |graphics, physics, _, _| { let Some(graphics) = graphics else { return }; - if let Some((multibody, link_id)) = physics.context.multibody_joints.get_mut(last_link) { + if let Some((multibody, link_id)) = physics.multibody_joints.get_mut(last_link) { // Ensure our displacement vector has the right number of elements. if displacements.nrows() < multibody.ndofs() { displacements = DVector::zeros(multibody.ndofs()); @@ -78,7 +78,7 @@ pub fn init_world(testbed: &mut Testbed) { }; multibody.inverse_kinematics( - &physics.context.bodies, + &physics.bodies, link_id, &options, &Isometry::from(target_point), diff --git a/examples2d/one_way_platforms2.rs b/examples2d/one_way_platforms2.rs index da7b37e41..bf377b5d0 100644 --- a/examples2d/one_way_platforms2.rs +++ b/examples2d/one_way_platforms2.rs @@ -90,21 +90,21 @@ pub fn init_world(testbed: &mut Testbed) { * depending on their position. */ testbed.add_callback(move |graphics, physics, _, run_state| { - if run_state.timestep_id % 200 == 0 && physics.context.bodies.len() <= 7 { + if run_state.timestep_id % 200 == 0 && physics.bodies.len() <= 7 { // Spawn a new cube. let collider = ColliderBuilder::cuboid(1.5, 2.0); - let (handle, _) = physics.context.insert_body_and_collider( + let (handle, _) = physics.insert_body_and_collider( RigidBodyBuilder::dynamic().translation(vector![20.0, 10.0]), collider, ); if let Some(graphics) = graphics { - graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); + graphics.add_body(handle, &physics.bodies, &physics.colliders); } } - for handle in physics.context.island_manager.active_dynamic_bodies() { - let body = &mut physics.context.bodies[*handle]; + for handle in physics.island_manager.active_dynamic_bodies() { + let body = &mut physics.bodies[*handle]; if body.position().translation.y > 1.0 { body.set_gravity_scale(1.0, false); } else if body.position().translation.y < -1.0 { diff --git a/examples2d/platform2.rs b/examples2d/platform2.rs index 18b5ee994..c2405186c 100644 --- a/examples2d/platform2.rs +++ b/examples2d/platform2.rs @@ -69,22 +69,14 @@ pub fn init_world(testbed: &mut Testbed) { let velocity = vector![run_state.time.sin() * 5.0, (run_state.time * 5.0).sin()]; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics - .context - .bodies - .get_mut(velocity_based_platform_handle) - { + if let Some(platform) = physics.bodies.get_mut(velocity_based_platform_handle) { platform.set_linvel(velocity, true); } // Update the position-based kinematic body by setting its next position. - if let Some(platform) = physics - .context - .bodies - .get_mut(position_based_platform_handle) - { + if let Some(platform) = physics.bodies.get_mut(position_based_platform_handle) { let mut next_tra = *platform.translation(); - next_tra += velocity * physics.context.integration_parameters.dt; + next_tra += velocity * physics.integration_parameters.dt; platform.set_next_kinematic_translation(next_tra); } }); diff --git a/examples2d/sensor2.rs b/examples2d/sensor2.rs index 2a845d87a..c64f88a39 100644 --- a/examples2d/sensor2.rs +++ b/examples2d/sensor2.rs @@ -75,10 +75,10 @@ pub fn init_world(testbed: &mut Testbed) { [0.5, 0.5, 1.0] }; - let parent_handle1 = physics.context.colliders[prox.collider1()] + let parent_handle1 = physics.colliders[prox.collider1()] .parent() .unwrap(); - let parent_handle2 = physics.context.colliders[prox.collider2()] + let parent_handle2 = physics.colliders[prox.collider2()] .parent() .unwrap(); diff --git a/examples3d-f64/debug_serialized3.rs b/examples3d-f64/debug_serialized3.rs index 71d4364bb..12f3963d1 100644 --- a/examples3d-f64/debug_serialized3.rs +++ b/examples3d-f64/debug_serialized3.rs @@ -26,10 +26,10 @@ pub fn init_world(testbed: &mut Testbed) { state.impulse_joints, state.multibody_joints, ); - testbed.harness_mut().physics.context.island_manager = state.islands; - testbed.harness_mut().physics.context.broad_phase = state.broad_phase; - testbed.harness_mut().physics.context.narrow_phase = state.narrow_phase; - testbed.harness_mut().physics.context.ccd_solver = state.ccd_solver; + testbed.harness_mut().physics.island_manager = state.islands; + testbed.harness_mut().physics.broad_phase = state.broad_phase; + testbed.harness_mut().physics.narrow_phase = state.narrow_phase; + testbed.harness_mut().physics.ccd_solver = state.ccd_solver; testbed.set_graphics_shift(vector![-541.0, -6377257.0, -61.0]); testbed.look_at(point![10.0, 10.0, 10.0], point![0.0, 0.0, 0.0]); diff --git a/examples3d/ccd3.rs b/examples3d/ccd3.rs index 40e01515c..c1a5176a4 100644 --- a/examples3d/ccd3.rs +++ b/examples3d/ccd3.rs @@ -120,14 +120,12 @@ pub fn init_world(testbed: &mut Testbed) { }; let parent_handle1 = physics - .context .colliders .get(prox.collider1()) .unwrap() .parent() .unwrap(); let parent_handle2 = physics - .context .colliders .get(prox.collider2()) .unwrap() diff --git a/examples3d/character_controller3.rs b/examples3d/character_controller3.rs index 1f83e615d..ce96bf8a8 100644 --- a/examples3d/character_controller3.rs +++ b/examples3d/character_controller3.rs @@ -169,7 +169,7 @@ pub fn init_world(testbed: &mut Testbed) { // let angvel = run_state.time.sin() * 0.5; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics.context.bodies.get_mut(platform_handle) { + if let Some(platform) = physics.bodies.get_mut(platform_handle) { platform.set_linvel(linvel, true); // NOTE: interaction with rotating platforms isn’t handled very well yet. // platform.set_angvel(angvel, true); diff --git a/examples3d/debug_add_remove_collider3.rs b/examples3d/debug_add_remove_collider3.rs index 7ec6f274d..715acc44c 100644 --- a/examples3d/debug_add_remove_collider3.rs +++ b/examples3d/debug_add_remove_collider3.rs @@ -35,20 +35,18 @@ pub fn init_world(testbed: &mut Testbed) { // Remove then re-add the ground collider. let removed_collider_handle = ground_collider_handle; let coll = physics - .context .colliders .remove( removed_collider_handle, - &mut physics.context.island_manager, - &mut physics.context.bodies, + &mut physics.island_manager, + &mut physics.bodies, true, ) .unwrap(); - ground_collider_handle = physics.context.colliders.insert_with_parent( - coll, - ground_handle, - &mut physics.context.bodies, - ); + ground_collider_handle = + physics + .colliders + .insert_with_parent(coll, ground_handle, &mut physics.bodies); }); /* diff --git a/examples3d/debug_deserialize3.rs b/examples3d/debug_deserialize3.rs index 5aed78806..a875f2a49 100644 --- a/examples3d/debug_deserialize3.rs +++ b/examples3d/debug_deserialize3.rs @@ -38,12 +38,12 @@ pub fn init_world(testbed: &mut Testbed) { state.impulse_joints, state.multibody_joints, ); - testbed.harness_mut().physics.context.island_manager = state.islands; - testbed.harness_mut().physics.context.broad_phase = state.broad_phase; - testbed.harness_mut().physics.context.narrow_phase = state.narrow_phase; - testbed.harness_mut().physics.context.integration_parameters = + testbed.harness_mut().physics.island_manager = state.islands; + testbed.harness_mut().physics.broad_phase = state.broad_phase; + testbed.harness_mut().physics.narrow_phase = state.narrow_phase; + testbed.harness_mut().physics.integration_parameters = state.integration_parameters; - testbed.harness_mut().physics.context.gravity = state.gravity; + testbed.harness_mut().physics.gravity = state.gravity; testbed.set_graphics_shift(vector![-541.0, -6377257.0, -61.0]); testbed.look_at(point![10.0, 10.0, 10.0], point![0.0, 0.0, 0.0]); diff --git a/examples3d/debug_dynamic_collider_add3.rs b/examples3d/debug_dynamic_collider_add3.rs index ab8801b98..757c448cb 100644 --- a/examples3d/debug_dynamic_collider_add3.rs +++ b/examples3d/debug_dynamic_collider_add3.rs @@ -47,20 +47,20 @@ pub fn init_world(testbed: &mut Testbed) { // Add a bigger ball collider let collider = ColliderBuilder::ball(ball_rad + 0.01 * (step as f32)).density(100.0); - let new_ball_collider_handle = physics.context.colliders.insert_with_parent( + let new_ball_collider_handle = physics.colliders.insert_with_parent( collider, ball_handle, - &mut physics.context.bodies, + &mut physics.bodies, ); if let Some(graphics) = &mut graphics { - graphics.add_collider(new_ball_collider_handle, &physics.context.colliders); + graphics.add_collider(new_ball_collider_handle, &physics.colliders); } extra_colliders.push(new_ball_collider_handle); // Snap the ball velocity or restore it. - let ball = physics.context.bodies.get_mut(ball_handle).unwrap(); + let ball = physics.bodies.get_mut(ball_handle).unwrap(); if step == snapped_frame { linvel = *ball.linvel(); @@ -76,10 +76,10 @@ pub fn init_world(testbed: &mut Testbed) { for handle in &extra_colliders { if let Some(graphics) = &mut graphics { - graphics.remove_collider(*handle, &physics.context.colliders); + graphics.remove_collider(*handle, &physics.colliders); } - physics.context.remove_collider(*handle, true); + physics.remove_collider(*handle, true); } extra_colliders.clear(); @@ -94,14 +94,14 @@ pub fn init_world(testbed: &mut Testbed) { // .unwrap(); let coll = ColliderBuilder::cuboid(ground_size, ground_height + step as f32 * 0.01, 0.4) .friction(0.15); - let new_ground_collider_handle = physics.context.colliders.insert_with_parent( + let new_ground_collider_handle = physics.colliders.insert_with_parent( coll, ground_handle, - &mut physics.context.bodies, + &mut physics.bodies, ); if let Some(graphics) = &mut graphics { - graphics.add_collider(new_ground_collider_handle, &physics.context.colliders); + graphics.add_collider(new_ground_collider_handle, &physics.colliders); } extra_colliders.push(new_ground_collider_handle); diff --git a/examples3d/debug_rollback3.rs b/examples3d/debug_rollback3.rs index 2a63c0734..9936e37bc 100644 --- a/examples3d/debug_rollback3.rs +++ b/examples3d/debug_rollback3.rs @@ -45,7 +45,7 @@ pub fn init_world(testbed: &mut Testbed) { step += 1; // Snap the ball velocity or restore it. - let ball = physics.context.bodies.get_mut(ball_handle).unwrap(); + let ball = physics.bodies.get_mut(ball_handle).unwrap(); if step == snapped_frame { linvel = *ball.linvel(); diff --git a/examples3d/debug_shape_modification3.rs b/examples3d/debug_shape_modification3.rs index d092904af..897421879 100644 --- a/examples3d/debug_shape_modification3.rs +++ b/examples3d/debug_shape_modification3.rs @@ -64,7 +64,7 @@ pub fn init_world(testbed: &mut Testbed) { step += 1; // Snap the ball velocity or restore it. - let ball = physics.context.bodies.get_mut(ball_handle).unwrap(); + let ball = physics.bodies.get_mut(ball_handle).unwrap(); if step == snapped_frame { linvel = *ball.linvel(); @@ -73,7 +73,6 @@ pub fn init_world(testbed: &mut Testbed) { } let shapeshifting_coll = physics - .context .colliders .get_mut(shapeshifting_coll_handle) .unwrap(); @@ -89,12 +88,12 @@ pub fn init_world(testbed: &mut Testbed) { step = snapped_frame; } - let ball_coll = physics.context.colliders.get_mut(ball_coll_handle).unwrap(); + let ball_coll = physics.colliders.get_mut(ball_coll_handle).unwrap(); ball_coll.set_shape(SharedShape::ball(ball_rad * step as f32 * 2.0)); if let Some(gfx) = &mut gfx { - gfx.update_collider(ball_coll_handle, &physics.context.colliders); - gfx.update_collider(shapeshifting_coll_handle, &physics.context.colliders); + gfx.update_collider(ball_coll_handle, &physics.colliders); + gfx.update_collider(shapeshifting_coll_handle, &physics.colliders); } }); diff --git a/examples3d/fountain3.rs b/examples3d/fountain3.rs index 854a86c4e..050d9a697 100644 --- a/examples3d/fountain3.rs +++ b/examples3d/fountain3.rs @@ -24,7 +24,7 @@ pub fn init_world(testbed: &mut Testbed) { // Callback that will be executed on the main loop to handle proximities. testbed.add_callback(move |mut graphics, physics, _, run_state| { - physics.context.insert_body_and_collider( + physics.insert_body_and_collider( RigidBodyBuilder::dynamic().translation(vector![0.0, 10.0, 0.0]), match run_state.timestep_id % 3 { 0 => ColliderBuilder::round_cylinder(rad, rad, rad / 10.0), @@ -34,12 +34,11 @@ pub fn init_world(testbed: &mut Testbed) { ); if let Some(graphics) = &mut graphics { - graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); + graphics.add_body(handle, &physics.bodies, &physics.colliders); } - if physics.context.bodies.len() > MAX_NUMBER_OF_BODIES { + if physics.bodies.len() > MAX_NUMBER_OF_BODIES { let mut to_remove: Vec<_> = physics - .context .bodies .iter() .filter(|e| e.1.is_dynamic()) @@ -55,7 +54,7 @@ pub fn init_world(testbed: &mut Testbed) { let num_to_remove = to_remove.len() - MAX_NUMBER_OF_BODIES; for (handle, _) in &to_remove[..num_to_remove] { - physics.context.remove_rigidbody(*handle, true); + physics.remove_rigidbody(*handle, true); if let Some(graphics) = &mut graphics { graphics.remove_body(*handle); diff --git a/examples3d/inverse_kinematics3.rs b/examples3d/inverse_kinematics3.rs index cf12f3c33..50cd589b7 100644 --- a/examples3d/inverse_kinematics3.rs +++ b/examples3d/inverse_kinematics3.rs @@ -57,7 +57,7 @@ pub fn init_world(testbed: &mut Testbed) { testbed.add_callback(move |graphics, physics, _, _| { let Some(graphics) = graphics else { return }; - if let Some((multibody, link_id)) = physics.context.multibody_joints.get_mut(last_link) { + if let Some((multibody, link_id)) = physics.multibody_joints.get_mut(last_link) { // Ensure our displacement vector has the right number of elements. if displacements.nrows() < multibody.ndofs() { displacements = DVector::zeros(multibody.ndofs()); @@ -85,7 +85,7 @@ pub fn init_world(testbed: &mut Testbed) { }; multibody.inverse_kinematics( - &physics.context.bodies, + &physics.bodies, link_id, &options, &Isometry::from(target_point), diff --git a/examples3d/joint_motor_position3.rs b/examples3d/joint_motor_position3.rs index 1d9839442..f89e880b8 100644 --- a/examples3d/joint_motor_position3.rs +++ b/examples3d/joint_motor_position3.rs @@ -63,14 +63,9 @@ pub fn init_world(testbed: &mut Testbed) { } testbed.add_callback(move |_, physics, _, state| { - for ((_, joint), target) in physics - .context - .impulse_joints - .iter() - .zip(target_angles.iter()) - { - let rb1 = &physics.context.bodies[joint.body1]; - let rb2 = &physics.context.bodies[joint.body2]; + for ((_, joint), target) in physics.impulse_joints.iter().zip(target_angles.iter()) { + let rb1 = &physics.bodies[joint.body1]; + let rb2 = &physics.bodies[joint.body2]; let revolute = joint.data.as_revolute().unwrap(); println!( "[Step {}] rev angle: {} (target = {})", diff --git a/examples3d/one_way_platforms3.rs b/examples3d/one_way_platforms3.rs index 7a11607d9..3ec589be0 100644 --- a/examples3d/one_way_platforms3.rs +++ b/examples3d/one_way_platforms3.rs @@ -90,24 +90,24 @@ pub fn init_world(testbed: &mut Testbed) { * depending on their position. */ testbed.add_callback(move |graphics, physics, _, run_state| { - if run_state.timestep_id % 200 == 0 && physics.context.bodies.len() <= 7 { + if run_state.timestep_id % 200 == 0 && physics.bodies.len() <= 7 { // Spawn a new cube. let collider = ColliderBuilder::cuboid(1.0, 2.0, 1.5); let body = RigidBodyBuilder::dynamic().translation(vector![0.0, 6.0, 20.0]); - let handle = physics.context.bodies.insert(body); - physics.context.colliders.insert_with_parent( + let handle = physics.bodies.insert(body); + physics.colliders.insert_with_parent( collider, handle, - &mut physics.context.bodies, + &mut physics.bodies, ); if let Some(graphics) = graphics { - graphics.add_body(handle, &physics.context.bodies, &physics.context.colliders); + graphics.add_body(handle, &physics.bodies, &physics.colliders); } } - for handle in physics.context.island_manager.active_dynamic_bodies() { - let body = physics.context.bodies.get_mut(*handle).unwrap(); + for handle in physics.island_manager.active_dynamic_bodies() { + let body = physics.bodies.get_mut(*handle).unwrap(); if body.position().translation.y > 1.0 { body.set_gravity_scale(1.0, false); } else if body.position().translation.y < -1.0 { diff --git a/examples3d/platform3.rs b/examples3d/platform3.rs index f36b10134..9025afa0b 100644 --- a/examples3d/platform3.rs +++ b/examples3d/platform3.rs @@ -80,23 +80,15 @@ pub fn init_world(testbed: &mut Testbed) { ]; // Update the velocity-based kinematic body by setting its velocity. - if let Some(platform) = physics - .context - .bodies - .get_mut(velocity_based_platform_handle) - { + if let Some(platform) = physics.bodies.get_mut(velocity_based_platform_handle) { platform.set_linvel(velocity, true); platform.set_angvel(vector![0.0, 0.2, 0.0], true); } // Update the position-based kinematic body by setting its next position. - if let Some(platform) = physics - .context - .bodies - .get_mut(position_based_platform_handle) - { + if let Some(platform) = physics.bodies.get_mut(position_based_platform_handle) { let mut next_tra = *platform.translation(); - next_tra += velocity * physics.context.integration_parameters.dt; + next_tra += velocity * physics.integration_parameters.dt; platform.set_next_kinematic_translation(next_tra); } }); diff --git a/examples3d/sensor3.rs b/examples3d/sensor3.rs index 2b40ae08f..912174bef 100644 --- a/examples3d/sensor3.rs +++ b/examples3d/sensor3.rs @@ -79,10 +79,10 @@ pub fn init_world(testbed: &mut Testbed) { [0.5, 0.5, 1.0] }; - let parent_handle1 = physics.context.colliders[prox.collider1()] + let parent_handle1 = physics.colliders[prox.collider1()] .parent() .unwrap(); - let parent_handle2 = physics.context.colliders[prox.collider2()] + let parent_handle2 = physics.colliders[prox.collider2()] .parent() .unwrap(); diff --git a/examples3d/vehicle_joints3.rs b/examples3d/vehicle_joints3.rs index cc79af8c4..517bd9cb9 100644 --- a/examples3d/vehicle_joints3.rs +++ b/examples3d/vehicle_joints3.rs @@ -166,7 +166,6 @@ pub fn init_world(testbed: &mut Testbed) { // Apply steering to the axles. for steering_handle in &steering_joints { let steering_joint = physics - .context .impulse_joints .get_mut(*steering_handle, should_wake_up) .unwrap(); @@ -192,7 +191,6 @@ pub fn init_world(testbed: &mut Testbed) { let ms = [1.0 / speed_diff, speed_diff]; for (motor_handle, &ms) in motor_joints.iter().copied().zip(ms.iter()) { let motor_joint = physics - .context .impulse_joints .get_mut(motor_handle, should_wake_up) .unwrap(); diff --git a/src_testbed/debug_render.rs b/src_testbed/debug_render.rs index aae99b1ea..6bd538b85 100644 --- a/src_testbed/debug_render.rs +++ b/src_testbed/debug_render.rs @@ -74,11 +74,11 @@ fn debug_render_scene( let mut backend = BevyLinesRenderBackend { gizmos }; debug_render.pipeline.render( &mut backend, - &harness.physics.context.bodies, - &harness.physics.context.colliders, - &harness.physics.context.impulse_joints, - &harness.physics.context.multibody_joints, - &harness.physics.context.narrow_phase, + &harness.physics.bodies, + &harness.physics.colliders, + &harness.physics.impulse_joints, + &harness.physics.multibody_joints, + &harness.physics.narrow_phase, ); } } diff --git a/src_testbed/harness/mod.rs b/src_testbed/harness/mod.rs index 8fe866016..c66678b3a 100644 --- a/src_testbed/harness/mod.rs +++ b/src_testbed/harness/mod.rs @@ -1,9 +1,6 @@ #![allow(clippy::unnecessary_cast)] // Casts are needed for switching between f32/f64. -use crate::{ - physics::{PhysicsEvents, PhysicsState}, - TestbedGraphics, -}; +use crate::{physics::PhysicsEvents, TestbedGraphics}; use plugin::HarnessPlugin; use rapier::geometry::{ColliderSet, DefaultBroadPhase, NarrowPhase}; use rapier::math::{Real, Vector}; @@ -82,17 +79,19 @@ impl RunState { } pub struct Harness { - pub physics: PhysicsState, + pub physics: PhysicsContext, max_steps: usize, callbacks: Callbacks, plugins: Vec>, events: PhysicsEvents, + pub hooks: Box, event_handler: ChannelEventCollector, pub state: RunState, } -type Callbacks = - Vec, &mut PhysicsState, &PhysicsEvents, &RunState)>>; +type Callbacks = Vec< + Box, &mut PhysicsContext, &PhysicsEvents, &RunState)>, +>; #[allow(dead_code)] impl Harness { @@ -105,7 +104,7 @@ impl Harness { collision_events: collision_event_channel.1, contact_force_events: contact_force_event_channel.1, }; - let physics = PhysicsState::new(); + let physics = PhysicsContext::default(); let state = RunState::new(); Self { @@ -114,6 +113,7 @@ impl Harness { callbacks: Vec::new(), plugins: Vec::new(), events, + hooks: Box::new(()), event_handler, state, } @@ -135,14 +135,14 @@ impl Harness { } pub fn integration_parameters_mut(&mut self) -> &mut IntegrationParameters { - &mut self.physics.context.integration_parameters + &mut self.physics.integration_parameters } pub fn clear_callbacks(&mut self) { self.callbacks.clear(); } - pub fn physics_state_mut(&mut self) -> &mut PhysicsState { + pub fn physics_state_mut(&mut self) -> &mut PhysicsContext { &mut self.physics } @@ -174,24 +174,22 @@ impl Harness { ) { // println!("Num bodies: {}", bodies.len()); // println!("Num impulse_joints: {}", impulse_joints.len()); - self.physics = PhysicsState { - context: PhysicsContext { - gravity, - integration_parameters: IntegrationParameters::default(), - physics_pipeline: PhysicsPipeline::new(), - island_manager: IslandManager::new(), - broad_phase: DefaultBroadPhase::new(), - narrow_phase: NarrowPhase::new(), - bodies, - colliders, - impulse_joints, - multibody_joints, - ccd_solver: CCDSolver::new(), - query_pipeline: Some(QueryPipeline::new()), - }, - hooks: Box::new(hooks), + self.physics = PhysicsContext { + gravity, + integration_parameters: IntegrationParameters::default(), + physics_pipeline: PhysicsPipeline::new(), + island_manager: IslandManager::new(), + broad_phase: DefaultBroadPhase::new(), + narrow_phase: NarrowPhase::new(), + bodies, + colliders, + impulse_joints, + multibody_joints, + ccd_solver: CCDSolver::new(), + query_pipeline: Some(QueryPipeline::new()), }; - self.physics.context.physics_pipeline.counters.enable(); + self.hooks = Box::new(hooks); + self.physics.physics_pipeline.counters.enable(); self.state.timestep_id = 0; self.state.time = 0.0; } @@ -201,7 +199,8 @@ impl Harness { } pub fn add_callback< - F: FnMut(Option<&mut TestbedGraphics>, &mut PhysicsState, &PhysicsEvents, &RunState) + 'static, + F: FnMut(Option<&mut TestbedGraphics>, &mut PhysicsContext, &PhysicsEvents, &RunState) + + 'static, >( &mut self, callback: F, @@ -220,14 +219,12 @@ impl Harness { let physics = &mut self.physics; let event_handler = &self.event_handler; self.state.thread_pool.install(|| { - physics.context.step(&*physics.hooks, event_handler); + physics.step(&*physics.hooks, event_handler); }); } #[cfg(not(feature = "parallel"))] - self.physics - .context - .step(&*self.physics.hooks, &self.event_handler); + self.physics.step(&*self.hooks, &self.event_handler); for plugin in &mut self.plugins { plugin.step(&mut self.physics, &self.state) @@ -248,7 +245,7 @@ impl Harness { self.events.poll_all(); - self.state.time += self.physics.context.integration_parameters.dt as f32; + self.state.time += self.physics.integration_parameters.dt as f32; self.state.timestep_id += 1; } diff --git a/src_testbed/harness/plugin.rs b/src_testbed/harness/plugin.rs index ac2094541..be3bfc2d5 100644 --- a/src_testbed/harness/plugin.rs +++ b/src_testbed/harness/plugin.rs @@ -1,14 +1,15 @@ +use rapier::prelude::PhysicsContext; + use crate::harness::RunState; use crate::physics::PhysicsEvents; -use crate::PhysicsState; pub trait HarnessPlugin { fn run_callbacks( &mut self, - physics: &mut PhysicsState, + physics: &mut PhysicsContext, events: &PhysicsEvents, harness_state: &RunState, ); - fn step(&mut self, physics: &mut PhysicsState, run_state: &RunState); + fn step(&mut self, physics: &mut PhysicsContext, run_state: &RunState); fn profiling_string(&self) -> String; } diff --git a/src_testbed/lib.rs b/src_testbed/lib.rs index 1eec06f26..bb65d0f7c 100644 --- a/src_testbed/lib.rs +++ b/src_testbed/lib.rs @@ -3,10 +3,10 @@ extern crate nalgebra as na; pub use crate::graphics::{BevyMaterial, GraphicsManager}; pub use crate::harness::plugin::HarnessPlugin; -pub use crate::physics::PhysicsState; pub use crate::plugin::TestbedPlugin; pub use crate::testbed::{Testbed, TestbedApp, TestbedGraphics, TestbedState}; pub use bevy::prelude::KeyCode; +pub use rapier::prelude::PhysicsContext; #[cfg(all(feature = "dim2", feature = "other-backends"))] mod box2d_backend; diff --git a/src_testbed/physics/mod.rs b/src_testbed/physics/mod.rs index 06ea061df..4d26a99fe 100644 --- a/src_testbed/physics/mod.rs +++ b/src_testbed/physics/mod.rs @@ -3,8 +3,6 @@ use rapier::dynamics::{ImpulseJointSet, IslandManager, MultibodyJointSet, RigidB use rapier::geometry::{ ColliderSet, CollisionEvent, ContactForceEvent, DefaultBroadPhase, NarrowPhase, }; -use rapier::pipeline::PhysicsHooks; -use rapier::prelude::PhysicsContext; pub struct PhysicsSnapshot { timestep_id: usize, @@ -84,26 +82,6 @@ impl PhysicsSnapshot { } } -pub struct PhysicsState { - pub context: PhysicsContext, - pub hooks: Box, -} - -impl Default for PhysicsState { - fn default() -> Self { - Self::new() - } -} - -impl PhysicsState { - pub fn new() -> Self { - Self { - context: PhysicsContext::default(), - hooks: Box::new(()), - } - } -} - pub struct PhysicsEvents { pub collision_events: Receiver, pub contact_force_events: Receiver, diff --git a/src_testbed/plugin.rs b/src_testbed/plugin.rs index 42fdd175a..a3288e6b0 100644 --- a/src_testbed/plugin.rs +++ b/src_testbed/plugin.rs @@ -1,10 +1,10 @@ use crate::graphics::BevyMaterial; use crate::harness::Harness; -use crate::physics::PhysicsState; use crate::GraphicsManager; use bevy::prelude::*; // use bevy::render::render_resource::RenderPipelineDescriptor; use bevy_egui::EguiContexts; +use rapier::prelude::PhysicsContext; pub trait TestbedPlugin { fn init_plugin(&mut self); @@ -19,7 +19,7 @@ pub trait TestbedPlugin { ); fn clear_graphics(&mut self, graphics: &mut GraphicsManager, commands: &mut Commands); fn run_callbacks(&mut self, harness: &mut Harness); - fn step(&mut self, physics: &mut PhysicsState); + fn step(&mut self, physics: &mut PhysicsContext); fn draw( &mut self, graphics: &mut GraphicsManager, diff --git a/src_testbed/testbed.rs b/src_testbed/testbed.rs index f476d2bd1..d7a1b4b9f 100644 --- a/src_testbed/testbed.rs +++ b/src_testbed/testbed.rs @@ -8,7 +8,7 @@ use std::num::NonZeroUsize; use crate::debug_render::{DebugRenderPipelineResource, RapierDebugRenderPlugin}; use crate::graphics::BevyMaterialComponent; -use crate::physics::{DeserializedPhysicsSnapshot, PhysicsEvents, PhysicsSnapshot, PhysicsState}; +use crate::physics::{DeserializedPhysicsSnapshot, PhysicsEvents, PhysicsSnapshot}; use crate::plugin::TestbedPlugin; use crate::{graphics::GraphicsManager, harness::RunState}; use crate::{mouse, ui}; @@ -26,6 +26,7 @@ use rapier::geometry::Ray; use rapier::geometry::{ColliderHandle, ColliderSet, NarrowPhase}; use rapier::math::{Real, Vector}; use rapier::pipeline::{PhysicsHooks, QueryFilter, QueryPipeline}; +use rapier::prelude::PhysicsContext; #[cfg(all(feature = "dim2", feature = "other-backends"))] use crate::box2d_backend::Box2dWorld; @@ -377,7 +378,6 @@ impl TestbedApp { self.state.selected_backend = backend_id; self.harness .physics - .context .integration_parameters .num_solver_iterations = NonZeroUsize::new(4).unwrap(); @@ -403,12 +403,12 @@ impl TestbedApp { { if self.state.selected_backend == BOX2D_BACKEND { self.other_backends.box2d.as_mut().unwrap().step( - &mut self.harness.physics.context.physics_pipeline.counters, - &self.harness.physics.context.integration_parameters, + &mut self.harness.physics.physics_pipeline.counters, + &self.harness.physics.integration_parameters, ); self.other_backends.box2d.as_mut().unwrap().sync( - &mut self.harness.physics.context.bodies, - &mut self.harness.physics.context.colliders, + &mut self.harness.physics.bodies, + &mut self.harness.physics.colliders, ); } } @@ -420,12 +420,12 @@ impl TestbedApp { { // println!("Step"); self.other_backends.physx.as_mut().unwrap().step( - &mut self.harness.physics.context.physics_pipeline.counters, - &self.harness.physics.context.integration_parameters, + &mut self.harness.physics.physics_pipeline.counters, + &self.harness.physics.integration_parameters, ); self.other_backends.physx.as_mut().unwrap().sync( - &mut self.harness.physics.context.bodies, - &mut self.harness.physics.context.colliders, + &mut self.harness.physics.bodies, + &mut self.harness.physics.colliders, ); } } @@ -436,7 +436,6 @@ impl TestbedApp { timings.push( self.harness .physics - .context .physics_pipeline .counters .step_time @@ -601,10 +600,10 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { } pub fn integration_parameters_mut(&mut self) -> &mut IntegrationParameters { - &mut self.harness.physics.context.integration_parameters + &mut self.harness.physics.integration_parameters } - pub fn physics_state_mut(&mut self) -> &mut PhysicsState { + pub fn physics_state_mut(&mut self) -> &mut PhysicsContext { &mut self.harness.physics } @@ -759,7 +758,8 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { // } pub fn add_callback< - F: FnMut(Option<&mut TestbedGraphics>, &mut PhysicsState, &PhysicsEvents, &RunState) + 'static, + F: FnMut(Option<&mut TestbedGraphics>, &mut PhysicsContext, &PhysicsEvents, &RunState) + + 'static, >( &mut self, callback: F, @@ -807,15 +807,10 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { wheels[1].steering = steering_angle; vehicle.update_vehicle( - self.harness.physics.context.integration_parameters.dt, - &mut self.harness.physics.context.bodies, - &self.harness.physics.context.colliders, - self.harness - .physics - .context - .query_pipeline - .as_ref() - .unwrap(), + self.harness.physics.integration_parameters.dt, + &mut self.harness.physics.bodies, + &self.harness.physics.colliders, + self.harness.physics.query_pipeline.as_ref().unwrap(), QueryFilter::exclude_dynamic().exclude_rigid_body(vehicle.chassis), ); } @@ -899,16 +894,16 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let controller = self.state.character_controller.unwrap_or_default(); let phx = &mut self.harness.physics; - let character_body = &phx.context.bodies[character_handle]; - let character_collider = &phx.context.colliders[character_body.colliders()[0]]; + let character_body = &phx.bodies[character_handle]; + let character_collider = &phx.colliders[character_body.colliders()[0]]; let character_mass = character_body.mass(); let mut collisions = vec![]; let mvt = controller.move_shape( - phx.context.integration_parameters.dt, - &phx.context.bodies, - &phx.context.colliders, - phx.context.query_pipeline.as_ref().unwrap(), + phx.integration_parameters.dt, + &phx.bodies, + &phx.colliders, + phx.query_pipeline.as_ref().unwrap(), character_collider.shape(), character_collider.position(), desired_movement.cast::(), @@ -931,17 +926,17 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { } } controller.solve_character_collision_impulses( - phx.context.integration_parameters.dt, - &mut phx.context.bodies, - &phx.context.colliders, - phx.context.query_pipeline.as_ref().unwrap(), + phx.integration_parameters.dt, + &mut phx.bodies, + &phx.colliders, + phx.query_pipeline.as_ref().unwrap(), character_collider.shape(), character_mass, &*collisions, QueryFilter::new().exclude_rigid_body(character_handle), ); - let character_body = &mut phx.context.bodies[character_handle]; + let character_body = &mut phx.bodies[character_handle]; let pos = character_body.position(); character_body.set_next_kinematic_translation(pos.translation.vector + mvt.translation); // character_body.set_translation(pos.translation.vector + mvt.translation, false); @@ -972,7 +967,6 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let mut colliders: Vec<_> = self .harness .physics - .context .bodies .iter() .filter(|e| e.1.is_dynamic()) @@ -984,15 +978,12 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let num_to_delete = (colliders.len() / 10).max(0); for to_delete in &colliders[..num_to_delete] { if let Some(graphics) = self.graphics.as_mut() { - graphics.remove_collider( - to_delete[0], - &self.harness.physics.context.colliders, - ); + graphics.remove_collider(to_delete[0], &self.harness.physics.colliders); } - self.harness.physics.context.colliders.remove( + self.harness.physics.colliders.remove( to_delete[0], - &mut self.harness.physics.context.island_manager, - &mut self.harness.physics.context.bodies, + &mut self.harness.physics.island_manager, + &mut self.harness.physics.bodies, true, ); } @@ -1002,7 +993,6 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let dynamic_bodies: Vec<_> = self .harness .physics - .context .bodies .iter() .filter(|e| e.1.is_dynamic()) @@ -1013,12 +1003,12 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { if let Some(graphics) = self.graphics.as_mut() { graphics.remove_body(*to_delete); } - self.harness.physics.context.bodies.remove( + self.harness.physics.bodies.remove( *to_delete, - &mut self.harness.physics.context.island_manager, - &mut self.harness.physics.context.colliders, - &mut self.harness.physics.context.impulse_joints, - &mut self.harness.physics.context.multibody_joints, + &mut self.harness.physics.island_manager, + &mut self.harness.physics.colliders, + &mut self.harness.physics.impulse_joints, + &mut self.harness.physics.multibody_joints, true, ); } @@ -1028,18 +1018,13 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let impulse_joints: Vec<_> = self .harness .physics - .context .impulse_joints .iter() .map(|e| e.0) .collect(); let num_to_delete = (impulse_joints.len() / 10).max(0); for to_delete in &impulse_joints[..num_to_delete] { - self.harness - .physics - .context - .impulse_joints - .remove(*to_delete, true); + self.harness.physics.impulse_joints.remove(*to_delete, true); } } KeyCode::KeyA => { @@ -1047,7 +1032,6 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { let multibody_joints: Vec<_> = self .harness .physics - .context .multibody_joints .iter() .map(|e| e.0) @@ -1056,7 +1040,6 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { for to_delete in &multibody_joints[..num_to_delete] { self.harness .physics - .context .multibody_joints .remove(*to_delete, true); } @@ -1065,8 +1048,7 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { // Delete one remaining multibody. let to_delete = self .harness - .physics - .context + .physics_state_mut() .multibody_joints .iter() .next() @@ -1074,7 +1056,6 @@ impl Testbed<'_, '_, '_, '_, '_, '_> { if let Some(to_delete) = to_delete { self.harness .physics - .context .multibody_joints .remove_multibody_articulations(to_delete, true); } @@ -1425,13 +1406,13 @@ fn update_testbed( .set(TestbedActionFlags::TAKE_SNAPSHOT, false); state.snapshot = PhysicsSnapshot::new( harness.state.timestep_id, - &harness.physics.context.broad_phase, - &harness.physics.context.narrow_phase, - &harness.physics.context.island_manager, - &harness.physics.context.bodies, - &harness.physics.context.colliders, - &harness.physics.context.impulse_joints, - &harness.physics.context.multibody_joints, + &harness.physics.broad_phase, + &harness.physics.narrow_phase, + &harness.physics.island_manager, + &harness.physics.bodies, + &harness.physics.colliders, + &harness.physics.impulse_joints, + &harness.physics.multibody_joints, ) .ok(); @@ -1466,14 +1447,14 @@ fn update_testbed( } harness.state.timestep_id = timestep_id; - harness.physics.context.broad_phase = broad_phase; - harness.physics.context.narrow_phase = narrow_phase; - harness.physics.context.island_manager = island_manager; - harness.physics.context.bodies = bodies; - harness.physics.context.colliders = colliders; - harness.physics.context.impulse_joints = impulse_joints; - harness.physics.context.multibody_joints = multibody_joints; - harness.physics.context.query_pipeline = Some(QueryPipeline::new()); + harness.physics.broad_phase = broad_phase; + harness.physics.narrow_phase = narrow_phase; + harness.physics.island_manager = island_manager; + harness.physics.bodies = bodies; + harness.physics.colliders = colliders; + harness.physics.impulse_joints = impulse_joints; + harness.physics.multibody_joints = multibody_joints; + harness.physics.query_pipeline = Some(QueryPipeline::new()); state .action_flags @@ -1489,25 +1470,25 @@ fn update_testbed( state .action_flags .set(TestbedActionFlags::RESET_WORLD_GRAPHICS, false); - for (handle, _) in harness.physics.context.bodies.iter() { + for (handle, _) in harness.physics.bodies.iter() { graphics.add_body_colliders( &mut commands, meshes, materials, &mut gfx_components, handle, - &harness.physics.context.bodies, - &harness.physics.context.colliders, + &harness.physics.bodies, + &harness.physics.colliders, ); } - for (handle, _) in harness.physics.context.colliders.iter() { + for (handle, _) in harness.physics.colliders.iter() { graphics.add_collider( &mut commands, meshes, materials, handle, - &harness.physics.context.colliders, + &harness.physics.colliders, ); } @@ -1528,7 +1509,7 @@ fn update_testbed( != state.flags.contains(TestbedStateFlags::WIREFRAME) { graphics.toggle_wireframe_mode( - &harness.physics.context.colliders, + &harness.physics.colliders, state.flags.contains(TestbedStateFlags::WIREFRAME), ) } @@ -1537,14 +1518,14 @@ fn update_testbed( != state.flags.contains(TestbedStateFlags::SLEEP) { if state.flags.contains(TestbedStateFlags::SLEEP) { - for (_, body) in harness.physics.context.bodies.iter_mut() { + for (_, body) in harness.physics.bodies.iter_mut() { body.activation_mut().normalized_linear_threshold = RigidBodyActivation::default_normalized_linear_threshold(); body.activation_mut().angular_threshold = RigidBodyActivation::default_angular_threshold(); } } else { - for (_, body) in harness.physics.context.bodies.iter_mut() { + for (_, body) in harness.physics.bodies.iter_mut() { body.wake_up(true); body.activation_mut().normalized_linear_threshold = -1.0; } @@ -1640,8 +1621,8 @@ fn update_testbed( // Draw graphics.draw( state.flags, - &harness.physics.context.bodies, - &harness.physics.context.colliders, + &harness.physics.bodies, + &harness.physics.colliders, &mut gfx_components, &mut visibilities, &mut *materials, @@ -1659,10 +1640,7 @@ fn update_testbed( } if state.flags.contains(TestbedStateFlags::CONTACT_POINTS) { - draw_contacts( - &harness.physics.context.narrow_phase, - &harness.physics.context.colliders, - ); + draw_contacts(&harness.physics.narrow_phase, &harness.physics.colliders); } if state.running == RunMode::Step { @@ -1703,7 +1681,7 @@ fn highlight_hovered_body( _material_handles: &mut Query<&mut BevyMaterialComponent>, _graphics_manager: &mut GraphicsManager, _testbed_state: &mut TestbedState, - _physics: &PhysicsState, + _physics: &PhysicsContext, _window: &Window, _camera: &Camera, _camera_transform: &GlobalTransform, @@ -1716,7 +1694,7 @@ fn highlight_hovered_body( material_handles: &mut Query<&mut BevyMaterialComponent>, graphics_manager: &mut GraphicsManager, testbed_state: &mut TestbedState, - physics: &PhysicsState, + physics: &PhysicsContext, window: &Window, camera: &Camera, camera_transform: &GlobalTransform, @@ -1744,12 +1722,10 @@ fn highlight_hovered_body( let ray_dir = Vector3::new(ray_dir.x as Real, ray_dir.y as Real, ray_dir.z as Real); let ray = Ray::new(ray_origin, ray_dir); - let hit = physics - .context - .cast_ray(&ray, Real::MAX, true, QueryFilter::only_dynamic()); + let hit = physics.cast_ray(&ray, Real::MAX, true, QueryFilter::only_dynamic()); if let Some((handle, _)) = hit { - let collider = &physics.context.colliders[handle]; + let collider = &physics.colliders[handle]; if let Some(parent_handle) = collider.parent() { testbed_state.highlighted_body = Some(parent_handle); diff --git a/src_testbed/ui.rs b/src_testbed/ui.rs index 4dd83e2e4..5d2267c13 100644 --- a/src_testbed/ui.rs +++ b/src_testbed/ui.rs @@ -1,6 +1,7 @@ use rapier::control::CharacterLength; use rapier::counters::Counters; use rapier::math::Real; +use rapier::prelude::PhysicsContext; use std::num::NonZeroUsize; use crate::debug_render::DebugRenderPipelineResource; @@ -11,7 +12,6 @@ use crate::testbed::{ }; use crate::settings::SettingValue; -use crate::PhysicsState; use bevy_egui::egui::{Slider, Ui}; use bevy_egui::{egui, EguiContexts}; use rapier::dynamics::IntegrationParameters; @@ -95,7 +95,7 @@ pub fn update_ui( }); ui.collapsing("Profile infos", |ui| { ui.horizontal_wrapped(|ui| { - profiling_ui(ui, &harness.physics.context.physics_pipeline.counters); + profiling_ui(ui, &harness.physics.physics_pipeline.counters); }); }); ui.collapsing("Serialization infos", |ui| { @@ -107,7 +107,7 @@ pub fn update_ui( }); }); - let integration_parameters = &mut harness.physics.context.integration_parameters; + let integration_parameters = &mut harness.physics.integration_parameters; if state.selected_backend == PHYSX_BACKEND_PATCH_FRICTION || state.selected_backend == PHYSX_BACKEND_TWO_FRICTION_DIR @@ -323,13 +323,10 @@ pub fn update_ui( }); } -fn scene_infos_ui(ui: &mut Ui, physics: &PhysicsState) { - ui.label(format!("# rigid-bodies: {}", physics.context.bodies.len())); - ui.label(format!("# colliders: {}", physics.context.colliders.len())); - ui.label(format!( - "# impulse joint: {}", - physics.context.impulse_joints.len() - )); +fn scene_infos_ui(ui: &mut Ui, physics: &PhysicsContext) { + ui.label(format!("# rigid-bodies: {}", physics.bodies.len())); + ui.label(format!("# colliders: {}", physics.colliders.len())); + ui.label(format!("# impulse joint: {}", physics.impulse_joints.len())); // ui.label(format!( // "# multibody joint: {}", // physics.multibody_joints.len() @@ -415,25 +412,25 @@ fn profiling_ui(ui: &mut Ui, counters: &Counters) { }); } -fn serialization_string(timestep_id: usize, physics: &PhysicsState) -> String { +fn serialization_string(timestep_id: usize, physics: &PhysicsContext) -> String { let t = Instant::now(); // let t = Instant::now(); - let bf = bincode::serialize(&physics.context.broad_phase).unwrap(); + let bf = bincode::serialize(&physics.broad_phase).unwrap(); // println!("bf: {}", Instant::now() - t); // let t = Instant::now(); - let nf = bincode::serialize(&physics.context.narrow_phase).unwrap(); + let nf = bincode::serialize(&physics.narrow_phase).unwrap(); // println!("nf: {}", Instant::now() - t); // let t = Instant::now(); - let bs = bincode::serialize(&physics.context.bodies).unwrap(); + let bs = bincode::serialize(&physics.bodies).unwrap(); // println!("bs: {}", Instant::now() - t); // let t = Instant::now(); - let cs = bincode::serialize(&physics.context.colliders).unwrap(); + let cs = bincode::serialize(&physics.colliders).unwrap(); // println!("cs: {}", Instant::now() - t); // let t = Instant::now(); - let ijs = bincode::serialize(&physics.context.impulse_joints).unwrap(); + let ijs = bincode::serialize(&physics.impulse_joints).unwrap(); // println!("cs: {}", Instant::now() - t); // let t = Instant::now(); - let mjs = bincode::serialize(&physics.context.multibody_joints).unwrap(); + let mjs = bincode::serialize(&physics.multibody_joints).unwrap(); // println!("js: {}", Instant::now() - t); let serialization_time = Instant::now() - t; let hash_bf = md5::compute(&bf); From eaee06397cf35d1b497ec69942e954e58a614ab1 Mon Sep 17 00:00:00 2001 From: Thierry Berger Date: Mon, 3 Mar 2025 10:07:38 +0100 Subject: [PATCH 10/10] cargo fmt --- examples2d/sensor2.rs | 8 ++------ examples3d/debug_deserialize3.rs | 3 +-- examples3d/debug_dynamic_collider_add3.rs | 18 ++++++++---------- examples3d/one_way_platforms3.rs | 8 +++----- examples3d/sensor3.rs | 8 ++------ 5 files changed, 16 insertions(+), 29 deletions(-) diff --git a/examples2d/sensor2.rs b/examples2d/sensor2.rs index c64f88a39..595ad3b0b 100644 --- a/examples2d/sensor2.rs +++ b/examples2d/sensor2.rs @@ -75,12 +75,8 @@ pub fn init_world(testbed: &mut Testbed) { [0.5, 0.5, 1.0] }; - let parent_handle1 = physics.colliders[prox.collider1()] - .parent() - .unwrap(); - let parent_handle2 = physics.colliders[prox.collider2()] - .parent() - .unwrap(); + let parent_handle1 = physics.colliders[prox.collider1()].parent().unwrap(); + let parent_handle2 = physics.colliders[prox.collider2()].parent().unwrap(); if let Some(graphics) = &mut graphics { if parent_handle1 != ground_handle && parent_handle1 != sensor_handle { diff --git a/examples3d/debug_deserialize3.rs b/examples3d/debug_deserialize3.rs index a875f2a49..25515b0db 100644 --- a/examples3d/debug_deserialize3.rs +++ b/examples3d/debug_deserialize3.rs @@ -41,8 +41,7 @@ pub fn init_world(testbed: &mut Testbed) { testbed.harness_mut().physics.island_manager = state.islands; testbed.harness_mut().physics.broad_phase = state.broad_phase; testbed.harness_mut().physics.narrow_phase = state.narrow_phase; - testbed.harness_mut().physics.integration_parameters = - state.integration_parameters; + testbed.harness_mut().physics.integration_parameters = state.integration_parameters; testbed.harness_mut().physics.gravity = state.gravity; testbed.set_graphics_shift(vector![-541.0, -6377257.0, -61.0]); diff --git a/examples3d/debug_dynamic_collider_add3.rs b/examples3d/debug_dynamic_collider_add3.rs index 757c448cb..0b61b5853 100644 --- a/examples3d/debug_dynamic_collider_add3.rs +++ b/examples3d/debug_dynamic_collider_add3.rs @@ -47,11 +47,10 @@ pub fn init_world(testbed: &mut Testbed) { // Add a bigger ball collider let collider = ColliderBuilder::ball(ball_rad + 0.01 * (step as f32)).density(100.0); - let new_ball_collider_handle = physics.colliders.insert_with_parent( - collider, - ball_handle, - &mut physics.bodies, - ); + let new_ball_collider_handle = + physics + .colliders + .insert_with_parent(collider, ball_handle, &mut physics.bodies); if let Some(graphics) = &mut graphics { graphics.add_collider(new_ball_collider_handle, &physics.colliders); @@ -94,11 +93,10 @@ pub fn init_world(testbed: &mut Testbed) { // .unwrap(); let coll = ColliderBuilder::cuboid(ground_size, ground_height + step as f32 * 0.01, 0.4) .friction(0.15); - let new_ground_collider_handle = physics.colliders.insert_with_parent( - coll, - ground_handle, - &mut physics.bodies, - ); + let new_ground_collider_handle = + physics + .colliders + .insert_with_parent(coll, ground_handle, &mut physics.bodies); if let Some(graphics) = &mut graphics { graphics.add_collider(new_ground_collider_handle, &physics.colliders); diff --git a/examples3d/one_way_platforms3.rs b/examples3d/one_way_platforms3.rs index 3ec589be0..b476e5723 100644 --- a/examples3d/one_way_platforms3.rs +++ b/examples3d/one_way_platforms3.rs @@ -95,11 +95,9 @@ pub fn init_world(testbed: &mut Testbed) { let collider = ColliderBuilder::cuboid(1.0, 2.0, 1.5); let body = RigidBodyBuilder::dynamic().translation(vector![0.0, 6.0, 20.0]); let handle = physics.bodies.insert(body); - physics.colliders.insert_with_parent( - collider, - handle, - &mut physics.bodies, - ); + physics + .colliders + .insert_with_parent(collider, handle, &mut physics.bodies); if let Some(graphics) = graphics { graphics.add_body(handle, &physics.bodies, &physics.colliders); diff --git a/examples3d/sensor3.rs b/examples3d/sensor3.rs index 912174bef..479b0c652 100644 --- a/examples3d/sensor3.rs +++ b/examples3d/sensor3.rs @@ -79,12 +79,8 @@ pub fn init_world(testbed: &mut Testbed) { [0.5, 0.5, 1.0] }; - let parent_handle1 = physics.colliders[prox.collider1()] - .parent() - .unwrap(); - let parent_handle2 = physics.colliders[prox.collider2()] - .parent() - .unwrap(); + let parent_handle1 = physics.colliders[prox.collider1()].parent().unwrap(); + let parent_handle2 = physics.colliders[prox.collider2()].parent().unwrap(); if let Some(graphics) = &mut graphics { if parent_handle1 != ground_handle && parent_handle1 != sensor_handle {