feat: add MeshConverter and Colliders::converted_trimesh for building a collider with a shape computed form mesh buffers
This commit is contained in:
committed by
Sébastien Crozet
parent
d127af7816
commit
9865d5836a
@@ -2,7 +2,7 @@ use crate::dynamics::{CoefficientCombineRule, MassProperties, RigidBodyHandle};
|
|||||||
use crate::geometry::{
|
use crate::geometry::{
|
||||||
ActiveCollisionTypes, BroadPhaseProxyIndex, ColliderBroadPhaseData, ColliderChanges,
|
ActiveCollisionTypes, BroadPhaseProxyIndex, ColliderBroadPhaseData, ColliderChanges,
|
||||||
ColliderFlags, ColliderMassProps, ColliderMaterial, ColliderParent, ColliderPosition,
|
ColliderFlags, ColliderMassProps, ColliderMaterial, ColliderParent, ColliderPosition,
|
||||||
ColliderShape, ColliderType, InteractionGroups, SharedShape,
|
ColliderShape, ColliderType, InteractionGroups, MeshConverter, MeshConverterError, SharedShape,
|
||||||
};
|
};
|
||||||
use crate::math::{AngVector, Isometry, Point, Real, Rotation, Vector, DIM};
|
use crate::math::{AngVector, Isometry, Point, Real, Rotation, Vector, DIM};
|
||||||
use crate::parry::transformation::vhacd::VHACDParameters;
|
use crate::parry::transformation::vhacd::VHACDParameters;
|
||||||
@@ -698,6 +698,21 @@ impl ColliderBuilder {
|
|||||||
Self::new(SharedShape::trimesh_with_flags(vertices, indices, flags))
|
Self::new(SharedShape::trimesh_with_flags(vertices, indices, flags))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Initializes a collider builder with a shape converted from the given triangle mesh index
|
||||||
|
/// and vertex buffer.
|
||||||
|
///
|
||||||
|
/// All the conversion variants could be achieved with other constructors of [`ColliderBuilder`]
|
||||||
|
/// but having this specified by an enum can occasionally be easier or more flexible (determined
|
||||||
|
/// at runtime).
|
||||||
|
pub fn converted_trimesh(
|
||||||
|
vertices: Vec<Point<Real>>,
|
||||||
|
indices: Vec<[u32; 3]>,
|
||||||
|
converter: MeshConverter,
|
||||||
|
) -> Result<Self, MeshConverterError> {
|
||||||
|
let (shape, pose) = converter.convert(vertices, indices)?;
|
||||||
|
Ok(Self::new(shape).position(pose))
|
||||||
|
}
|
||||||
|
|
||||||
/// Initializes a collider builder with a compound shape obtained from the decomposition of
|
/// Initializes a collider builder with a compound shape obtained from the decomposition of
|
||||||
/// the given trimesh (in 3D) or polyline (in 2D) into convex parts.
|
/// the given trimesh (in 3D) or polyline (in 2D) into convex parts.
|
||||||
pub fn convex_decomposition(vertices: &[Point<Real>], indices: &[[u32; DIM]]) -> Self {
|
pub fn convex_decomposition(vertices: &[Point<Real>], indices: &[[u32; DIM]]) -> Self {
|
||||||
|
|||||||
82
src/geometry/mesh_converter.rs
Normal file
82
src/geometry/mesh_converter.rs
Normal file
@@ -0,0 +1,82 @@
|
|||||||
|
use parry::bounding_volume;
|
||||||
|
use parry::math::{Isometry, Point, Real};
|
||||||
|
use parry::shape::{Cuboid, SharedShape, TriMeshFlags};
|
||||||
|
use parry::transformation::vhacd::VHACDParameters;
|
||||||
|
|
||||||
|
/*
|
||||||
|
*
|
||||||
|
* TODO: should all this be part of parry instead?
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#[derive(thiserror::Error, Debug)]
|
||||||
|
pub enum MeshConverterError {
|
||||||
|
#[error("convex-hull computation failed")]
|
||||||
|
ConvexHullFailed,
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Determines how meshes (generally when loaded from a file) are converted into Rapier colliders.
|
||||||
|
// TODO: implement Copy once we add a Copy implementation for VHACDParameters.
|
||||||
|
#[derive(Clone, 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 mesh’s index buffer is ignored.
|
||||||
|
Obb,
|
||||||
|
/// The mesh is replaced by its AABB.
|
||||||
|
///
|
||||||
|
/// With this option, the mesh’s index buffer is ignored.
|
||||||
|
Aabb,
|
||||||
|
/// The mesh is replaced by its convex-hull.
|
||||||
|
///
|
||||||
|
/// With this option, the mesh’s index buffer is ignored.
|
||||||
|
ConvexHull,
|
||||||
|
/// The mesh is replaced by its convex decomposition.
|
||||||
|
ConvexDecomposition,
|
||||||
|
/// The mesh is replaced by its convex decomposition with parameters specified to adjust
|
||||||
|
/// the convex decomposition algorithm.
|
||||||
|
ConvexDecompositionWithParams(VHACDParameters),
|
||||||
|
}
|
||||||
|
|
||||||
|
impl MeshConverter {
|
||||||
|
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),
|
||||||
|
MeshConverter::TriMeshWithFlags(flags) => {
|
||||||
|
SharedShape::trimesh_with_flags(vertices, indices, *flags)
|
||||||
|
}
|
||||||
|
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);
|
||||||
|
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)?
|
||||||
|
}
|
||||||
|
MeshConverter::ConvexDecomposition => {
|
||||||
|
SharedShape::convex_decomposition(&vertices, &indices)
|
||||||
|
}
|
||||||
|
MeshConverter::ConvexDecompositionWithParams(params) => {
|
||||||
|
SharedShape::convex_decomposition_with_params(&vertices, &indices, ¶ms)
|
||||||
|
}
|
||||||
|
};
|
||||||
|
Ok((shape, transform))
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -2,7 +2,9 @@
|
|||||||
|
|
||||||
pub use self::broad_phase::BroadPhase;
|
pub use self::broad_phase::BroadPhase;
|
||||||
pub use self::broad_phase_multi_sap::{BroadPhaseMultiSap, BroadPhasePairEvent, ColliderPair};
|
pub use self::broad_phase_multi_sap::{BroadPhaseMultiSap, BroadPhasePairEvent, ColliderPair};
|
||||||
|
pub use self::collider::{Collider, ColliderBuilder};
|
||||||
pub use self::collider_components::*;
|
pub use self::collider_components::*;
|
||||||
|
pub use self::collider_set::ColliderSet;
|
||||||
pub use self::contact_pair::{
|
pub use self::contact_pair::{
|
||||||
ContactData, ContactManifoldData, ContactPair, IntersectionPair, SolverContact, SolverFlags,
|
ContactData, ContactManifoldData, ContactPair, IntersectionPair, SolverContact, SolverFlags,
|
||||||
};
|
};
|
||||||
@@ -10,11 +12,9 @@ pub use self::interaction_graph::{
|
|||||||
ColliderGraphIndex, InteractionGraph, RigidBodyGraphIndex, TemporaryInteractionIndex,
|
ColliderGraphIndex, InteractionGraph, RigidBodyGraphIndex, TemporaryInteractionIndex,
|
||||||
};
|
};
|
||||||
pub use self::interaction_groups::{Group, InteractionGroups};
|
pub use self::interaction_groups::{Group, InteractionGroups};
|
||||||
|
pub use self::mesh_converter::{MeshConverter, MeshConverterError};
|
||||||
pub use self::narrow_phase::NarrowPhase;
|
pub use self::narrow_phase::NarrowPhase;
|
||||||
|
|
||||||
pub use self::collider::{Collider, ColliderBuilder};
|
|
||||||
pub use self::collider_set::ColliderSet;
|
|
||||||
|
|
||||||
pub use parry::bounding_volume::BoundingVolume;
|
pub use parry::bounding_volume::BoundingVolume;
|
||||||
pub use parry::query::{PointQuery, PointQueryWithLocation, RayCast, TrackedContact};
|
pub use parry::query::{PointQuery, PointQueryWithLocation, RayCast, TrackedContact};
|
||||||
pub use parry::shape::SharedShape;
|
pub use parry::shape::SharedShape;
|
||||||
@@ -207,3 +207,4 @@ mod broad_phase;
|
|||||||
mod broad_phase_qbvh;
|
mod broad_phase_qbvh;
|
||||||
mod collider;
|
mod collider;
|
||||||
mod collider_set;
|
mod collider_set;
|
||||||
|
mod mesh_converter;
|
||||||
|
|||||||
Reference in New Issue
Block a user