1use std::cell::RefCell;
2use std::rc::{Rc, Weak};
3
4#[cfg(feature="serde_support")]
5use serde::{Serialize, Deserialize};
6
7use crate::b2_contact::*;
8use crate::b2_fixture::*;
9use crate::b2_joint::*;
10use crate::b2_math::*;
11use crate::b2rs_common::UserDataType;
12use crate::b2_shape::*;
13use crate::b2_world::*;
14use crate::private::dynamics::b2_body as private;
15
16use crate::b2rs_linked_list::*;
17use crate::b2rs_double_linked_list::*;
18
19use bitflags::bitflags;
20
21#[derive(Debug, Copy, Clone, PartialEq)]
26#[cfg_attr(feature = "serde_support", derive(Serialize, Deserialize))]
27pub enum B2bodyType {
28 B2StaticBody = 0,
29 B2KinematicBody,
30 B2DynamicBody,
31}
32
33impl Default for B2bodyType {
34 fn default() -> Self {
35 return B2bodyType::B2StaticBody;
36 }
37}
38
39impl<D: UserDataType> Default for B2bodyDef<D> {
40 fn default() -> Self {
42 return Self {
43 position: B2vec2::zero(),
44 angle: 0.0,
45 linear_velocity: B2vec2::zero(),
46 angular_velocity: 0.0,
47 linear_damping: 0.0,
48 angular_damping: 0.0,
49 allow_sleep: true,
50 awake: true,
51 fixed_rotation: false,
52 bullet: false,
53 body_type: B2bodyType::B2StaticBody,
54 enabled: true,
55 gravity_scale: 1.0,
56 user_data: None,
57 };
58 }
59}
60
61impl<D:UserDataType> LinkedListNode<B2body<D>> for B2body<D>
62{
63 fn get_next(&self) -> Option<BodyPtr<D>> {
64 return self.m_next.clone();
65 }
66 fn set_next(&mut self, value: Option<BodyPtr<D>>)
67 {
68 self.m_next = value;
69 }
70 fn take_next(&mut self) -> Option<BodyPtr<D>> {
71 return self.m_next.take();
72 }
73}
74
75impl<D:UserDataType> DoubleLinkedListNode<B2body<D>> for B2body<D>
76{
77 fn get_prev(&self) -> Option<BodyWeakPtr<D>>
78 {
79 return self.m_prev.clone();
80 }
81 fn set_prev(&mut self, value: Option<BodyWeakPtr<D>>)
82 {
83 self.m_prev = value;
84 }
85}
86
87#[derive(Debug, Clone)]
90#[cfg_attr(feature = "serde_support", derive(Serialize, Deserialize))]
91pub struct B2bodyDef<D: UserDataType> {
92 pub body_type: B2bodyType,
95
96 pub position: B2vec2,
99
100 pub angle: f32,
102
103 pub linear_velocity: B2vec2,
105
106 pub angular_velocity: f32,
108
109 pub linear_damping: f32,
114
115 pub angular_damping: f32,
120
121 pub allow_sleep: bool,
124
125 pub awake: bool,
127
128 pub fixed_rotation: bool,
130
131 pub bullet: bool,
138
139 pub enabled: bool,
141
142 pub user_data: Option<D::Body>,
144
145 pub gravity_scale: f32,
147}
148
149pub type BodyPtr<D> = Rc<RefCell<B2body<D>>>;
150pub type BodyWeakPtr<D> = Weak<RefCell<B2body<D>>>;
151
152#[derive(Default)]
154pub struct B2body<D: UserDataType>
155{
157 pub(crate) m_type: B2bodyType,
158
159 pub(crate) m_flags: BodyFlags,
160
161 pub(crate) m_island_index: i32,
162
163 pub(crate) m_xf: B2Transform,
165 pub(crate) m_sweep: B2Sweep,
167
168 pub(crate) m_linear_velocity: B2vec2,
169 pub(crate) m_angular_velocity: f32,
170
171 pub(crate) m_force: B2vec2,
172 pub(crate) m_torque: f32,
173
174 pub(crate) m_world: B2worldWeakPtr<D>,
175 pub(crate) m_prev: Option<BodyWeakPtr<D>>,
176 pub(crate) m_next: Option<BodyPtr<D>>,
177
178 pub(crate) m_fixture_list: LinkedList<B2fixture<D>>,
179 pub(crate) m_fixture_count: i32,
180
181 pub(crate) m_joint_list: DoubleLinkedList<B2jointEdge<D>>,
182 pub(crate) m_contact_list: DoubleLinkedList<B2contactEdge<D>>,
183
184 pub(crate) m_mass: f32,
185 pub(crate) m_inv_mass: f32,
186
187 pub(crate) m_i: f32,
189 pub(crate) m_inv_i: f32,
190
191 pub(crate) m_linear_damping: f32,
192 pub(crate) m_angular_damping: f32,
193 pub(crate) m_gravity_scale: f32,
194
195 pub(crate) m_sleep_time: f32,
196
197 pub(crate) m_user_data: Option<D::Body>,
198}
199
200
201impl<D: UserDataType> Drop for B2body<D>
202{
203 fn drop(&mut self) {
204 self.m_fixture_list.remove_all();
205 }
206}
207
208
209bitflags! {
210 #[derive(Default)]
212 pub struct BodyFlags: u16 {
213 const E_ISLAND_FLAG = 0x0001;
214 const E_AWAKE_FLAG = 0x0002;
215 const E_AUTO_SLEEP_FLAG = 0x0004;
216 const E_BULLET_FLAG = 0x0008;
217 const E_FIXED_ROTATION_FLAG = 0x0010;
218 const E_ENABLED_FLAG = 0x0020;
219 const E_TOI_FLAG = 0x0040;
220 }
221}
222
223impl<D: UserDataType> B2body<D> {
224 pub fn create_fixture(self_: BodyPtr<D>, def: &B2fixtureDef<D>) -> FixturePtr<D> {
234 return private::create_fixture(self_, def);
235 }
236
237 pub fn create_fixture_by_shape(self_: BodyPtr<D>, shape: ShapeDefPtr, density: f32) -> FixturePtr<D> {
247 return private::create_fixture_by_shape(self_, shape, density);
248 }
249
250 pub fn destroy_fixture(self_: BodyPtr<D>, fixture: FixturePtr<D>) {
260 private::destroy_fixture(self_, fixture);
261 }
262
263 pub fn set_transform(&mut self, position: B2vec2, angle: f32) {
269 private::set_transform(self, position, angle);
270 }
271
272 pub fn get_transform(&self) -> B2Transform {
276 return inline::get_transform(self);
277 }
278
279 pub fn get_position(&self) -> B2vec2 {
283 return inline::get_position(self);
284 }
285
286 pub fn get_angle(&self) -> f32 {
290 return inline::get_angle(self);
291 }
292
293 pub fn get_world_center(&self) -> B2vec2 {
295 return inline::get_world_center(self);
296 }
297
298 pub fn get_local_center(&self) -> B2vec2 {
300 return inline::get_local_center(self);
301 }
302
303 pub fn set_linear_velocity(&mut self, v: B2vec2) {
306 inline::set_linear_velocity(self, v);
307 }
308
309 pub fn get_linear_velocity(&self) -> B2vec2 {
313 return inline::get_linear_velocity(self);
314 }
315
316 pub fn set_angular_velocity(&mut self, omega: f32) {
319 inline::set_angular_velocity(self, omega);
320 }
321
322 pub fn get_angular_velocity(&self) -> f32 {
326 return inline::get_angular_velocity(self);
327 }
328
329 pub fn apply_force(&mut self, force: B2vec2, point: B2vec2, wake: bool) {
336 inline::apply_force(self, force, point, wake);
337 }
338
339 pub fn apply_force_to_center(&mut self, force: B2vec2, wake: bool) {
343 inline::apply_force_to_center(self, force, wake);
344 }
345
346 pub fn apply_torque(&mut self, torque: f32, wake: bool) {
351 inline::apply_torque(self, torque, wake);
352 }
353
354 pub fn apply_linear_impulse(&mut self, impulse: B2vec2, point: B2vec2, wake: bool) {
361 inline::apply_linear_impulse(self, impulse, point, wake);
362 }
363
364 pub fn apply_linear_impulse_to_center(&mut self, impulse: B2vec2, wake: bool) {
368 inline::apply_linear_impulse_to_center(self, impulse, wake);
369 }
370
371 pub fn apply_angular_impulse(&mut self, impulse: f32, wake: bool) {
375 inline::apply_angular_impulse(self, impulse, wake);
376 }
377
378 pub fn get_mass(&self) -> f32 {
382 return inline::get_mass(self);
383 }
384
385 pub fn get_inertia(&self) -> f32 {
389 return inline::get_inertia(self);
390 }
391
392 pub fn get_mass_data(&self, data: &mut B2massData) {
396 inline::get_mass_data(self, data);
397 }
398
399 pub fn set_mass_data(&mut self, mass_data: &B2massData) {
405 private::set_mass_data(self, mass_data);
406 }
407
408 pub fn reset_mass_data(&mut self) {
412 private::reset_mass_data(self);
413 }
414
415 pub fn get_world_point(&self, local_point: B2vec2) -> B2vec2 {
420 return inline::get_world_point(self, local_point);
421 }
422
423 pub fn get_world_vector(&self, local_vector: B2vec2) -> B2vec2 {
428 return inline::get_world_vector(self, local_vector);
429 }
430
431 pub fn get_local_point(&self, world_point: B2vec2) -> B2vec2 {
436 return inline::get_local_point(self, world_point);
437 }
438
439 pub fn get_local_vector(&self, world_vector: B2vec2) -> B2vec2 {
444 return inline::get_local_vector(self, world_vector);
445 }
446
447 pub fn get_linear_velocity_from_world_point(&self, world_point: B2vec2) -> B2vec2 {
452 return inline::get_linear_velocity_from_world_point(self, world_point);
453 }
454
455 pub fn get_linear_velocity_from_local_point(&self, local_point: B2vec2) -> B2vec2 {
460 return inline::get_linear_velocity_from_local_point(self, local_point);
461 }
462
463 pub fn get_linear_damping(&self) -> f32 {
465 return inline::get_linear_damping(self);
466 }
467
468 pub fn set_linear_damping(&mut self, linear_damping: f32) {
470 inline::set_linear_damping(self, linear_damping);
471 }
472
473 pub fn get_angular_damping(&self) -> f32 {
475 return inline::get_angular_damping(self);
476 }
477
478 pub fn set_angular_damping(&mut self, angular_damping: f32) {
480 inline::set_angular_damping(self, angular_damping);
481 }
482
483 pub fn get_gravity_scale(&self) -> f32 {
485 return inline::get_gravity_scale(self);
486 }
487
488 pub fn set_gravity_scale(&mut self, scale: f32) {
490 inline::set_gravity_scale(self, scale);
491 }
492
493 pub fn set_type(self_: BodyPtr<D>, body_type: B2bodyType) {
495 private::set_type(self_, body_type);
496 }
497
498 pub fn get_type(&self) -> B2bodyType {
500 return inline::get_type(self);
501 }
502
503 pub fn set_bullet(&mut self, flag: bool) {
505 inline::set_bullet(self, flag);
506 }
507
508 pub fn is_bullet(&self) -> bool {
510 return inline::is_bullet(self);
511 }
512
513 pub fn set_sleeping_allowed(&mut self, flag: bool) {
516 inline::set_sleeping_allowed(self, flag);
517 }
518
519 pub fn is_sleeping_allowed(&self) -> bool {
521 return inline::is_sleeping_allowed(self);
522 }
523
524 pub fn set_awake(&mut self, flag: bool) {
528 inline::set_awake(self, flag);
529 }
530
531 pub fn is_awake(&self) -> bool {
535 return inline::is_awake(self);
536 }
537
538 pub fn set_enabled(self_: BodyPtr<D>, flag: bool) {
551 private::set_enabled(self_, flag);
552 }
553
554 pub fn is_enabled(&self) -> bool {
556 return inline::is_enabled(self);
557 }
558
559 pub fn set_fixed_rotation(&mut self, flag: bool) {
562 private::set_fixed_rotation(self, flag);
563 }
564
565 pub fn is_fixed_rotation(&self) -> bool {
567 return inline::is_fixed_rotation(self);
568 }
569
570 pub fn get_fixture_list(&self) -> &LinkedList<B2fixture<D>> {
572 return inline::get_fixture_list(self);
573 }
574 pub fn get_joint_list(&self) -> &DoubleLinkedList<B2jointEdge<D>> {
580 return inline::get_joint_list(self);
581 }
582 pub fn get_joint_list_mut(&mut self) -> &mut DoubleLinkedList<B2jointEdge<D>> {
583 return inline::get_joint_list_mut(self);
584 }
585
586 pub fn get_contact_list(&self) -> &DoubleLinkedList<B2contactEdge<D>> {
592 return inline::get_contact_list(self);
593 }
594 pub fn get_next(&self) -> Option<BodyPtr<D>> {
600 return inline::get_next(self);
601 }
602
603 pub fn get_user_data(&self) -> Option<D::Body> {
605 return inline::get_user_data(self);
606 }
607
608 pub fn set_user_data(&mut self, data: &D::Body) {
610 inline::set_user_data(self, data);
611 }
612
613 pub fn get_world(&self) -> B2worldPtr<D> {
615 return inline::get_world(self);
616 }
617
618 pub(crate) fn new(bd: &B2bodyDef<D>, world: B2worldPtr<D>) -> Self {
621 return private::b2_body(bd, world);
622 }
623
624 pub(crate) fn synchronize_fixtures(&mut self) {
625 private::synchronize_fixtures(self);
626 }
627 pub(crate) fn synchronize_fixtures_by_world(&mut self, world: &B2world<D>) {
628 private::synchronize_fixtures_by_world(self, world);
629 }
630 pub(crate) fn synchronize_transform(&mut self) {
631 inline::synchronize_transform(self);
632 }
633
634 pub(crate) fn should_collide(&self, other: BodyPtr<D>) -> bool {
637 return private::should_collide(self, other);
638 }
639
640 pub(crate) fn advance(&mut self, t: f32) {
641 inline::advance(self, t);
642 }
643}
644
645mod inline {
646 use super::*;
647
648 pub fn get_type<D: UserDataType>(self_: &B2body<D>) -> B2bodyType {
649 return self_.m_type;
650 }
651
652 pub fn get_transform<D: UserDataType>(self_: &B2body<D>) -> B2Transform {
653 return self_.m_xf;
654 }
655
656 pub fn get_position<D: UserDataType>(self_: &B2body<D>) -> B2vec2 {
657 return self_.m_xf.p;
658 }
659
660 pub fn get_angle<D: UserDataType>(self_: &B2body<D>) -> f32 {
661 return self_.m_sweep.a;
662 }
663
664 pub fn get_world_center<D: UserDataType>(self_: &B2body<D>) -> B2vec2 {
665 return self_.m_sweep.c;
666 }
667
668 pub fn get_local_center<D: UserDataType>(self_: &B2body<D>) -> B2vec2 {
669 return self_.m_sweep.local_center;
670 }
671
672 pub fn set_linear_velocity<D: UserDataType>(self_: &mut B2body<D>, v: B2vec2) {
673 if self_.m_type == B2bodyType::B2StaticBody {
674 return;
675 }
676
677 if b2_dot(v, v) > 0.0 {
678 self_.set_awake(true);
679 }
680
681 self_.m_linear_velocity = v;
682 }
683
684 pub fn get_linear_velocity<D: UserDataType>(self_: &B2body<D>) -> B2vec2 {
685 return self_.m_linear_velocity;
686 }
687
688 pub fn set_angular_velocity<D: UserDataType>(self_: &mut B2body<D>, w: f32) {
689 if self_.m_type == B2bodyType::B2StaticBody {
690 return;
691 }
692
693 if w * w > 0.0 {
694 self_.set_awake(true);
695 }
696
697 self_.m_angular_velocity = w;
698 }
699
700 pub fn get_angular_velocity<D: UserDataType>(self_: &B2body<D>) -> f32 {
701 return self_.m_angular_velocity;
702 }
703
704 pub fn get_mass<D: UserDataType>(self_: &B2body<D>) -> f32 {
705 return self_.m_mass;
706 }
707
708 pub fn get_inertia<D: UserDataType>(self_: &B2body<D>) -> f32 {
709 return self_.m_i
710 + self_.m_mass * b2_dot(self_.m_sweep.local_center, self_.m_sweep.local_center);
711 }
712
713 pub fn get_mass_data<D: UserDataType>(self_: &B2body<D>, data: &mut B2massData) {
714 data.mass = self_.m_mass;
715 data.i =
716 self_.m_i + self_.m_mass * b2_dot(self_.m_sweep.local_center, self_.m_sweep.local_center);
717 data.center = self_.m_sweep.local_center;
718 }
719
720 pub fn get_world_point<D: UserDataType>(self_: &B2body<D>, local_point: B2vec2) -> B2vec2 {
721 return b2_mul_transform_by_vec2(self_.m_xf, local_point);
722 }
723
724 pub fn get_world_vector<D: UserDataType>(self_: &B2body<D>, local_vector: B2vec2) -> B2vec2 {
725 return b2_mul_rot_by_vec2(self_.m_xf.q, local_vector);
726 }
727
728 pub fn get_local_point<D: UserDataType>(self_: &B2body<D>, world_point: B2vec2) -> B2vec2 {
729 return b2_mul_t_transform_by_vec2(self_.m_xf, world_point);
730 }
731
732 pub fn get_local_vector<D: UserDataType>(self_: &B2body<D>, world_vector: B2vec2) -> B2vec2 {
733 return b2_mul_t_rot_by_vec2(self_.m_xf.q, world_vector);
734 }
735
736 pub fn get_linear_velocity_from_world_point<D: UserDataType>(
737 self_: &B2body<D>,
738 world_point: B2vec2,
739 ) -> B2vec2 {
740 return self_.m_linear_velocity
741 + b2_cross_scalar_by_vec(self_.m_angular_velocity, world_point - self_.m_sweep.c);
742 }
743
744 pub fn get_linear_velocity_from_local_point<D: UserDataType>(
745 self_: &B2body<D>,
746 local_point: B2vec2,
747 ) -> B2vec2 {
748 return self_.get_linear_velocity_from_world_point(self_.get_world_point(local_point));
749 }
750
751 pub fn get_linear_damping<D: UserDataType>(self_: &B2body<D>) -> f32 {
752 return self_.m_linear_damping;
753 }
754
755 pub fn set_linear_damping<D: UserDataType>(self_: &mut B2body<D>, linear_damping: f32) {
756 self_.m_linear_damping = linear_damping;
757 }
758
759 pub fn get_angular_damping<D: UserDataType>(self_: &B2body<D>) -> f32 {
760 return self_.m_angular_damping;
761 }
762
763 pub fn set_angular_damping<D: UserDataType>(self_: &mut B2body<D>, angular_damping: f32) {
764 self_.m_angular_damping = angular_damping;
765 }
766
767 pub fn get_gravity_scale<D: UserDataType>(self_: &B2body<D>) -> f32 {
768 return self_.m_gravity_scale;
769 }
770
771 pub fn set_gravity_scale<D: UserDataType>(self_: &mut B2body<D>, scale: f32) {
772 self_.m_gravity_scale = scale;
773 }
774
775 pub fn set_bullet<D: UserDataType>(self_: &mut B2body<D>, flag: bool) {
776 self_.m_flags.set(BodyFlags::E_BULLET_FLAG, flag);
777 }
778
779 pub fn is_bullet<D: UserDataType>(self_: &B2body<D>) -> bool {
780 return self_.m_flags.contains(BodyFlags::E_BULLET_FLAG);
781 }
782
783 pub fn set_awake<D: UserDataType>(self_: &mut B2body<D>, flag: bool) {
784
785 if self_.m_type == B2bodyType::B2StaticBody
786 {
787 return;
788
789 }
790
791 self_.m_flags.set(BodyFlags::E_AWAKE_FLAG, flag);
792 if flag {
793 self_.m_sleep_time = 0.0;
794 } else {
795 self_.m_sleep_time = 0.0;
796 self_.m_linear_velocity.set_zero();
797 self_.m_angular_velocity = 0.0;
798 self_.m_force.set_zero();
799 self_.m_torque = 0.0;
800 }
801 }
802
803 pub fn is_awake<D: UserDataType>(self_: &B2body<D>) -> bool {
804 return self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG);
805 }
806
807 pub fn is_enabled<D: UserDataType>(self_: &B2body<D>) -> bool {
808 return self_.m_flags.contains(BodyFlags::E_ENABLED_FLAG);
809 }
810
811 pub fn is_fixed_rotation<D: UserDataType>(self_: &B2body<D>) -> bool {
812 return self_.m_flags.contains(BodyFlags::E_FIXED_ROTATION_FLAG);
813 }
814
815 pub fn set_sleeping_allowed<D: UserDataType>(self_: &mut B2body<D>, flag: bool) {
816 self_.m_flags.set(BodyFlags::E_AUTO_SLEEP_FLAG, flag);
817 if flag {
818 } else {
819 self_.set_awake(true);
820 }
821 }
822
823 pub fn is_sleeping_allowed<D: UserDataType>(self_: &B2body<D>) -> bool {
824 return self_.m_flags.contains(BodyFlags::E_AUTO_SLEEP_FLAG);
825 }
826
827 pub fn get_fixture_list<D: UserDataType>(self_: &B2body<D>) -> &LinkedList<B2fixture<D>> {
834 return &self_.m_fixture_list;
835 }
836
837 pub fn get_joint_list_mut<D: UserDataType>(
838 self_: &mut B2body<D>,
839 ) -> &mut DoubleLinkedList<B2jointEdge<D>> {
840 return &mut self_.m_joint_list;
841 }
842
843 pub fn get_joint_list<D: UserDataType>(self_: &B2body<D>) -> &DoubleLinkedList<B2jointEdge<D>> {
844 return &self_.m_joint_list;
845 }
846
847 pub fn get_contact_list<D: UserDataType>(self_: &B2body<D>) -> &DoubleLinkedList<B2contactEdge<D>> {
854 return &self_.m_contact_list;
855 }
856
857 pub fn get_next<D: UserDataType>(self_: &B2body<D>) -> Option<BodyPtr<D>> {
858 return self_.m_next.clone();
859 }
860
861 pub fn set_user_data<D: UserDataType>(self_: &mut B2body<D>, data: &D::Body) {
862 self_.m_user_data = Some(data.clone());
863 }
864
865 pub fn get_user_data<D: UserDataType>(self_: &B2body<D>) -> Option<D::Body> {
866 return self_.m_user_data.clone();
867 }
868
869 pub fn apply_force<D: UserDataType>(
870 self_: &mut B2body<D>,
871 force: B2vec2,
872 point: B2vec2,
873 wake: bool,
874 ) {
875 if self_.m_type != B2bodyType::B2DynamicBody {
876 return;
877 }
878
879 if wake && !self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
880 self_.set_awake(true);
881 }
882
883 if self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
885 self_.m_force += force;
886 self_.m_torque += b2_cross(point - self_.m_sweep.c, force);
887 }
888 }
889
890 pub fn apply_force_to_center<D: UserDataType>(self_: &mut B2body<D>, force: B2vec2, wake: bool) {
891 if self_.m_type != B2bodyType::B2DynamicBody {
892 return;
893 }
894
895 if wake && !self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
896 self_.set_awake(true);
897 }
898
899 if self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
901 self_.m_force += force;
902 }
903 }
904
905 pub fn apply_torque<D: UserDataType>(self_: &mut B2body<D>, torque: f32, wake: bool) {
906 if self_.m_type != B2bodyType::B2DynamicBody {
907 return;
908 }
909
910 if wake && !self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
911 self_.set_awake(true);
912 }
913
914 if self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
916 self_.m_torque += torque;
917 }
918 }
919
920 pub fn apply_linear_impulse<D: UserDataType>(
921 self_: &mut B2body<D>,
922 impulse: B2vec2,
923 point: B2vec2,
924 wake: bool,
925 ) {
926 if self_.m_type != B2bodyType::B2DynamicBody {
927 return;
928 }
929
930 if wake && !self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
931 self_.set_awake(true);
932 }
933
934 if self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
936 self_.m_linear_velocity += self_.m_inv_mass * impulse;
937 self_.m_angular_velocity += self_.m_inv_i * b2_cross(point - self_.m_sweep.c, impulse);
938 }
939 }
940
941 pub fn apply_linear_impulse_to_center<D: UserDataType>(
942 self_: &mut B2body<D>,
943 impulse: B2vec2,
944 wake: bool,
945 ) {
946 if self_.m_type != B2bodyType::B2DynamicBody {
947 return;
948 }
949 if wake && !self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
950 self_.set_awake(true);
951 }
952
953 if self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
955 self_.m_linear_velocity += self_.m_inv_mass * impulse;
956 }
957 }
958
959 pub fn apply_angular_impulse<D: UserDataType>(self_: &mut B2body<D>, impulse: f32, wake: bool) {
960 if self_.m_type != B2bodyType::B2DynamicBody {
961 return;
962 }
963
964 if wake && !self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
965 self_.set_awake(true);
966 }
967
968 if self_.m_flags.contains(BodyFlags::E_AWAKE_FLAG) {
970 self_.m_angular_velocity += self_.m_inv_i * impulse;
971 }
972 }
973
974 pub fn synchronize_transform<D: UserDataType>(self_: &mut B2body<D>) {
975 self_.m_xf.q.set(self_.m_sweep.a);
976 self_.m_xf.p = self_.m_sweep.c - b2_mul_rot_by_vec2(self_.m_xf.q, self_.m_sweep.local_center);
977 }
978
979 pub fn advance<D: UserDataType>(self_: &mut B2body<D>, alpha: f32) {
980 self_.m_sweep.advance(alpha);
982 self_.m_sweep.c = self_.m_sweep.c0;
983 self_.m_sweep.a = self_.m_sweep.a0;
984 self_.m_xf.q.set(self_.m_sweep.a);
985 self_.m_xf.p = self_.m_sweep.c - b2_mul_rot_by_vec2(self_.m_xf.q, self_.m_sweep.local_center);
986 }
987
988 pub fn get_world<D: UserDataType>(self_: &B2body<D>) -> B2worldPtr<D> {
989 return self_.m_world.upgrade().unwrap();
990 }
991}