bevy_rapier3d/dynamics/
revolute_joint.rs1use crate::dynamics::{GenericJoint, GenericJointBuilder};
2use crate::math::{Real, Vect};
3use crate::plugin::context::RapierRigidBodySet;
4use bevy::prelude::Entity;
5use rapier::dynamics::{
6 JointAxesMask, JointAxis, JointLimits, JointMotor, MotorModel, RigidBodyHandle, RigidBodySet,
7};
8
9#[cfg(doc)]
10use crate::prelude::RapierContext;
11
12use super::TypedJoint;
13
14#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
15#[derive(Copy, Clone, Debug, PartialEq)]
16#[repr(transparent)]
17pub struct RevoluteJoint {
19 pub data: GenericJoint,
21}
22
23#[cfg(feature = "dim2")]
24impl Default for RevoluteJoint {
25 fn default() -> Self {
26 Self::new()
27 }
28}
29
30impl RevoluteJoint {
31 #[cfg(feature = "dim2")]
33 pub fn new() -> Self {
34 let data = GenericJointBuilder::new(JointAxesMask::LOCKED_REVOLUTE_AXES);
35 Self { data: data.build() }
36 }
37
38 #[cfg(feature = "dim3")]
42 pub fn new(axis: Vect) -> Self {
43 let data = GenericJointBuilder::new(JointAxesMask::LOCKED_REVOLUTE_AXES)
44 .local_axis1(axis)
45 .local_axis2(axis)
46 .build();
47 Self { data }
48 }
49
50 pub fn contacts_enabled(&self) -> bool {
52 self.data.contacts_enabled()
53 }
54
55 pub fn set_contacts_enabled(&mut self, enabled: bool) -> &mut Self {
57 self.data.set_contacts_enabled(enabled);
58 self
59 }
60
61 #[must_use]
63 pub fn local_anchor1(&self) -> Vect {
64 self.data.local_anchor1()
65 }
66
67 pub fn set_local_anchor1(&mut self, anchor1: Vect) -> &mut Self {
69 self.data.set_local_anchor1(anchor1);
70 self
71 }
72
73 #[must_use]
75 pub fn local_anchor2(&self) -> Vect {
76 self.data.local_anchor2()
77 }
78
79 pub fn set_local_anchor2(&mut self, anchor2: Vect) -> &mut Self {
81 self.data.set_local_anchor2(anchor2);
82 self
83 }
84
85 pub fn set_local_axis1(&mut self, axis1: Vect) -> &mut Self {
87 self.data.set_local_axis1(axis1);
88 self
89 }
90
91 pub fn set_local_axis2(&mut self, axis2: Vect) -> &mut Self {
93 self.data.set_local_axis2(axis2);
94 self
95 }
96
97 #[must_use]
99 pub fn motor(&self) -> Option<&JointMotor> {
100 self.data.motor(JointAxis::AngX)
101 }
102
103 pub fn set_motor_model(&mut self, model: MotorModel) -> &mut Self {
105 self.data.set_motor_model(JointAxis::AngX, model);
106 self
107 }
108
109 pub fn set_motor_velocity(&mut self, target_vel: Real, factor: Real) -> &mut Self {
111 self.data
112 .set_motor_velocity(JointAxis::AngX, target_vel, factor);
113 self
114 }
115
116 pub fn set_motor_position(
118 &mut self,
119 target_pos: Real,
120 stiffness: Real,
121 damping: Real,
122 ) -> &mut Self {
123 self.data
124 .set_motor_position(JointAxis::AngX, target_pos, stiffness, damping);
125 self
126 }
127
128 pub fn set_motor(
130 &mut self,
131 target_pos: Real,
132 target_vel: Real,
133 stiffness: Real,
134 damping: Real,
135 ) -> &mut Self {
136 self.data
137 .set_motor(JointAxis::AngX, target_pos, target_vel, stiffness, damping);
138 self
139 }
140
141 pub fn set_motor_max_force(&mut self, max_force: Real) -> &mut Self {
143 self.data.set_motor_max_force(JointAxis::AngX, max_force);
144 self
145 }
146
147 #[must_use]
149 pub fn limits(&self) -> Option<&JointLimits<Real>> {
150 self.data.limits(JointAxis::AngX)
151 }
152
153 pub fn set_limits(&mut self, limits: [Real; 2]) -> &mut Self {
155 self.data.set_limits(JointAxis::AngX, limits);
156 self
157 }
158
159 pub fn angle_from_handles(
169 &self,
170 bodies: &RigidBodySet,
171 body1: RigidBodyHandle,
172 body2: RigidBodyHandle,
173 ) -> f32 {
174 let joint = self.data.raw.as_revolute().unwrap();
176
177 let rb1 = &bodies[body1];
178 let rb2 = &bodies[body2];
179 joint.angle(rb1.rotation(), rb2.rotation())
180 }
181
182 pub fn angle(&self, rigidbody_set: &RapierRigidBodySet, body1: Entity, body2: Entity) -> f32 {
189 let rb1 = rigidbody_set.entity2body().get(&body1).unwrap();
190 let rb2 = rigidbody_set.entity2body().get(&body2).unwrap();
191 self.angle_from_handles(&rigidbody_set.bodies, *rb1, *rb2)
192 }
193}
194
195impl From<RevoluteJoint> for GenericJoint {
196 fn from(joint: RevoluteJoint) -> GenericJoint {
197 joint.data
198 }
199}
200
201#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
205#[derive(Copy, Clone, Debug, PartialEq)]
206pub struct RevoluteJointBuilder(RevoluteJoint);
207
208#[cfg(feature = "dim2")]
209impl Default for RevoluteJointBuilder {
210 fn default() -> Self {
211 Self::new()
212 }
213}
214
215impl RevoluteJointBuilder {
216 #[cfg(feature = "dim2")]
218 pub fn new() -> Self {
219 Self(RevoluteJoint::new())
220 }
221
222 #[cfg(feature = "dim3")]
226 pub fn new(axis: Vect) -> Self {
227 Self(RevoluteJoint::new(axis))
228 }
229
230 #[must_use]
232 pub fn local_anchor1(mut self, anchor1: Vect) -> Self {
233 self.0.set_local_anchor1(anchor1);
234 self
235 }
236
237 #[must_use]
239 pub fn local_anchor2(mut self, anchor2: Vect) -> Self {
240 self.0.set_local_anchor2(anchor2);
241 self
242 }
243
244 pub fn local_axis1(mut self, axis1: Vect) -> Self {
246 self.0.set_local_axis1(axis1);
247 self
248 }
249
250 pub fn local_axis2(mut self, axis2: Vect) -> Self {
252 self.0.set_local_axis2(axis2);
253 self
254 }
255
256 #[must_use]
258 pub fn motor_model(mut self, model: MotorModel) -> Self {
259 self.0.set_motor_model(model);
260 self
261 }
262
263 #[must_use]
265 pub fn motor_velocity(mut self, target_vel: Real, factor: Real) -> Self {
266 self.0.set_motor_velocity(target_vel, factor);
267 self
268 }
269
270 #[must_use]
272 pub fn motor_position(mut self, target_pos: Real, stiffness: Real, damping: Real) -> Self {
273 self.0.set_motor_position(target_pos, stiffness, damping);
274 self
275 }
276
277 #[must_use]
279 pub fn motor(
280 mut self,
281 target_pos: Real,
282 target_vel: Real,
283 stiffness: Real,
284 damping: Real,
285 ) -> Self {
286 self.0.set_motor(target_pos, target_vel, stiffness, damping);
287 self
288 }
289
290 #[must_use]
292 pub fn motor_max_force(mut self, max_force: Real) -> Self {
293 self.0.set_motor_max_force(max_force);
294 self
295 }
296
297 #[must_use]
299 pub fn limits(mut self, limits: [Real; 2]) -> Self {
300 self.0.set_limits(limits);
301 self
302 }
303
304 #[must_use]
306 pub fn build(self) -> RevoluteJoint {
307 self.0
308 }
309}
310
311impl From<RevoluteJointBuilder> for TypedJoint {
312 fn from(joint: RevoluteJointBuilder) -> TypedJoint {
313 joint.0.into()
314 }
315}
316
317impl From<RevoluteJoint> for TypedJoint {
318 fn from(joint: RevoluteJoint) -> TypedJoint {
319 TypedJoint::RevoluteJoint(joint)
320 }
321}