diff options
| author | Sébastien Crozet <developer@crozet.re> | 2022-07-07 11:22:14 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2022-07-07 11:22:14 +0200 |
| commit | 949573dd100ab2ae69402300794937f83daabeb1 (patch) | |
| tree | 6313fdaad266efdfc329a7e0388373c7cd6ce041 | |
| parent | 06ec9a0e76cea7a035b4335c591cd3fddd0d9999 (diff) | |
| parent | fade7682d4c3da35cd18104a903fc562a07b35b3 (diff) | |
| download | rapier-949573dd100ab2ae69402300794937f83daabeb1.tar.gz rapier-949573dd100ab2ae69402300794937f83daabeb1.tar.bz2 rapier-949573dd100ab2ae69402300794937f83daabeb1.zip | |
Merge pull request #362 from dimforge/active-events-contact-force-event
Add ActiveEvents::CONTACT_FORCE_EVENTS for consistency with ActiveEvents::COLLISION_EVENTS
| -rw-r--r-- | CHANGELOG.md | 15 | ||||
| -rw-r--r-- | src/geometry/collider.rs | 16 | ||||
| -rw-r--r-- | src/pipeline/event_handler.rs | 7 | ||||
| -rw-r--r-- | src/pipeline/physics_pipeline.rs | 4 |
4 files changed, 36 insertions, 6 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md index 0f1da52..63a90e1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,10 @@ ## Unreleased ### Fixed +- Fix unpredictable broad-phase panic when using small colliders in the simulation. +- Fix collision events being incorrectly generated for any shape that produces multiple + contact manifolds (like triangle meshes). +- Fix panic in the `CollisionPipeline` if a collider is both added and removed before a call + to `CollisionPipeline::step`. ### Modified - The `RigidBodyBuilder::additional_mass` method will now result in the additional angular inertia @@ -22,6 +27,16 @@ - Add `ColliderBuilder::mass` to set the mass of the collider instead of its density. Its angular inertia tensor will be automatically computed based on this mass and its shape. - Add `Collider::mass` and `Collider::volume` to retrieve the mass or volume of a collider. +- Add the `QueryFilter` that is now used by all the scene queries instead of the `CollisionGroups` and `Fn(ColliderHandle) -> bool` + closure. This `QueryFilter` provides easy access to most common filtering strategies (e.g. dynamic bodies only, + excluding one particular collider, etc.) for scene queries. +- Add force reporting based on contact force events. The `EventHandler` trait has been modified to include + the method `EventHandler::handle_contact_force_event`. Contact force events are generated whenever the sum of the + magnitudes of all the forces between two colliders is greater than any of their + `Collider::contact_force_event_threshold` values (only the colliders wit the `ActiveEvents::CONTACT_FORCE_EVENT` flag + set are taken into account for this threshold). +- Add the `ContactForceEvent` struct that is generated by the `ChannelEventCollector` to report + contact force events. ## v0.13.0 (31 May 2022) ### Fixed diff --git a/src/geometry/collider.rs b/src/geometry/collider.rs index 7b0cc4c..a9af8d1 100644 --- a/src/geometry/collider.rs +++ b/src/geometry/collider.rs @@ -26,7 +26,7 @@ pub struct Collider { pub(crate) material: ColliderMaterial, pub(crate) flags: ColliderFlags, pub(crate) bf_data: ColliderBroadPhaseData, - pub(crate) contact_force_event_threshold: Real, + contact_force_event_threshold: Real, /// User-defined data associated to this collider. pub user_data: u128, } @@ -37,6 +37,18 @@ impl Collider { self.changes = ColliderChanges::all(); } + pub(crate) fn effective_contact_force_event_threshold(&self) -> Real { + if self + .flags + .active_events + .contains(ActiveEvents::CONTACT_FORCE_EVENTS) + { + self.contact_force_event_threshold + } else { + Real::MAX + } + } + /// The rigid body this collider is attached to. pub fn parent(&self) -> Option<RigidBodyHandle> { self.parent.map(|parent| parent.handle) @@ -412,7 +424,7 @@ impl ColliderBuilder { active_collision_types: ActiveCollisionTypes::default(), active_hooks: ActiveHooks::empty(), active_events: ActiveEvents::empty(), - contact_force_event_threshold: Real::MAX, + contact_force_event_threshold: 0.0, } } diff --git a/src/pipeline/event_handler.rs b/src/pipeline/event_handler.rs index e0f76a9..e5270ad 100644 --- a/src/pipeline/event_handler.rs +++ b/src/pipeline/event_handler.rs @@ -7,9 +7,12 @@ bitflags::bitflags! { #[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))] /// Flags affecting the events generated for this collider. pub struct ActiveEvents: u32 { - /// If set, Rapier will call `EventHandler::handle_contact_event` + /// If set, Rapier will call `EventHandler::handle_collision_event` /// whenever relevant for this collider. const COLLISION_EVENTS = 0b0001; + /// If set, Rapier will call `EventHandler::handle_contact_force_event` + /// whenever relevant for this collider. + const CONTACT_FORCE_EVENTS = 0b0010; } } @@ -48,7 +51,7 @@ pub trait EventHandler: Send + Sync { /// /// A force event is generated whenever the total force magnitude applied between two /// colliders is `> Collider::contact_force_event_threshold` value of any of these - /// colliders. + /// colliders with the `ActiveEvents::CONTACT_FORCE_EVENTS` flag set. /// /// The "total force magnitude" here means "the sum of the magnitudes of the forces applied at /// all the contact points in a contact pair". Therefore, if the contact pair involves two diff --git a/src/pipeline/physics_pipeline.rs b/src/pipeline/physics_pipeline.rs index 71ab578..391b39a 100644 --- a/src/pipeline/physics_pipeline.rs +++ b/src/pipeline/physics_pipeline.rs @@ -291,8 +291,8 @@ impl PhysicsPipeline { let co1 = &colliders[pair.collider1]; let co2 = &colliders[pair.collider2]; let threshold = co1 - .contact_force_event_threshold - .min(co2.contact_force_event_threshold); + .effective_contact_force_event_threshold() + .min(co2.effective_contact_force_event_threshold()); if threshold < Real::MAX { let total_magnitude = pair.total_impulse_magnitude() * inv_dt; |
