aboutsummaryrefslogtreecommitdiff
path: root/src/dynamics/rigid_body_components.rs
diff options
context:
space:
mode:
authorSébastien Crozet <developer@crozet.re>2021-06-02 17:15:46 +0200
committerGitHub <noreply@github.com>2021-06-02 17:15:46 +0200
commit6ba1c9dec184adcba2c68cc1851dc05587fd0bf0 (patch)
treeb672cfc4db1d2f426dad931d77098ecb4a600358 /src/dynamics/rigid_body_components.rs
parent3bac79ecacdeaa18de19127b7a6c82cbfab29d14 (diff)
parentbde6657287cd32a801abb996322c520673406418 (diff)
downloadrapier-6ba1c9dec184adcba2c68cc1851dc05587fd0bf0.tar.gz
rapier-6ba1c9dec184adcba2c68cc1851dc05587fd0bf0.tar.bz2
rapier-6ba1c9dec184adcba2c68cc1851dc05587fd0bf0.zip
Merge pull request #196 from dimforge/api_changes
More API changes
Diffstat (limited to 'src/dynamics/rigid_body_components.rs')
-rw-r--r--src/dynamics/rigid_body_components.rs64
1 files changed, 44 insertions, 20 deletions
diff --git a/src/dynamics/rigid_body_components.rs b/src/dynamics/rigid_body_components.rs
index 2a652f7..ec67b66 100644
--- a/src/dynamics/rigid_body_components.rs
+++ b/src/dynamics/rigid_body_components.rs
@@ -1,7 +1,7 @@
use crate::data::{ComponentSetMut, ComponentSetOption};
use crate::dynamics::MassProperties;
use crate::geometry::{
- ColliderChanges, ColliderHandle, ColliderMassProperties, ColliderParent, ColliderPosition,
+ ColliderChanges, ColliderHandle, ColliderMassProps, ColliderParent, ColliderPosition,
ColliderShape, InteractionGraph, RigidBodyGraphIndex,
};
use crate::math::{AngVector, AngularInertia, Isometry, Point, Real, Translation, Vector};
@@ -54,16 +54,23 @@ pub type BodyStatus = RigidBodyType;
/// The status of a body, governing the way it is affected by external forces.
pub enum RigidBodyType {
/// A `RigidBodyType::Dynamic` body can be affected by all external forces.
- Dynamic,
+ Dynamic = 0,
/// A `RigidBodyType::Static` body cannot be affected by external forces.
- Static,
- /// A `RigidBodyType::Kinematic` body cannot be affected by any external forces but can be controlled
+ Static = 1,
+ /// A `RigidBodyType::KinematicPositionBased` body cannot be affected by any external forces but can be controlled
/// by the user at the position level while keeping realistic one-way interaction with dynamic bodies.
///
/// One-way interaction means that a kinematic body can push a dynamic body, but a kinematic body
/// cannot be pushed by anything. In other words, the trajectory of a kinematic body can only be
/// modified by the user and is independent from any contact or joint it is involved in.
- Kinematic,
+ KinematicPositionBased = 2,
+ /// A `RigidBodyType::KinematicVelocityBased` body cannot be affected by any external forces but can be controlled
+ /// by the user at the velocity level while keeping realistic one-way interaction with dynamic bodies.
+ ///
+ /// One-way interaction means that a kinematic body can push a dynamic body, but a kinematic body
+ /// cannot be pushed by anything. In other words, the trajectory of a kinematic body can only be
+ /// modified by the user and is independent from any contact or joint it is involved in.
+ KinematicVelocityBased = 3,
// Semikinematic, // A kinematic that performs automatic CCD with the static environment to avoid traversing it?
// Disabled,
}
@@ -81,7 +88,8 @@ impl RigidBodyType {
/// Is this rigid-body kinematic (i.e. can move but is unaffected by forces)?
pub fn is_kinematic(self) -> bool {
- self == RigidBodyType::Kinematic
+ self == RigidBodyType::KinematicPositionBased
+ || self == RigidBodyType::KinematicVelocityBased
}
}
@@ -166,7 +174,7 @@ impl RigidBodyPosition {
mprops: &RigidBodyMassProps,
) -> Isometry<Real> {
let new_vels = forces.integrate(dt, vels, mprops);
- new_vels.integrate(dt, &self.position, &mprops.mass_properties.local_com)
+ new_vels.integrate(dt, &self.position, &mprops.local_mprops.local_com)
}
}
@@ -208,7 +216,7 @@ pub struct RigidBodyMassProps {
/// Flags for locking rotation and translation.
pub flags: RigidBodyMassPropsFlags,
/// The local mass properties of the rigid-body.
- pub mass_properties: MassProperties,
+ pub local_mprops: MassProperties,
/// The world-space center of mass of the rigid-body.
pub world_com: Point<Real>,
/// The inverse mass taking into account translation locking.
@@ -222,7 +230,7 @@ impl Default for RigidBodyMassProps {
fn default() -> Self {
Self {
flags: RigidBodyMassPropsFlags::empty(),
- mass_properties: MassProperties::zero(),
+ local_mprops: MassProperties::zero(),
world_com: Point::origin(),
effective_inv_mass: 0.0,
effective_world_inv_inertia_sqrt: AngularInertia::zero(),
@@ -239,11 +247,20 @@ impl From<RigidBodyMassPropsFlags> for RigidBodyMassProps {
}
}
+impl From<MassProperties> for RigidBodyMassProps {
+ fn from(local_mprops: MassProperties) -> Self {
+ Self {
+ local_mprops,
+ ..Default::default()
+ }
+ }
+}
+
impl RigidBodyMassProps {
/// The mass of the rigid-body.
#[must_use]
pub fn mass(&self) -> Real {
- crate::utils::inv(self.mass_properties.inv_mass)
+ crate::utils::inv(self.local_mprops.inv_mass)
}
/// The effective mass (that takes the potential translation locking into account) of
@@ -255,11 +272,10 @@ impl RigidBodyMassProps {
/// Update the world-space mass properties of `self`, taking into account the new position.
pub fn update_world_mass_properties(&mut self, position: &Isometry<Real>) {
- self.world_com = self.mass_properties.world_com(&position);
- self.effective_inv_mass = self.mass_properties.inv_mass;
- self.effective_world_inv_inertia_sqrt = self
- .mass_properties
- .world_inv_inertia_sqrt(&position.rotation);
+ self.world_com = self.local_mprops.world_com(&position);
+ self.effective_inv_mass = self.local_mprops.inv_mass;
+ self.effective_world_inv_inertia_sqrt =
+ self.local_mprops.world_inv_inertia_sqrt(&position.rotation);
// Take into account translation/rotation locking.
if self
@@ -665,7 +681,7 @@ impl RigidBodyColliders {
co_pos: &mut ColliderPosition,
co_parent: &ColliderParent,
co_shape: &ColliderShape,
- co_mprops: &ColliderMassProperties,
+ co_mprops: &ColliderMassProps,
) {
rb_changes.set(
RigidBodyChanges::MODIFIED | RigidBodyChanges::COLLIDERS,
@@ -684,7 +700,7 @@ impl RigidBodyColliders {
.mass_properties(&**co_shape)
.transform_by(&co_parent.pos_wrt_parent);
self.0.push(co_handle);
- rb_mprops.mass_properties += mass_properties;
+ rb_mprops.local_mprops += mass_properties;
rb_mprops.update_world_mass_properties(&rb_pos.position);
}
@@ -759,7 +775,7 @@ pub struct RigidBodyActivation {
impl Default for RigidBodyActivation {
fn default() -> Self {
- Self::new_active()
+ Self::active()
}
}
@@ -770,7 +786,7 @@ impl RigidBodyActivation {
}
/// Create a new rb_activation status initialised with the default rb_activation threshold and is active.
- pub fn new_active() -> Self {
+ pub fn active() -> Self {
RigidBodyActivation {
threshold: Self::default_threshold(),
energy: Self::default_threshold() * 4.0,
@@ -779,7 +795,7 @@ impl RigidBodyActivation {
}
/// Create a new rb_activation status initialised with the default rb_activation threshold and is inactive.
- pub fn new_inactive() -> Self {
+ pub fn inactive() -> Self {
RigidBodyActivation {
threshold: Self::default_threshold(),
energy: 0.0,
@@ -787,6 +803,14 @@ impl RigidBodyActivation {
}
}
+ /// Create a new activation status that prevents the rigid-body from sleeping.
+ pub fn cannot_sleep() -> Self {
+ RigidBodyActivation {
+ threshold: -Real::MAX,
+ ..Self::active()
+ }
+ }
+
/// Returns `true` if the body is not asleep.
#[inline]
pub fn is_active(&self) -> bool {