soft_body_events
The tears applied during a step, whether they were generated by the simulation itself or requested with
RapierSoftBody::tear_edge (as well as the ones applied by
RapierContextMut::tear_soft_body and cut_soft_body),
are reported the same way as the
collision events, i.e., as messages.
Each event (a SoftBodyTearEvent, read with a MessageReader) identifies the soft-body that tore and gives the
pieces it was split into, so the rendering of the scene can be updated accordingly:
The SoftBodyTearEvent message gives the entities of the torn soft-body and of its pieces (the first
piece being the torn entity itself, the other ones being the entities already returned by tear_soft_body and
cut_soft_body for the tears they applied), the pieces of the clusters the tear split (cluster_splits), and the
joints it moved from a cluster proxy to another (moved_joints). Its raw field is the event of Rapier, with every
detail of the topology change in terms of handles and particle indices:
- Example 2D
- Example 3D
fn read_tear_events(context: ReadRapierContext, mut tears: MessageReader<SoftBodyTearEvent>) {
let Ok(context) = context.single() else {
return;
};
for tear in tears.read() {
// The first piece is the torn entity itself, the others are the entities spawned for
// the soft-bodies split off it.
for piece in &tear.pieces {
println!(
"Soft body {} tore: piece {} has {} particles",
tear.soft_body,
piece.soft_body,
piece.particles.len()
);
}
// Where a particle of the torn body went.
if let Some((handle, index)) = tear.raw.particle_destination(399) {
let entity = context.soft_body_entity(handle);
println!("particle 399 is now particle {index} of {entity:?}");
}
}
}
fn read_tear_events(context: ReadRapierContext, mut tears: MessageReader<SoftBodyTearEvent>) {
let Ok(context) = context.single() else {
return;
};
for tear in tears.read() {
// The first piece is the torn entity itself, the others are the entities spawned for
// the soft-bodies split off it.
for piece in &tear.pieces {
println!(
"Soft body {} tore: piece {} has {} particles",
tear.soft_body,
piece.soft_body,
piece.particles.len()
);
}
// Where a particle of the torn body went.
if let Some((handle, index)) = tear.raw.particle_destination(399) {
let entity = context.soft_body_entity(handle);
println!("particle 399 is now particle {index} of {entity:?}");
}
}
}