30 btVector3 inertia(0, 0, 0);
33 btRigidBody::btRigidBodyConstructionInfo ci(mass, &_motion, _shape, inertia);
36 if (bullet_additional_damping) {
37 ci.m_additionalDamping =
true;
38 ci.m_additionalDampingFactor = bullet_additional_damping_linear_factor;
39 ci.m_additionalLinearDampingThresholdSqr = bullet_additional_damping_linear_threshold;
40 ci.m_additionalAngularDampingFactor = bullet_additional_damping_angular_factor;
41 ci.m_additionalAngularDampingThresholdSqr = bullet_additional_damping_angular_threshold;
45 _rigid =
new btRigidBody(ci);
46 _rigid->setUserPointer(
this);
59 _motion = copy._motion;
60 _rigid =
new btRigidBody(*copy._rigid);
61 _rigid->setUserPointer(
this);
62 _rigid->setCollisionShape(_shape);
63 _rigid->setMotionState(&_motion);
74 return new BulletRigidBodyNode(*
this);
80void BulletRigidBodyNode::
81output(std::ostream &out)
const {
84 BulletBodyNode::do_output(out);
86 out <<
" mass=" << do_get_mass();
92btCollisionObject *BulletRigidBodyNode::
103void BulletRigidBodyNode::
106 do_set_mass(do_get_mass());
107 do_transform_changed();
117void BulletRigidBodyNode::
118do_set_mass(PN_stdfloat mass) {
120 btScalar bt_mass = mass;
121 btVector3 bt_inertia(0.0, 0.0, 0.0);
123 if (bt_mass > 0.0 && !_shapes.empty()) {
124 _rigid->getCollisionShape()->calculateLocalInertia(bt_mass, bt_inertia);
127 _rigid->setMassProps(bt_mass, bt_inertia);
128 _rigid->updateInertiaTensor();
139 LightMutexHolder holder(BulletWorld::get_global_lock());
149PN_stdfloat BulletRigidBodyNode::
152 btScalar inv_mass = _rigid->getInvMass();
153 btScalar mass = (inv_mass == btScalar(0.0)) ? btScalar(0.0) : btScalar(1.0) / inv_mass;
164 LightMutexHolder holder(BulletWorld::get_global_lock());
166 return do_get_mass();
175 LightMutexHolder holder(BulletWorld::get_global_lock());
177 return (PN_stdfloat)_rigid->getInvMass();
192 LightMutexHolder holder(BulletWorld::get_global_lock());
194 btVector3 inv_inertia(
195 inertia.get_x() == 0.0 ? btScalar(0.0) : btScalar(1.0 / inertia.get_x()),
196 inertia.get_y() == 0.0 ? btScalar(0.0) : btScalar(1.0 / inertia.get_y()),
197 inertia.get_z() == 0.0 ? btScalar(0.0) : btScalar(1.0 / inertia.get_z())
200 _rigid->setInvInertiaDiagLocal(inv_inertia);
201 _rigid->updateInertiaTensor();
211 LightMutexHolder holder(BulletWorld::get_global_lock());
213 btVector3 inv_inertia = _rigid->getInvInertiaDiagLocal();
215 inv_inertia.x() == btScalar(0.0) ? 0.0 : 1.0 / inv_inertia.x(),
216 inv_inertia.y() == btScalar(0.0) ? 0.0 : 1.0 / inv_inertia.y(),
217 inv_inertia.z() == btScalar(0.0) ? 0.0 : 1.0 / inv_inertia.z()
226LVector3 BulletRigidBodyNode::
227get_inv_inertia_diag_local()
const {
228 LightMutexHolder holder(BulletWorld::get_global_lock());
230 return btVector3_to_LVector3(_rigid->getInvInertiaDiagLocal());
236LMatrix3 BulletRigidBodyNode::
237get_inv_inertia_tensor_world()
const {
238 LightMutexHolder holder(BulletWorld::get_global_lock());
240 return btMatrix3x3_to_LMatrix3(_rigid->getInvInertiaTensorWorld());
246void BulletRigidBodyNode::
247apply_force(
const LVector3 &force,
const LPoint3 &pos) {
248 LightMutexHolder holder(BulletWorld::get_global_lock());
250 nassertv_always(!force.is_nan());
251 nassertv_always(!pos.is_nan());
253 _rigid->applyForce(LVecBase3_to_btVector3(force),
254 LVecBase3_to_btVector3(pos));
260void BulletRigidBodyNode::
261apply_central_force(
const LVector3 &force) {
262 LightMutexHolder holder(BulletWorld::get_global_lock());
264 nassertv_always(!force.is_nan());
266 _rigid->applyCentralForce(LVecBase3_to_btVector3(force));
272void BulletRigidBodyNode::
273apply_torque(
const LVector3 &torque) {
274 LightMutexHolder holder(BulletWorld::get_global_lock());
276 nassertv_always(!torque.is_nan());
278 _rigid->applyTorque(LVecBase3_to_btVector3(torque));
284void BulletRigidBodyNode::
285apply_torque_impulse(
const LVector3 &torque) {
286 LightMutexHolder holder(BulletWorld::get_global_lock());
288 nassertv_always(!torque.is_nan());
290 _rigid->applyTorqueImpulse(LVecBase3_to_btVector3(torque));
296void BulletRigidBodyNode::
297apply_impulse(
const LVector3 &impulse,
const LPoint3 &pos) {
298 LightMutexHolder holder(BulletWorld::get_global_lock());
300 nassertv_always(!impulse.is_nan());
301 nassertv_always(!pos.is_nan());
303 _rigid->applyImpulse(LVecBase3_to_btVector3(impulse),
304 LVecBase3_to_btVector3(pos));
310void BulletRigidBodyNode::
311apply_central_impulse(
const LVector3 &impulse) {
312 LightMutexHolder holder(BulletWorld::get_global_lock());
314 nassertv_always(!impulse.is_nan());
316 _rigid->applyCentralImpulse(LVecBase3_to_btVector3(impulse));
322void BulletRigidBodyNode::
323do_transform_changed() {
325 if (_motion.sync_disabled())
return;
335 _motion.set_net_transform(ts);
338 if (!(get_object()->isKinematicObject())) {
339 btTransform trans = TransformState_to_btTrans(ts);
340 _rigid->setCenterOfMassTransform(trans);
345 if (ts->has_scale()) {
346 btVector3 new_scale = LVecBase3_to_btVector3(ts->get_scale());
347 btVector3 current_scale = _shape->getLocalScaling();
348 btVector3 current_scale_inv(1.0/current_scale.x(), 1.0/current_scale.y(), 1.0/current_scale.z());
350 if (new_scale != current_scale) {
351 _shape->setLocalScaling(current_scale_inv);
352 _shape->setLocalScaling(new_scale);
357 if (!_rigid->isActive()) {
358 _rigid->activate(
true);
365void BulletRigidBodyNode::
368 if (_motion.sync_disabled())
return;
371 LightMutexHolder holder(BulletWorld::get_global_lock());
372 do_transform_changed();
379void BulletRigidBodyNode::
382 if (_motion.sync_disabled())
return;
384 LightMutexHolder holder(BulletWorld::get_global_lock());
386 do_transform_changed();
395 if (get_object()->isKinematicObject()) {
396 do_transform_changed();
406 _motion.sync_b2p((PandaNode *)
this);
412LVector3 BulletRigidBodyNode::
413get_linear_velocity()
const {
416 return btVector3_to_LVector3(_rigid->getLinearVelocity());
422LVector3 BulletRigidBodyNode::
423get_angular_velocity()
const {
424 LightMutexHolder holder(BulletWorld::get_global_lock());
426 return btVector3_to_LVector3(_rigid->getAngularVelocity());
432void BulletRigidBodyNode::
433set_linear_velocity(
const LVector3 &velocity) {
434 LightMutexHolder holder(BulletWorld::get_global_lock());
436 nassertv_always(!velocity.is_nan());
438 _rigid->setLinearVelocity(LVecBase3_to_btVector3(velocity));
444void BulletRigidBodyNode::
445set_angular_velocity(
const LVector3 &velocity) {
446 LightMutexHolder holder(BulletWorld::get_global_lock());
448 nassertv_always(!velocity.is_nan());
450 _rigid->setAngularVelocity(LVecBase3_to_btVector3(velocity));
456void BulletRigidBodyNode::
457set_linear_damping(PN_stdfloat value) {
458 LightMutexHolder holder(BulletWorld::get_global_lock());
460 _rigid->setDamping(value, _rigid->getAngularDamping());
466void BulletRigidBodyNode::
467set_angular_damping(PN_stdfloat value) {
468 LightMutexHolder holder(BulletWorld::get_global_lock());
470 _rigid->setDamping(_rigid->getLinearDamping(), value);
476PN_stdfloat BulletRigidBodyNode::
477get_linear_damping()
const {
478 LightMutexHolder holder(BulletWorld::get_global_lock());
480 return (PN_stdfloat)_rigid->getLinearDamping();
486PN_stdfloat BulletRigidBodyNode::
487get_angular_damping()
const {
488 LightMutexHolder holder(BulletWorld::get_global_lock());
490 return (PN_stdfloat)_rigid->getAngularDamping();
496void BulletRigidBodyNode::
498 LightMutexHolder holder(BulletWorld::get_global_lock());
500 _rigid->clearForces();
506PN_stdfloat BulletRigidBodyNode::
507get_linear_sleep_threshold()
const {
508 LightMutexHolder holder(BulletWorld::get_global_lock());
510 return _rigid->getLinearSleepingThreshold();
516PN_stdfloat BulletRigidBodyNode::
517get_angular_sleep_threshold()
const {
518 LightMutexHolder holder(BulletWorld::get_global_lock());
520 return _rigid->getAngularSleepingThreshold();
526void BulletRigidBodyNode::
527set_linear_sleep_threshold(PN_stdfloat threshold) {
528 LightMutexHolder holder(BulletWorld::get_global_lock());
530 _rigid->setSleepingThresholds(threshold, _rigid->getAngularSleepingThreshold());
536void BulletRigidBodyNode::
537set_angular_sleep_threshold(PN_stdfloat threshold) {
538 LightMutexHolder holder(BulletWorld::get_global_lock());
540 _rigid->setSleepingThresholds(_rigid->getLinearSleepingThreshold(), threshold);
546void BulletRigidBodyNode::
547set_gravity(
const LVector3 &gravity) {
548 LightMutexHolder holder(BulletWorld::get_global_lock());
550 nassertv_always(!gravity.is_nan());
552 _rigid->setGravity(LVecBase3_to_btVector3(gravity));
558LVector3 BulletRigidBodyNode::
560 LightMutexHolder holder(BulletWorld::get_global_lock());
562 return btVector3_to_LVector3(_rigid->getGravity());
568LVector3 BulletRigidBodyNode::
569get_linear_factor()
const {
570 LightMutexHolder holder(BulletWorld::get_global_lock());
572 return btVector3_to_LVector3(_rigid->getLinearFactor());
578LVector3 BulletRigidBodyNode::
579get_angular_factor()
const {
580 LightMutexHolder holder(BulletWorld::get_global_lock());
582 return btVector3_to_LVector3(_rigid->getAngularFactor());
588void BulletRigidBodyNode::
589set_linear_factor(
const LVector3 &factor) {
590 LightMutexHolder holder(BulletWorld::get_global_lock());
592 _rigid->setLinearFactor(LVecBase3_to_btVector3(factor));
598void BulletRigidBodyNode::
599set_angular_factor(
const LVector3 &factor) {
600 LightMutexHolder holder(BulletWorld::get_global_lock());
602 _rigid->setAngularFactor(LVecBase3_to_btVector3(factor));
608LVector3 BulletRigidBodyNode::
609get_total_force()
const {
610 LightMutexHolder holder(BulletWorld::get_global_lock());
612 return btVector3_to_LVector3(_rigid->getTotalForce());
618LVector3 BulletRigidBodyNode::
619get_total_torque()
const {
620 LightMutexHolder holder(BulletWorld::get_global_lock());
622 return btVector3_to_LVector3(_rigid->getTotalTorque());
628BulletRigidBodyNode::MotionState::
631 _trans.setIdentity();
640void BulletRigidBodyNode::MotionState::
641getWorldTransform(btTransform &trans)
const {
649void BulletRigidBodyNode::MotionState::
650setWorldTransform(
const btTransform &trans) {
660void BulletRigidBodyNode::MotionState::
661sync_b2p(PandaNode *node) {
666 LPoint3 p = btVector3_to_LPoint3(_trans.getOrigin());
667 LQuaternion q = btQuat_to_LQuaternion(_trans.getRotation());
683void BulletRigidBodyNode::MotionState::
688 _trans = TransformState_to_btTrans(ts);
694bool BulletRigidBodyNode::MotionState::
695sync_disabled()
const {
703bool BulletRigidBodyNode::MotionState::
706 bool rc = _was_dirty;
718 return _motion.pick_dirty_flag();
742 get_gravity().write_datagram(dg);
743 get_linear_factor().write_datagram(dg);
744 get_angular_factor().write_datagram(dg);
746 get_linear_velocity().write_datagram(dg);
747 get_angular_velocity().write_datagram(dg);
762 param->fillin(scan, manager);
771void BulletRigidBodyNode::
772fillin(DatagramIterator &scan, BamReader *manager) {
773 BulletBodyNode::fillin(scan, manager);
781 LVector3 gravity, linear_factor, angular_factor;
782 gravity.read_datagram(scan);
783 linear_factor.read_datagram(scan);
784 angular_factor.read_datagram(scan);
786 set_gravity(gravity);
787 set_linear_factor(linear_factor);
788 set_angular_factor(angular_factor);
void parse_params(const FactoryParams ¶ms, DatagramIterator &scan, BamReader *&manager)
Takes in a FactoryParams, passed from a WritableFactory into any TypedWritable's make function,...
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
This is the fundamental interface for extracting binary objects from a Bam file, as generated by a Ba...
static WritableFactory * get_factory()
Returns the global WritableFactory for generating TypedWritable objects.
This is the fundamental interface for writing binary objects to a Bam file, to be extracted later by ...
virtual void write_datagram(BamWriter *manager, Datagram &dg)
Writes the contents of this object to the datagram for shipping out to a Bam file.
virtual PandaNode * make_copy() const
Returns a newly-allocated PandaNode that is a shallow copy of this one.
virtual void write_datagram(BamWriter *manager, Datagram &dg)
Writes the contents of this object to the datagram for shipping out to a Bam file.
set_mass
Sets the mass of a rigid body.
static void register_with_read_factory()
Tells the BamReader how to create objects of type BulletRigidBodyNode.
get_mass
Returns the total mass of a rigid body.
void do_sync_b2p()
Assumes the lock(bullet global lock) is held by the caller.
bool pick_dirty_flag()
Returns TRUE if the transform of the rigid body has changed at least once since the last call to this...
get_inv_mass
Returns the inverse mass of a rigid body.
set_inertia
Sets the inertia of a rigid body.
get_inertia
Returns the inertia of the rigid body.
void do_sync_p2b()
Assumes the lock(bullet global lock) is held by the caller.
A class to retrieve the individual data elements previously stored in a Datagram.
PN_stdfloat get_stdfloat()
Extracts either a 32-bit or a 64-bit floating-point number, according to Datagram::set_stdfloat_doubl...
An ordered list of data elements, formatted in memory for transmission over a socket or writing to a ...
void add_stdfloat(PN_stdfloat value)
Adds either a 32-bit or a 64-bit floating-point number, according to set_stdfloat_double().
An instance of this class is passed to the Factory when requesting it to do its business and construc...
void register_factory(TypeHandle handle, CreateFunc *func, void *user_data=nullptr)
Registers a new kind of thing the Factory will be able to create.
Similar to MutexHolder, but for a light mutex.
static NodePath any_path(PandaNode *node, Thread *current_thread=Thread::get_current_thread())
Returns a new NodePath that represents any arbitrary path from the root to the indicated node.
void set_pos_quat(const LVecBase3 &pos, const LQuaternion &quat)
Sets the translation and rotation component of the transform, leaving scale untouched.
get_num_parents
Returns the number of parent nodes this node has.
TypeHandle is the identifier used to differentiate C++ class types.
Base class for objects that can be written to and read from Bam files.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.