-
-
Notifications
You must be signed in to change notification settings - Fork 265
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Assertion failure: position change, enabled state change, and missing MODIFIED flag #802
Comments
In the step function in rapier/src/pipeline/physics_pipeline.rs Here in the handle_user_changes_to_rigid_bodies function some colliders are added multiple times to modified_bodies // Apply modifications.
let mut modified_colliders = colliders.take_modified();
let mut removed_colliders = colliders.take_removed();
super::user_changes::handle_user_changes_to_colliders(
bodies,
colliders,
&modified_colliders[..],
);
let mut modified_bodies = bodies.take_modified();
super::user_changes::handle_user_changes_to_rigid_bodies( // Here ------------------------------
Some(islands),
bodies,
colliders,
impulse_joints,
multibody_joints,
&modified_bodies,
&mut modified_colliders,
); Here disabled colliders are treated as if they were removed. // Disabled colliders are treated as if they were removed.
// NOTE: this must be called here, after handle_user_changes_to_rigid_bodies to take into
// account colliders disabled because of their parent rigid-body.
removed_colliders.extend(
modified_colliders
.iter()
.copied()
.filter(|h| colliders.get(*h).map(|c| !c.is_enabled()).unwrap_or(false)),
); In rapier/src/geometry/broad_phase_multi_sap/broad_phase_multi_sap.rs // Phase 1: pre-delete the collisions that have been deleted.
self.handle_removed_colliders(removed_colliders); Then line 154 -> self.predelete_proxy(proxy_id); fn handle_removed_colliders(&mut self, removed_colliders: &[ColliderHandle]) {
// For each removed collider, remove the corresponding proxy.
for removed in removed_colliders {
if let Some(proxy_id) = self.colliders_proxy_ids.get(removed).copied() {
self.predelete_proxy(proxy_id);
}
}
} In rapier/src/geometry/broad_phase_multi_sap/sap_layer.rs // Discretize the Aabb to find the regions that need to be invalidated.
let proxy_aabb = &mut proxies[proxy_index].aabb;
let start = super::point_key(proxy_aabb.mins, self.region_width);
let end = super::point_key(proxy_aabb.maxs, self.region_width);
// Set the Aabb of the proxy to a very large value.
proxy_aabb.mins.coords.fill(DELETED_AABB_VALUE);
proxy_aabb.maxs.coords.fill(DELETED_AABB_VALUE); In the predelete_proxy function, the AABB of a proxy is set to an invalid value with DELETED_AABB_VALUE. If this function is called multiple times on the same collider, it causes an assertion failure in point_key. This happens because the collider is added multiple times to the removed_colliders list, which occurs because it is present multiple times in the modified_colliders list. |
Thanks for the thorough investigation! I think your conclusions are correct, I'll work towards verifying and applying those fixes + add no-regression tests. |
Sounds good, glad I could help! |
// Error ------------------------------------------------
Ball altitude: 9.998297
thread 'main' panicked at /home/johannes/.cargo/registry/src/index.crates.io-1949cf8c6b5b557f/rapier2d-0.23.0/src/geometry/broad_phase_multi_sap/sap_utils.rs:36:13:
assertion failed: e.floor() < RegionKey::MAX as Real
note: run with
RUST_BACKTRACE=1
environment variable to display a backtrace// What happened ----------------------------------------
// Reproduce --------------------------------------------
In the for loop at the bottom.
// Solution (maybe) -------------------------------------------
rapier/src/dynamics/rigid_body_components.rs
line 970
In the function update_positions in the RigidBodyColliders impl:
The handle is only added to modified_colliders if it does not already contain ColliderChanges::MODIFIED.
However, I believe the ColliderChanges::MODIFIED flag must be inserted into the changes when pushing
the handle to modified_colliders.
rapier/src/pipeline/user_changes.rs
line 141 and 142
update_positions is called and colliders may be added to the modified_colliders
line 154 and 170
Collider handles are added to the modified_colliders if the ColliderChanges::MODIFIED is not set
If a collider is pushed to modified_colliders in the update_positions function without setting the MODIFIED flag,
it can be pushed to modified_colliders twice.
Solution:
rapier/src/dynamics/rigid_body_components.rs
in the update_positions function:
// Also -----------------------------------------------
rapier/src/geometry/collider_set.rs
line 69
In the funktion iter_mut
The text was updated successfully, but these errors were encountered: