Files
rapier/src/geometry/mesh_converter.rs
Sébastien Crozet 95bd6fcfeb feat: switch to the new Bvh from parry for the broad-phase (#853)
* feat: switch to the new Bvh from parry for the broad-phase

* chore: cargo fmt + update testbed

* chore: remove the multi-grid SAP broad-phase

* fix soft-ccd handling in broad-phase

* Fix contact cleanup in broad-phase after collider removal

* chore: clippy fixes

* fix CCD regression

* chore: update changelog

* fix build with the parallel feature enabled

* chore: remove the now useless broad-phase proxy index from colliders

* fix tests
2025-07-11 22:36:40 +02:00

99 lines
3.7 KiB
Rust
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
use parry::bounding_volume;
use parry::math::{Isometry, Point, Real};
use parry::shape::{Cuboid, SharedShape, TriMeshBuilderError, TriMeshFlags};
#[cfg(feature = "dim3")]
use parry::transformation::vhacd::VHACDParameters;
/*
*
* TODO: should all this be part of parry instead?
*
*/
/// Error that can be generated by the [`MeshConverter`].
#[derive(thiserror::Error, Debug)]
pub enum MeshConverterError {
/// The convex hull calculation carried out by the [`MeshConverter::ConvexHull`] failed.
#[error("convex-hull computation failed")]
ConvexHullFailed,
/// The TriMesh building failed.
#[error("TriMesh building failed")]
TriMeshBuilderError(TriMeshBuilderError),
}
/// Determines how meshes (generally when loaded from a file) are converted into Rapier colliders.
#[derive(Clone, Copy, Debug, PartialEq, Default)]
pub enum MeshConverter {
/// The mesh is loaded as-is without any particular processing.
#[default]
TriMesh,
/// The mesh is loaded with the specified flags.
TriMeshWithFlags(TriMeshFlags),
/// The mesh is replaced by its Oriented Bounding Box (represented as
/// a rotated cuboid).
///
/// With this option, the meshs index buffer is ignored.
Obb,
/// The mesh is replaced by its AABB.
///
/// With this option, the meshs index buffer is ignored.
Aabb,
/// The mesh is replaced by its convex-hull.
///
/// With this option, the meshs index buffer is ignored.
ConvexHull,
/// The mesh is replaced by its convex decomposition.
#[cfg(feature = "dim3")]
ConvexDecomposition,
/// The mesh is replaced by its convex decomposition with parameters specified to adjust
/// the convex decomposition algorithm.
#[cfg(feature = "dim3")]
ConvexDecompositionWithParams(VHACDParameters),
}
impl MeshConverter {
/// Applies the conversion rule described by this [`MeshConverter`] to build a shape from
/// the given vertex and index buffers.
#[profiling::function]
pub fn convert(
&self,
vertices: Vec<Point<Real>>,
indices: Vec<[u32; 3]>,
) -> Result<(SharedShape, Isometry<Real>), MeshConverterError> {
let mut transform = Isometry::identity();
let shape = match self {
MeshConverter::TriMesh => SharedShape::trimesh(vertices, indices)
.map_err(MeshConverterError::TriMeshBuilderError)?,
MeshConverter::TriMeshWithFlags(flags) => {
SharedShape::trimesh_with_flags(vertices, indices, *flags)
.map_err(MeshConverterError::TriMeshBuilderError)?
}
MeshConverter::Obb => {
let (pose, cuboid) = parry::utils::obb(&vertices);
transform = pose;
SharedShape::new(cuboid)
}
MeshConverter::Aabb => {
let aabb =
bounding_volume::details::local_point_cloud_aabb(vertices.iter().copied());
let cuboid = Cuboid::new(aabb.half_extents());
transform = Isometry::from(aabb.center().coords);
SharedShape::new(cuboid)
}
MeshConverter::ConvexHull => {
SharedShape::convex_hull(&vertices).ok_or(MeshConverterError::ConvexHullFailed)?
}
#[cfg(feature = "dim3")]
MeshConverter::ConvexDecomposition => {
SharedShape::convex_decomposition(&vertices, &indices)
}
#[cfg(feature = "dim3")]
MeshConverter::ConvexDecompositionWithParams(params) => {
SharedShape::convex_decomposition_with_params(&vertices, &indices, params)
}
};
Ok((shape, transform))
}
}