Move ColliderShape out of Rapier.
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
use na::{Isometry3, Point3};
|
||||
use rapier3d::dynamics::{JointSet, RigidBodyBuilder, RigidBodySet};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, ColliderShape};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, SharedShape};
|
||||
use rapier_testbed3d::Testbed;
|
||||
|
||||
pub fn init_world(testbed: &mut Testbed) {
|
||||
@@ -66,15 +66,15 @@ pub fn init_world(testbed: &mut Testbed) {
|
||||
let shapes = vec![
|
||||
(
|
||||
Isometry3::identity(),
|
||||
ColliderShape::cuboid(rad * 10.0, rad, rad),
|
||||
SharedShape::cuboid(rad * 10.0, rad, rad),
|
||||
),
|
||||
(
|
||||
Isometry3::translation(rad * 10.0, rad * 10.0, 0.0),
|
||||
ColliderShape::cuboid(rad, rad * 10.0, rad),
|
||||
SharedShape::cuboid(rad, rad * 10.0, rad),
|
||||
),
|
||||
(
|
||||
Isometry3::translation(-rad * 10.0, rad * 10.0, 0.0),
|
||||
ColliderShape::cuboid(rad, rad * 10.0, rad),
|
||||
SharedShape::cuboid(rad, rad * 10.0, rad),
|
||||
),
|
||||
];
|
||||
|
||||
|
||||
@@ -3,7 +3,7 @@ use na::{Point3, Translation3};
|
||||
use rapier3d::cdl::bounding_volume::{self, BoundingVolume};
|
||||
use rapier3d::cdl::transformation::vhacd::{VHACDParameters, VHACD};
|
||||
use rapier3d::dynamics::{JointSet, RigidBodyBuilder, RigidBodySet};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, ColliderShape};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, SharedShape};
|
||||
use rapier_testbed3d::Testbed;
|
||||
use std::path::Path;
|
||||
|
||||
@@ -82,11 +82,11 @@ pub fn init_world(testbed: &mut Testbed) {
|
||||
.map(|idx| [idx.x, idx.y, idx.z])
|
||||
.collect();
|
||||
|
||||
let decomposed_shape = ColliderShape::convex_decomposition(&vertices, &indices);
|
||||
let decomposed_shape = SharedShape::convex_decomposition(&vertices, &indices);
|
||||
shapes.push(decomposed_shape);
|
||||
}
|
||||
|
||||
// let compound = ColliderShape::compound(compound_parts);
|
||||
// let compound = SharedShape::compound(compound_parts);
|
||||
|
||||
for k in 1..num_duplications + 1 {
|
||||
let x = (igeom % width) as f32 * shift;
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
use na::{ComplexField, DMatrix, Isometry3, Point3, Vector3};
|
||||
use rapier3d::dynamics::{JointSet, RigidBodyBuilder, RigidBodySet};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, ColliderShape};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, SharedShape};
|
||||
use rapier_testbed3d::Testbed;
|
||||
|
||||
pub fn init_world(testbed: &mut Testbed) {
|
||||
@@ -70,15 +70,15 @@ pub fn init_world(testbed: &mut Testbed) {
|
||||
let shapes = vec![
|
||||
(
|
||||
Isometry3::identity(),
|
||||
ColliderShape::cuboid(rad, rad / 2.0, rad / 2.0),
|
||||
SharedShape::cuboid(rad, rad / 2.0, rad / 2.0),
|
||||
),
|
||||
(
|
||||
Isometry3::translation(rad, 0.0, 0.0),
|
||||
ColliderShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
SharedShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
),
|
||||
(
|
||||
Isometry3::translation(-rad, 0.0, 0.0),
|
||||
ColliderShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
SharedShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
),
|
||||
];
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
use na::{ComplexField, DMatrix, Isometry3, Point3, Vector3};
|
||||
use rapier3d::dynamics::{JointSet, RigidBodyBuilder, RigidBodySet};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, ColliderShape, HeightField};
|
||||
use rapier3d::geometry::{ColliderBuilder, ColliderSet, HeightField, SharedShape};
|
||||
use rapier_testbed3d::Testbed;
|
||||
|
||||
pub fn init_world(testbed: &mut Testbed) {
|
||||
@@ -75,15 +75,15 @@ pub fn init_world(testbed: &mut Testbed) {
|
||||
let shapes = vec![
|
||||
(
|
||||
Isometry3::identity(),
|
||||
ColliderShape::cuboid(rad, rad / 2.0, rad / 2.0),
|
||||
SharedShape::cuboid(rad, rad / 2.0, rad / 2.0),
|
||||
),
|
||||
(
|
||||
Isometry3::translation(rad, 0.0, 0.0),
|
||||
ColliderShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
SharedShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
),
|
||||
(
|
||||
Isometry3::translation(-rad, 0.0, 0.0),
|
||||
ColliderShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
SharedShape::cuboid(rad / 2.0, rad, rad / 2.0),
|
||||
),
|
||||
];
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
use crate::cdl::transformation::vhacd::VHACDParameters;
|
||||
use crate::dynamics::{CoefficientCombineRule, MassProperties, RigidBodyHandle};
|
||||
use crate::geometry::{ColliderShape, InteractionGroups};
|
||||
use crate::geometry::{InteractionGroups, SharedShape};
|
||||
use crate::math::{AngVector, Isometry, Point, Real, Rotation, Vector, DIM};
|
||||
use cdl::bounding_volume::AABB;
|
||||
use cdl::shape::Shape;
|
||||
@@ -47,7 +47,7 @@ impl ColliderFlags {
|
||||
///
|
||||
/// To build a new collider, use the `ColliderBuilder` structure.
|
||||
pub struct Collider {
|
||||
shape: ColliderShape,
|
||||
shape: SharedShape,
|
||||
density: Real,
|
||||
pub(crate) flags: ColliderFlags,
|
||||
pub(crate) parent: RigidBodyHandle,
|
||||
@@ -144,7 +144,7 @@ impl Collider {
|
||||
#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
|
||||
pub struct ColliderBuilder {
|
||||
/// The shape of the collider to be built.
|
||||
pub shape: ColliderShape,
|
||||
pub shape: SharedShape,
|
||||
/// The density of the collider to be built.
|
||||
density: Option<Real>,
|
||||
/// The friction coefficient of the collider to be built.
|
||||
@@ -169,7 +169,7 @@ pub struct ColliderBuilder {
|
||||
|
||||
impl ColliderBuilder {
|
||||
/// Initialize a new collider builder with the given shape.
|
||||
pub fn new(shape: ColliderShape) -> Self {
|
||||
pub fn new(shape: SharedShape) -> Self {
|
||||
Self {
|
||||
shape,
|
||||
density: None,
|
||||
@@ -191,20 +191,20 @@ impl ColliderBuilder {
|
||||
self.density.unwrap_or(default_density)
|
||||
}
|
||||
|
||||
pub fn compound(shapes: Vec<(Isometry<Real>, ColliderShape)>) -> Self {
|
||||
Self::new(ColliderShape::compound(shapes))
|
||||
pub fn compound(shapes: Vec<(Isometry<Real>, SharedShape)>) -> Self {
|
||||
Self::new(SharedShape::compound(shapes))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a ball shape defined by its radius.
|
||||
pub fn ball(radius: Real) -> Self {
|
||||
Self::new(ColliderShape::ball(radius))
|
||||
Self::new(SharedShape::ball(radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a cylindrical shape defined by its half-height
|
||||
/// (along along the y axis) and its radius.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn cylinder(half_height: Real, radius: Real) -> Self {
|
||||
Self::new(ColliderShape::cylinder(half_height, radius))
|
||||
Self::new(SharedShape::cylinder(half_height, radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a rounded cylindrical shape defined by its half-height
|
||||
@@ -212,7 +212,7 @@ impl ColliderBuilder {
|
||||
/// radius of the sphere used for dilating the cylinder).
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn round_cylinder(half_height: Real, radius: Real, border_radius: Real) -> Self {
|
||||
Self::new(ColliderShape::round_cylinder(
|
||||
Self::new(SharedShape::round_cylinder(
|
||||
half_height,
|
||||
radius,
|
||||
border_radius,
|
||||
@@ -223,7 +223,7 @@ impl ColliderBuilder {
|
||||
/// (along along the y axis) and its basis radius.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn cone(half_height: Real, radius: Real) -> Self {
|
||||
Self::new(ColliderShape::cone(half_height, radius))
|
||||
Self::new(SharedShape::cone(half_height, radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a rounded cone shape defined by its half-height
|
||||
@@ -231,77 +231,73 @@ impl ColliderBuilder {
|
||||
/// radius of the sphere used for dilating the cylinder).
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn round_cone(half_height: Real, radius: Real, border_radius: Real) -> Self {
|
||||
Self::new(ColliderShape::round_cone(
|
||||
half_height,
|
||||
radius,
|
||||
border_radius,
|
||||
))
|
||||
Self::new(SharedShape::round_cone(half_height, radius, border_radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a cuboid shape defined by its half-extents.
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn cuboid(hx: Real, hy: Real) -> Self {
|
||||
Self::new(ColliderShape::cuboid(hx, hy))
|
||||
Self::new(SharedShape::cuboid(hx, hy))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a round cuboid shape defined by its half-extents
|
||||
/// and border radius.
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn round_cuboid(hx: Real, hy: Real, border_radius: Real) -> Self {
|
||||
Self::new(ColliderShape::round_cuboid(hx, hy, border_radius))
|
||||
Self::new(SharedShape::round_cuboid(hx, hy, border_radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a capsule shape aligned with the `x` axis.
|
||||
pub fn capsule_x(half_height: Real, radius: Real) -> Self {
|
||||
let p = Point::from(Vector::x() * half_height);
|
||||
Self::new(ColliderShape::capsule(-p, p, radius))
|
||||
Self::new(SharedShape::capsule(-p, p, radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a capsule shape aligned with the `y` axis.
|
||||
pub fn capsule_y(half_height: Real, radius: Real) -> Self {
|
||||
let p = Point::from(Vector::y() * half_height);
|
||||
Self::new(ColliderShape::capsule(-p, p, radius))
|
||||
Self::new(SharedShape::capsule(-p, p, radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a capsule shape aligned with the `z` axis.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn capsule_z(half_height: Real, radius: Real) -> Self {
|
||||
let p = Point::from(Vector::z() * half_height);
|
||||
Self::new(ColliderShape::capsule(-p, p, radius))
|
||||
Self::new(SharedShape::capsule(-p, p, radius))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a cuboid shape defined by its half-extents.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn cuboid(hx: Real, hy: Real, hz: Real) -> Self {
|
||||
Self::new(ColliderShape::cuboid(hx, hy, hz))
|
||||
Self::new(SharedShape::cuboid(hx, hy, hz))
|
||||
}
|
||||
|
||||
/// Initialize a new collider builder with a round cuboid shape defined by its half-extents
|
||||
/// and border radius.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn round_cuboid(hx: Real, hy: Real, hz: Real, border_radius: Real) -> Self {
|
||||
Self::new(ColliderShape::round_cuboid(hx, hy, hz, border_radius))
|
||||
Self::new(SharedShape::round_cuboid(hx, hy, hz, border_radius))
|
||||
}
|
||||
|
||||
/// Initializes a collider builder with a segment shape.
|
||||
pub fn segment(a: Point<Real>, b: Point<Real>) -> Self {
|
||||
Self::new(ColliderShape::segment(a, b))
|
||||
Self::new(SharedShape::segment(a, b))
|
||||
}
|
||||
|
||||
/// Initializes a collider builder with a triangle shape.
|
||||
pub fn triangle(a: Point<Real>, b: Point<Real>, c: Point<Real>) -> Self {
|
||||
Self::new(ColliderShape::triangle(a, b, c))
|
||||
Self::new(SharedShape::triangle(a, b, c))
|
||||
}
|
||||
|
||||
/// Initializes a collider builder with a triangle mesh shape defined by its vertex and index buffers.
|
||||
pub fn trimesh(vertices: Vec<Point<Real>>, indices: Vec<[u32; 3]>) -> Self {
|
||||
Self::new(ColliderShape::trimesh(vertices, indices))
|
||||
Self::new(SharedShape::trimesh(vertices, indices))
|
||||
}
|
||||
|
||||
/// 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.
|
||||
pub fn convex_decomposition(vertices: &[Point<Real>], indices: &[[u32; DIM]]) -> Self {
|
||||
Self::new(ColliderShape::convex_decomposition(vertices, indices))
|
||||
Self::new(SharedShape::convex_decomposition(vertices, indices))
|
||||
}
|
||||
|
||||
/// Initializes a collider builder with a compound shape obtained from the decomposition of
|
||||
@@ -311,7 +307,7 @@ impl ColliderBuilder {
|
||||
indices: &[[u32; DIM]],
|
||||
border_radius: Real,
|
||||
) -> Self {
|
||||
Self::new(ColliderShape::round_convex_decomposition(
|
||||
Self::new(SharedShape::round_convex_decomposition(
|
||||
vertices,
|
||||
indices,
|
||||
border_radius,
|
||||
@@ -325,7 +321,7 @@ impl ColliderBuilder {
|
||||
indices: &[[u32; DIM]],
|
||||
params: &VHACDParameters,
|
||||
) -> Self {
|
||||
Self::new(ColliderShape::convex_decomposition_with_params(
|
||||
Self::new(SharedShape::convex_decomposition_with_params(
|
||||
vertices, indices, params,
|
||||
))
|
||||
}
|
||||
@@ -338,7 +334,7 @@ impl ColliderBuilder {
|
||||
params: &VHACDParameters,
|
||||
border_radius: Real,
|
||||
) -> Self {
|
||||
Self::new(ColliderShape::round_convex_decomposition_with_params(
|
||||
Self::new(SharedShape::round_convex_decomposition_with_params(
|
||||
vertices,
|
||||
indices,
|
||||
params,
|
||||
@@ -347,26 +343,26 @@ impl ColliderBuilder {
|
||||
}
|
||||
|
||||
pub fn convex_hull(points: &[Point<Real>]) -> Option<Self> {
|
||||
ColliderShape::convex_hull(points).map(|cp| Self::new(cp))
|
||||
SharedShape::convex_hull(points).map(|cp| Self::new(cp))
|
||||
}
|
||||
|
||||
pub fn round_convex_hull(points: &[Point<Real>], border_radius: Real) -> Option<Self> {
|
||||
ColliderShape::round_convex_hull(points, border_radius).map(|cp| Self::new(cp))
|
||||
SharedShape::round_convex_hull(points, border_radius).map(|cp| Self::new(cp))
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn convex_polyline(points: Vec<Point<Real>>) -> Option<Self> {
|
||||
ColliderShape::convex_polyline(points).map(|cp| Self::new(cp))
|
||||
SharedShape::convex_polyline(points).map(|cp| Self::new(cp))
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn round_convex_polyline(points: Vec<Point<Real>>, border_radius: Real) -> Option<Self> {
|
||||
ColliderShape::round_convex_polyline(points, border_radius).map(|cp| Self::new(cp))
|
||||
SharedShape::round_convex_polyline(points, border_radius).map(|cp| Self::new(cp))
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn convex_mesh(points: Vec<Point<Real>>, indices: &[[u32; 3]]) -> Option<Self> {
|
||||
ColliderShape::convex_mesh(points, indices).map(|cp| Self::new(cp))
|
||||
SharedShape::convex_mesh(points, indices).map(|cp| Self::new(cp))
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim3")]
|
||||
@@ -375,21 +371,21 @@ impl ColliderBuilder {
|
||||
indices: &[[u32; 3]],
|
||||
border_radius: Real,
|
||||
) -> Option<Self> {
|
||||
ColliderShape::round_convex_mesh(points, indices, border_radius).map(|cp| Self::new(cp))
|
||||
SharedShape::round_convex_mesh(points, indices, border_radius).map(|cp| Self::new(cp))
|
||||
}
|
||||
|
||||
/// Initializes a collider builder with a heightfield shape defined by its set of height and a scale
|
||||
/// factor along each coordinate axis.
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn heightfield(heights: na::DVector<Real>, scale: Vector<Real>) -> Self {
|
||||
Self::new(ColliderShape::heightfield(heights, scale))
|
||||
Self::new(SharedShape::heightfield(heights, scale))
|
||||
}
|
||||
|
||||
/// Initializes a collider builder with a heightfield shape defined by its set of height and a scale
|
||||
/// factor along each coordinate axis.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn heightfield(heights: na::DMatrix<Real>, scale: Vector<Real>) -> Self {
|
||||
Self::new(ColliderShape::heightfield(heights, scale))
|
||||
Self::new(SharedShape::heightfield(heights, scale))
|
||||
}
|
||||
|
||||
/// The default friction coefficient used by the collider builder.
|
||||
|
||||
@@ -1,381 +0,0 @@
|
||||
use crate::cdl::transformation::vhacd::{VHACDParameters, VHACD};
|
||||
use crate::math::{Isometry, Point, Real, Vector, DIM};
|
||||
use cdl::shape::{
|
||||
Ball, Capsule, Compound, Cuboid, HalfSpace, HeightField, RoundCuboid, RoundShape,
|
||||
RoundTriangle, Segment, Shape, ShapeType, TriMesh, Triangle,
|
||||
};
|
||||
#[cfg(feature = "dim3")]
|
||||
use cdl::shape::{
|
||||
Cone, ConvexPolyhedron, Cylinder, RoundCone, RoundConvexPolyhedron, RoundCylinder,
|
||||
};
|
||||
#[cfg(feature = "dim2")]
|
||||
use cdl::shape::{ConvexPolygon, RoundConvexPolygon};
|
||||
use std::ops::Deref;
|
||||
use std::sync::Arc;
|
||||
|
||||
/// The shape of a collider.
|
||||
#[derive(Clone)]
|
||||
pub struct ColliderShape(pub Arc<dyn Shape>);
|
||||
|
||||
impl Deref for ColliderShape {
|
||||
type Target = dyn Shape;
|
||||
fn deref(&self) -> &dyn Shape {
|
||||
&*self.0
|
||||
}
|
||||
}
|
||||
|
||||
impl ColliderShape {
|
||||
/// Initialize a compound shape defined by its subshapes.
|
||||
pub fn compound(shapes: Vec<(Isometry<Real>, ColliderShape)>) -> Self {
|
||||
let raw_shapes = shapes.into_iter().map(|s| (s.0, s.1 .0)).collect();
|
||||
let compound = Compound::new(raw_shapes);
|
||||
ColliderShape(Arc::new(compound))
|
||||
}
|
||||
|
||||
/// Initialize a ball shape defined by its radius.
|
||||
pub fn ball(radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(Ball::new(radius)))
|
||||
}
|
||||
|
||||
/// Initialize a cylindrical shape defined by its half-height
|
||||
/// (along along the y axis) and its radius.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn cylinder(half_height: Real, radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(Cylinder::new(half_height, radius)))
|
||||
}
|
||||
|
||||
/// Initialize a rounded cylindrical shape defined by its half-height
|
||||
/// (along along the y axis), its radius, and its roundedness (the
|
||||
/// radius of the sphere used for dilating the cylinder).
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn round_cylinder(half_height: Real, radius: Real, border_radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: Cylinder::new(half_height, radius),
|
||||
border_radius,
|
||||
}))
|
||||
}
|
||||
|
||||
/// Initialize a rounded cone shape defined by its half-height
|
||||
/// (along along the y axis), its radius, and its roundedness (the
|
||||
/// radius of the sphere used for dilating the cylinder).
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn round_cone(half_height: Real, radius: Real, border_radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: Cone::new(half_height, radius),
|
||||
border_radius,
|
||||
}))
|
||||
}
|
||||
|
||||
/// Initialize a cone shape defined by its half-height
|
||||
/// (along along the y axis) and its basis radius.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn cone(half_height: Real, radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(Cone::new(half_height, radius)))
|
||||
}
|
||||
|
||||
/// Initialize a cuboid shape defined by its half-extents.
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn cuboid(hx: Real, hy: Real) -> Self {
|
||||
ColliderShape(Arc::new(Cuboid::new(Vector::new(hx, hy))))
|
||||
}
|
||||
|
||||
/// Initialize a round cuboid shape defined by its half-extents and border radius.
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn round_cuboid(hx: Real, hy: Real, border_radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: Cuboid::new(Vector::new(hx, hy)),
|
||||
border_radius,
|
||||
}))
|
||||
}
|
||||
|
||||
/// Initialize a cuboid shape defined by its half-extents.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn cuboid(hx: Real, hy: Real, hz: Real) -> Self {
|
||||
ColliderShape(Arc::new(Cuboid::new(Vector::new(hx, hy, hz))))
|
||||
}
|
||||
|
||||
/// Initialize a round cuboid shape defined by its half-extents and border radius.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn round_cuboid(hx: Real, hy: Real, hz: Real, border_radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: Cuboid::new(Vector::new(hx, hy, hz)),
|
||||
border_radius,
|
||||
}))
|
||||
}
|
||||
|
||||
/// Initialize a capsule shape from its endpoints and radius.
|
||||
pub fn capsule(a: Point<Real>, b: Point<Real>, radius: Real) -> Self {
|
||||
ColliderShape(Arc::new(Capsule::new(a, b, radius)))
|
||||
}
|
||||
|
||||
/// Initialize a segment shape from its endpoints.
|
||||
pub fn segment(a: Point<Real>, b: Point<Real>) -> Self {
|
||||
ColliderShape(Arc::new(Segment::new(a, b)))
|
||||
}
|
||||
|
||||
/// Initializes a triangle shape.
|
||||
pub fn triangle(a: Point<Real>, b: Point<Real>, c: Point<Real>) -> Self {
|
||||
ColliderShape(Arc::new(Triangle::new(a, b, c)))
|
||||
}
|
||||
|
||||
/// Initializes a triangle mesh shape defined by its vertex and index buffers.
|
||||
pub fn trimesh(vertices: Vec<Point<Real>>, indices: Vec<[u32; 3]>) -> Self {
|
||||
ColliderShape(Arc::new(TriMesh::new(vertices, indices)))
|
||||
}
|
||||
|
||||
/// Initializes a compound shape obtained from the decomposition of the given trimesh (in 3D) or
|
||||
/// polyline (in 2D) into convex parts.
|
||||
pub fn convex_decomposition(vertices: &[Point<Real>], indices: &[[u32; DIM]]) -> Self {
|
||||
Self::convex_decomposition_with_params(vertices, indices, &VHACDParameters::default())
|
||||
}
|
||||
|
||||
/// Initializes a compound shape obtained from the decomposition of the given trimesh (in 3D) or
|
||||
/// polyline (in 2D) into convex parts dilated with round corners.
|
||||
pub fn round_convex_decomposition(
|
||||
vertices: &[Point<Real>],
|
||||
indices: &[[u32; DIM]],
|
||||
border_radius: Real,
|
||||
) -> Self {
|
||||
Self::round_convex_decomposition_with_params(
|
||||
vertices,
|
||||
indices,
|
||||
&VHACDParameters::default(),
|
||||
border_radius,
|
||||
)
|
||||
}
|
||||
|
||||
/// Initializes a compound shape obtained from the decomposition of the given trimesh (in 3D) or
|
||||
/// polyline (in 2D) into convex parts.
|
||||
pub fn convex_decomposition_with_params(
|
||||
vertices: &[Point<Real>],
|
||||
indices: &[[u32; DIM]],
|
||||
params: &VHACDParameters,
|
||||
) -> Self {
|
||||
let mut parts = vec![];
|
||||
let decomp = VHACD::decompose(params, &vertices, &indices, true);
|
||||
|
||||
#[cfg(feature = "dim2")]
|
||||
for vertices in decomp.compute_exact_convex_hulls(&vertices, &indices) {
|
||||
if let Some(convex) = Self::convex_polyline(vertices) {
|
||||
parts.push((Isometry::identity(), convex));
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim3")]
|
||||
for (vertices, indices) in decomp.compute_exact_convex_hulls(&vertices, &indices) {
|
||||
if let Some(convex) = Self::convex_mesh(vertices, &indices) {
|
||||
parts.push((Isometry::identity(), convex));
|
||||
}
|
||||
}
|
||||
|
||||
Self::compound(parts)
|
||||
}
|
||||
|
||||
/// Initializes a compound shape obtained from the decomposition of the given trimesh (in 3D) or
|
||||
/// polyline (in 2D) into convex parts dilated with round corners.
|
||||
pub fn round_convex_decomposition_with_params(
|
||||
vertices: &[Point<Real>],
|
||||
indices: &[[u32; DIM]],
|
||||
params: &VHACDParameters,
|
||||
border_radius: Real,
|
||||
) -> Self {
|
||||
let mut parts = vec![];
|
||||
let decomp = VHACD::decompose(params, &vertices, &indices, true);
|
||||
|
||||
#[cfg(feature = "dim2")]
|
||||
for vertices in decomp.compute_exact_convex_hulls(&vertices, &indices) {
|
||||
if let Some(convex) = Self::round_convex_polyline(vertices, border_radius) {
|
||||
parts.push((Isometry::identity(), convex));
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim3")]
|
||||
for (vertices, indices) in decomp.compute_exact_convex_hulls(&vertices, &indices) {
|
||||
if let Some(convex) = Self::round_convex_mesh(vertices, &indices, border_radius) {
|
||||
parts.push((Isometry::identity(), convex));
|
||||
}
|
||||
}
|
||||
|
||||
Self::compound(parts)
|
||||
}
|
||||
|
||||
pub fn convex_hull(points: &[Point<Real>]) -> Option<Self> {
|
||||
#[cfg(feature = "dim2")]
|
||||
return ConvexPolygon::from_convex_hull(points).map(|ch| ColliderShape(Arc::new(ch)));
|
||||
#[cfg(feature = "dim3")]
|
||||
return ConvexPolyhedron::from_convex_hull(points).map(|ch| ColliderShape(Arc::new(ch)));
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn convex_polyline(points: Vec<Point<Real>>) -> Option<Self> {
|
||||
ConvexPolygon::from_convex_polyline(points).map(|ch| ColliderShape(Arc::new(ch)))
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn convex_mesh(points: Vec<Point<Real>>, indices: &[[u32; 3]]) -> Option<Self> {
|
||||
ConvexPolyhedron::from_convex_mesh(points, indices).map(|ch| ColliderShape(Arc::new(ch)))
|
||||
}
|
||||
|
||||
pub fn round_convex_hull(points: &[Point<Real>], border_radius: Real) -> Option<Self> {
|
||||
#[cfg(feature = "dim2")]
|
||||
return ConvexPolygon::from_convex_hull(points).map(|ch| {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: ch,
|
||||
border_radius,
|
||||
}))
|
||||
});
|
||||
#[cfg(feature = "dim3")]
|
||||
return ConvexPolyhedron::from_convex_hull(points).map(|ch| {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: ch,
|
||||
border_radius,
|
||||
}))
|
||||
});
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn round_convex_polyline(points: Vec<Point<Real>>, border_radius: Real) -> Option<Self> {
|
||||
ConvexPolygon::from_convex_polyline(points).map(|ch| {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: ch,
|
||||
border_radius,
|
||||
}))
|
||||
})
|
||||
}
|
||||
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn round_convex_mesh(
|
||||
points: Vec<Point<Real>>,
|
||||
indices: &[[u32; 3]],
|
||||
border_radius: Real,
|
||||
) -> Option<Self> {
|
||||
ConvexPolyhedron::from_convex_mesh(points, indices).map(|ch| {
|
||||
ColliderShape(Arc::new(RoundShape {
|
||||
base_shape: ch,
|
||||
border_radius,
|
||||
}))
|
||||
})
|
||||
}
|
||||
|
||||
/// Initializes an heightfield shape defined by its set of height and a scale
|
||||
/// factor along each coordinate axis.
|
||||
#[cfg(feature = "dim2")]
|
||||
pub fn heightfield(heights: na::DVector<Real>, scale: Vector<Real>) -> Self {
|
||||
ColliderShape(Arc::new(HeightField::new(heights, scale)))
|
||||
}
|
||||
|
||||
/// Initializes an heightfield shape on the x-z plane defined by its set of height and a scale
|
||||
/// factor along each coordinate axis.
|
||||
#[cfg(feature = "dim3")]
|
||||
pub fn heightfield(heights: na::DMatrix<Real>, scale: Vector<Real>) -> Self {
|
||||
ColliderShape(Arc::new(HeightField::new(heights, scale)))
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "serde-serialize")]
|
||||
impl serde::Serialize for ColliderShape {
|
||||
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
||||
where
|
||||
S: serde::Serializer,
|
||||
{
|
||||
use crate::serde::ser::SerializeStruct;
|
||||
|
||||
if let Some(ser) = self.0.as_serialize() {
|
||||
let typ = self.0.shape_type();
|
||||
let mut state = serializer.serialize_struct("ColliderShape", 2)?;
|
||||
state.serialize_field("tag", &(typ as i32))?;
|
||||
state.serialize_field("inner", ser)?;
|
||||
state.end()
|
||||
} else {
|
||||
Err(serde::ser::Error::custom(
|
||||
"Found a non-serializable custom shape.",
|
||||
))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "serde-serialize")]
|
||||
impl<'de> serde::Deserialize<'de> for ColliderShape {
|
||||
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
|
||||
where
|
||||
D: serde::Deserializer<'de>,
|
||||
{
|
||||
struct Visitor {};
|
||||
impl<'de> serde::de::Visitor<'de> for Visitor {
|
||||
type Value = ColliderShape;
|
||||
fn expecting(&self, formatter: &mut std::fmt::Formatter) -> std::fmt::Result {
|
||||
write!(formatter, "one shape type tag and the inner shape data")
|
||||
}
|
||||
|
||||
fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
|
||||
where
|
||||
A: serde::de::SeqAccess<'de>,
|
||||
{
|
||||
use num::cast::FromPrimitive;
|
||||
|
||||
let tag: i32 = seq
|
||||
.next_element()?
|
||||
.ok_or_else(|| serde::de::Error::invalid_length(0, &self))?;
|
||||
|
||||
fn deser<'de, A, S: Shape + serde::Deserialize<'de>>(
|
||||
seq: &mut A,
|
||||
) -> Result<Arc<dyn Shape>, A::Error>
|
||||
where
|
||||
A: serde::de::SeqAccess<'de>,
|
||||
{
|
||||
let shape: S = seq.next_element()?.ok_or_else(|| {
|
||||
serde::de::Error::custom("Failed to deserialize builtin shape.")
|
||||
})?;
|
||||
Ok(Arc::new(shape) as Arc<dyn Shape>)
|
||||
}
|
||||
|
||||
let shape = match ShapeType::from_i32(tag) {
|
||||
Some(ShapeType::Ball) => deser::<A, Ball>(&mut seq)?,
|
||||
Some(ShapeType::Cuboid) => deser::<A, Cuboid>(&mut seq)?,
|
||||
Some(ShapeType::Capsule) => deser::<A, Capsule>(&mut seq)?,
|
||||
Some(ShapeType::Triangle) => deser::<A, Triangle>(&mut seq)?,
|
||||
Some(ShapeType::Segment) => deser::<A, Segment>(&mut seq)?,
|
||||
Some(ShapeType::TriMesh) => deser::<A, TriMesh>(&mut seq)?,
|
||||
Some(ShapeType::HeightField) => deser::<A, HeightField>(&mut seq)?,
|
||||
Some(ShapeType::HalfSpace) => deser::<A, HalfSpace>(&mut seq)?,
|
||||
Some(ShapeType::RoundCuboid) => deser::<A, RoundCuboid>(&mut seq)?,
|
||||
Some(ShapeType::RoundTriangle) => deser::<A, RoundTriangle>(&mut seq)?,
|
||||
#[cfg(feature = "dim2")]
|
||||
Some(ShapeType::ConvexPolygon) => deser::<A, ConvexPolygon>(&mut seq)?,
|
||||
#[cfg(feature = "dim2")]
|
||||
Some(ShapeType::RoundConvexPolygon) => {
|
||||
deser::<A, RoundConvexPolygon>(&mut seq)?
|
||||
}
|
||||
#[cfg(feature = "dim3")]
|
||||
Some(ShapeType::Cylinder) => deser::<A, Cylinder>(&mut seq)?,
|
||||
#[cfg(feature = "dim3")]
|
||||
Some(ShapeType::ConvexPolyhedron) => deser::<A, ConvexPolyhedron>(&mut seq)?,
|
||||
#[cfg(feature = "dim3")]
|
||||
Some(ShapeType::Cone) => deser::<A, Cone>(&mut seq)?,
|
||||
#[cfg(feature = "dim3")]
|
||||
Some(ShapeType::RoundCylinder) => deser::<A, RoundCylinder>(&mut seq)?,
|
||||
#[cfg(feature = "dim3")]
|
||||
Some(ShapeType::RoundCone) => deser::<A, RoundCone>(&mut seq)?,
|
||||
#[cfg(feature = "dim3")]
|
||||
Some(ShapeType::RoundConvexPolyhedron) => {
|
||||
deser::<A, RoundConvexPolyhedron>(&mut seq)?
|
||||
}
|
||||
Some(ShapeType::Compound) => {
|
||||
return Err(serde::de::Error::custom(
|
||||
"found invalid shape type to deserialize",
|
||||
))
|
||||
}
|
||||
None => {
|
||||
return Err(serde::de::Error::custom(
|
||||
"found invalid shape type to deserialize",
|
||||
))
|
||||
}
|
||||
};
|
||||
|
||||
Ok(ColliderShape(shape))
|
||||
}
|
||||
}
|
||||
|
||||
deserializer.deserialize_struct("ColliderShape", &["tag", "inner"], Visitor {})
|
||||
}
|
||||
}
|
||||
@@ -3,7 +3,6 @@
|
||||
pub use self::broad_phase_multi_sap::BroadPhase;
|
||||
pub use self::collider::{Collider, ColliderBuilder};
|
||||
pub use self::collider_set::{ColliderHandle, ColliderSet};
|
||||
pub use self::collider_shape::ColliderShape;
|
||||
pub use self::contact_pair::{ContactData, ContactManifoldData};
|
||||
pub use self::contact_pair::{ContactPair, SolverContact, SolverFlags};
|
||||
pub use self::interaction_graph::{
|
||||
@@ -43,6 +42,7 @@ pub type Ray = cdl::query::Ray;
|
||||
pub type RayIntersection = cdl::query::RayIntersection;
|
||||
/// The the projection of a point on a collider.
|
||||
pub type PointProjection = cdl::query::PointProjection;
|
||||
pub use cdl::shape::SharedShape;
|
||||
|
||||
#[derive(Copy, Clone, Hash, Debug)]
|
||||
/// Events occurring when two collision objects start or stop being in contact (or penetration).
|
||||
@@ -99,7 +99,6 @@ pub(crate) fn default_query_dispatcher() -> std::sync::Arc<dyn cdl::query::Query
|
||||
mod broad_phase_multi_sap;
|
||||
mod collider;
|
||||
mod collider_set;
|
||||
mod collider_shape;
|
||||
mod contact_pair;
|
||||
mod interaction_graph;
|
||||
mod interaction_groups;
|
||||
|
||||
Reference in New Issue
Block a user