Blender  V3.3
rb_bullet_api.cpp
Go to the documentation of this file.
1 /* SPDX-License-Identifier: GPL-2.0-or-later
2  * Copyright 2013 Blender Foundation. All rights reserved. */
3 
9 /*
10  * Bullet Continuous Collision Detection and Physics Library
11  * Copyright (c) 2003-2006 Erwin Coumans http://continuousphysics.com/Bullet/
12  *
13  * This software is provided 'as-is', without any express or implied warranty. In no event will the
14  * authors be held liable for any damages arising from the use of this software. Permission is
15  * granted to anyone to use this software for any purpose, including commercial applications, and
16  * to alter it and redistribute it freely, subject to the following restrictions:
17  *
18  * 1. The origin of this software must not be misrepresented; you must not claim that you wrote the
19  * original software. If you use this software in a product, an acknowledgment in the product
20  * documentation would be appreciated but is not required.
21  * 2. Altered source versions must be plainly marked as such, and must not be misrepresented as
22  * being the original software.
23  * 3. This notice may not be removed or altered from any source distribution.
24  */
25 
26 /* This file defines the "RigidBody interface" for the
27  * Bullet Physics Engine. This API is designed to be used
28  * from C-code in Blender as part of the Rigid Body simulation
29  * system.
30  *
31  * It is based on the Bullet C-API, but is heavily modified to
32  * give access to more data types and to offer a nicer interface.
33  *
34  * -- Joshua Leung, June 2010
35  */
36 
37 #include <errno.h>
38 #include <stdio.h>
39 
40 #include "RBI_api.h"
41 
42 #include "btBulletDynamicsCommon.h"
43 
45 #include "LinearMath/btMatrix3x3.h"
46 #include "LinearMath/btScalar.h"
47 #include "LinearMath/btTransform.h"
48 #include "LinearMath/btVector3.h"
49 
53 
61 };
62 struct rbRigidBody {
65 };
66 
67 struct rbVert {
69 };
70 struct rbTri {
71  int v0, v1, v2;
72 };
73 
74 struct rbMeshData {
80 };
81 
87 };
88 
90  virtual bool needBroadphaseCollision(btBroadphaseProxy *proxy0, btBroadphaseProxy *proxy1) const
91  {
92  rbRigidBody *rb0 = (rbRigidBody *)((btRigidBody *)proxy0->m_clientObject)->getUserPointer();
93  rbRigidBody *rb1 = (rbRigidBody *)((btRigidBody *)proxy1->m_clientObject)->getUserPointer();
94 
95  bool collides;
96  collides = (proxy0->m_collisionFilterGroup & proxy1->m_collisionFilterMask) != 0;
97  collides = collides && (proxy1->m_collisionFilterGroup & proxy0->m_collisionFilterMask);
98  collides = collides && (rb0->col_groups & rb1->col_groups);
99 
100  return collides;
101  }
102 };
103 
104 static inline void copy_v3_btvec3(float vec[3], const btVector3 &btvec)
105 {
106  vec[0] = (float)btvec[0];
107  vec[1] = (float)btvec[1];
108  vec[2] = (float)btvec[2];
109 }
110 static inline void copy_quat_btquat(float quat[4], const btQuaternion &btquat)
111 {
112  quat[0] = btquat.getW();
113  quat[1] = btquat.getX();
114  quat[2] = btquat.getY();
115  quat[3] = btquat.getZ();
116 }
117 
118 /* ********************************** */
119 /* Dynamics World Methods */
120 
121 /* Setup ---------------------------- */
122 
123 rbDynamicsWorld *RB_dworld_new(const float gravity[3])
124 {
126 
127  /* collision detection/handling */
128  world->collisionConfiguration = new btDefaultCollisionConfiguration();
129 
130  world->dispatcher = new btCollisionDispatcher(world->collisionConfiguration);
132 
133  world->pairCache = new btDbvtBroadphase();
134 
135  world->filterCallback = new rbFilterCallback();
136  world->pairCache->getOverlappingPairCache()->setOverlapFilterCallback(world->filterCallback);
137 
138  /* constraint solving */
139  world->constraintSolver = new btSequentialImpulseConstraintSolver();
140 
141  /* world */
142  world->dynamicsWorld = new btDiscreteDynamicsWorld(
143  world->dispatcher, world->pairCache, world->constraintSolver, world->collisionConfiguration);
144 
145  RB_dworld_set_gravity(world, gravity);
146 
147  return world;
148 }
149 
151 {
152  /* bullet doesn't like if we free these in a different order */
153  delete world->dynamicsWorld;
154  delete world->constraintSolver;
155  delete world->pairCache;
156  delete world->dispatcher;
157  delete world->collisionConfiguration;
158  delete world->filterCallback;
159  delete world;
160 }
161 
162 /* Settings ------------------------- */
163 
164 /* Gravity */
166 {
167  copy_v3_btvec3(g_out, world->dynamicsWorld->getGravity());
168 }
169 
170 void RB_dworld_set_gravity(rbDynamicsWorld *world, const float g_in[3])
171 {
172  world->dynamicsWorld->setGravity(btVector3(g_in[0], g_in[1], g_in[2]));
173 }
174 
175 /* Constraint Solver */
176 void RB_dworld_set_solver_iterations(rbDynamicsWorld *world, int num_solver_iterations)
177 {
178  btContactSolverInfo &info = world->dynamicsWorld->getSolverInfo();
179 
180  info.m_numIterations = num_solver_iterations;
181 }
182 
183 /* Split Impulse */
185 {
186  btContactSolverInfo &info = world->dynamicsWorld->getSolverInfo();
187 
188  info.m_splitImpulse = split_impulse;
189 }
190 
191 /* Simulation ----------------------- */
192 
194  float timeStep,
195  int maxSubSteps,
196  float timeSubStep)
197 {
198  world->dynamicsWorld->stepSimulation(timeStep, maxSubSteps, timeSubStep);
199 }
200 
201 /* Export -------------------------- */
202 
210 void RB_dworld_export(rbDynamicsWorld *world, const char *filename)
211 {
212  // create a large enough buffer. There is no method to pre-calculate the buffer size yet.
213  int maxSerializeBufferSize = 1024 * 1024 * 5;
214 
215  btDefaultSerializer *serializer = new btDefaultSerializer(maxSerializeBufferSize);
216  world->dynamicsWorld->serialize(serializer);
217 
218  FILE *file = fopen(filename, "wb");
219  if (file) {
220  fwrite(serializer->getBufferPointer(), serializer->getCurrentBufferSize(), 1, file);
221  fclose(file);
222  }
223  else {
224  fprintf(stderr, "RB_dworld_export: %s\n", strerror(errno));
225  }
226 }
227 
228 /* ********************************** */
229 /* Rigid Body Methods */
230 
231 /* Setup ---------------------------- */
232 
233 void RB_dworld_add_body(rbDynamicsWorld *world, rbRigidBody *object, int col_groups)
234 {
235  btRigidBody *body = object->body;
236  object->col_groups = col_groups;
237 
238  world->dynamicsWorld->addRigidBody(body);
239 }
240 
242 {
243  btRigidBody *body = object->body;
244 
245  world->dynamicsWorld->removeRigidBody(body);
246 }
247 
248 /* Collision detection */
249 
251  rbRigidBody *object,
252  const float loc_start[3],
253  const float loc_end[3],
254  float v_location[3],
255  float v_hitpoint[3],
256  float v_normal[3],
257  int *r_hit)
258 {
259  btRigidBody *body = object->body;
260  btCollisionShape *collisionShape = body->getCollisionShape();
261  /* only convex shapes are supported, but user can specify a non convex shape */
262  if (collisionShape->isConvex()) {
264  btVector3(loc_start[0], loc_start[1], loc_start[2]),
265  btVector3(loc_end[0], loc_end[1], loc_end[2]));
266 
267  btQuaternion obRot = body->getWorldTransform().getRotation();
268 
269  btTransform rayFromTrans;
270  rayFromTrans.setIdentity();
271  rayFromTrans.setRotation(obRot);
272  rayFromTrans.setOrigin(btVector3(loc_start[0], loc_start[1], loc_start[2]));
273 
274  btTransform rayToTrans;
275  rayToTrans.setIdentity();
276  rayToTrans.setRotation(obRot);
277  rayToTrans.setOrigin(btVector3(loc_end[0], loc_end[1], loc_end[2]));
278 
279  world->dynamicsWorld->convexSweepTest(
280  (btConvexShape *)collisionShape, rayFromTrans, rayToTrans, result, 0);
281 
282  if (result.hasHit()) {
283  *r_hit = 1;
284 
285  v_location[0] = result.m_convexFromWorld[0] +
286  (result.m_convexToWorld[0] - result.m_convexFromWorld[0]) *
287  result.m_closestHitFraction;
288  v_location[1] = result.m_convexFromWorld[1] +
289  (result.m_convexToWorld[1] - result.m_convexFromWorld[1]) *
290  result.m_closestHitFraction;
291  v_location[2] = result.m_convexFromWorld[2] +
292  (result.m_convexToWorld[2] - result.m_convexFromWorld[2]) *
293  result.m_closestHitFraction;
294 
295  v_hitpoint[0] = result.m_hitPointWorld[0];
296  v_hitpoint[1] = result.m_hitPointWorld[1];
297  v_hitpoint[2] = result.m_hitPointWorld[2];
298 
299  v_normal[0] = result.m_hitNormalWorld[0];
300  v_normal[1] = result.m_hitNormalWorld[1];
301  v_normal[2] = result.m_hitNormalWorld[2];
302  }
303  else {
304  *r_hit = 0;
305  }
306  }
307  else {
308  /* we need to return a value if user passes non convex body, to report */
309  *r_hit = -2;
310  }
311 }
312 
313 /* ............ */
314 
315 rbRigidBody *RB_body_new(rbCollisionShape *shape, const float loc[3], const float rot[4])
316 {
317  rbRigidBody *object = new rbRigidBody;
318  /* current transform */
319  btTransform trans;
320  trans.setIdentity();
321  trans.setOrigin(btVector3(loc[0], loc[1], loc[2]));
322  trans.setRotation(btQuaternion(rot[1], rot[2], rot[3], rot[0]));
323 
324  /* create motionstate, which is necessary for interpolation (includes reverse playback) */
325  btDefaultMotionState *motionState = new btDefaultMotionState(trans);
326 
327  /* make rigidbody */
328  btRigidBody::btRigidBodyConstructionInfo rbInfo(1.0f, motionState, shape->cshape);
329 
330  object->body = new btRigidBody(rbInfo);
331 
332  object->body->setUserPointer(object);
333 
334  return object;
335 }
336 
338 {
339  btRigidBody *body = object->body;
340 
341  /* motion state */
342  btMotionState *ms = body->getMotionState();
343 
344  delete ms;
345 
346  /* collision shape is done elsewhere... */
347 
348  /* body itself */
349 
350  /* manually remove constraint refs of the rigid body, normally this happens when removing
351  * constraints from the world
352  * but since we delete everything when the world is rebult, we need to do it manually here */
353  for (int i = body->getNumConstraintRefs() - 1; i >= 0; i--) {
354  btTypedConstraint *con = body->getConstraintRef(i);
355  body->removeConstraintRef(con);
356  }
357 
358  delete body;
359  delete object;
360 }
361 
362 /* Settings ------------------------- */
363 
365 {
366  btRigidBody *body = object->body;
367 
368  /* set new collision shape */
369  body->setCollisionShape(shape->cshape);
370 
371  /* recalculate inertia, since that depends on the collision shape... */
372  RB_body_set_mass(object, RB_body_get_mass(object));
373 }
374 
375 /* ............ */
376 
378 {
379  btRigidBody *body = object->body;
380 
381  /* there isn't really a mass setting, but rather 'inverse mass'
382  * which we convert back to mass by taking the reciprocal again
383  */
384  float value = (float)body->getInvMass();
385 
386  if (value) {
387  value = 1.0f / value;
388  }
389 
390  return value;
391 }
392 
393 void RB_body_set_mass(rbRigidBody *object, float value)
394 {
395  btRigidBody *body = object->body;
396  btVector3 localInertia(0, 0, 0);
397 
398  /* calculate new inertia if non-zero mass */
399  if (value) {
400  btCollisionShape *shape = body->getCollisionShape();
401  shape->calculateLocalInertia(value, localInertia);
402  }
403 
404  btVector3 minAabb, maxAabb;
405  btTransform ident;
406  ident.setIdentity();
407  body->getCollisionShape()->getAabb(ident, minAabb, maxAabb);
408  body->setMassProps(value, localInertia);
409  body->updateInertiaTensor();
410 }
411 
413 {
414  btRigidBody *body = object->body;
415  return body->getFriction();
416 }
417 
418 void RB_body_set_friction(rbRigidBody *object, float value)
419 {
420  btRigidBody *body = object->body;
421  body->setFriction(value);
422 }
423 
425 {
426  btRigidBody *body = object->body;
427  return body->getRestitution();
428 }
429 
430 void RB_body_set_restitution(rbRigidBody *object, float value)
431 {
432  btRigidBody *body = object->body;
433  body->setRestitution(value);
434 }
435 
437 {
438  btRigidBody *body = object->body;
439  return body->getLinearDamping();
440 }
441 
442 void RB_body_set_linear_damping(rbRigidBody *object, float value)
443 {
444  RB_body_set_damping(object, value, RB_body_get_linear_damping(object));
445 }
446 
448 {
449  btRigidBody *body = object->body;
450  return body->getAngularDamping();
451 }
452 
453 void RB_body_set_angular_damping(rbRigidBody *object, float value)
454 {
455  RB_body_set_damping(object, RB_body_get_linear_damping(object), value);
456 }
457 
458 void RB_body_set_damping(rbRigidBody *object, float linear, float angular)
459 {
460  btRigidBody *body = object->body;
461  body->setDamping(linear, angular);
462 }
463 
465 {
466  btRigidBody *body = object->body;
467  return body->getLinearSleepingThreshold();
468 }
469 
471 {
473 }
474 
476 {
477  btRigidBody *body = object->body;
478  return body->getAngularSleepingThreshold();
479 }
480 
482 {
484 }
485 
486 void RB_body_set_sleep_thresh(rbRigidBody *object, float linear, float angular)
487 {
488  btRigidBody *body = object->body;
489  body->setSleepingThresholds(linear, angular);
490 }
491 
492 /* ............ */
493 
494 void RB_body_get_linear_velocity(rbRigidBody *object, float v_out[3])
495 {
496  btRigidBody *body = object->body;
497 
498  copy_v3_btvec3(v_out, body->getLinearVelocity());
499 }
500 
501 void RB_body_set_linear_velocity(rbRigidBody *object, const float v_in[3])
502 {
503  btRigidBody *body = object->body;
504 
505  body->setLinearVelocity(btVector3(v_in[0], v_in[1], v_in[2]));
506 }
507 
508 void RB_body_get_angular_velocity(rbRigidBody *object, float v_out[3])
509 {
510  btRigidBody *body = object->body;
511 
512  copy_v3_btvec3(v_out, body->getAngularVelocity());
513 }
514 
515 void RB_body_set_angular_velocity(rbRigidBody *object, const float v_in[3])
516 {
517  btRigidBody *body = object->body;
518 
519  body->setAngularVelocity(btVector3(v_in[0], v_in[1], v_in[2]));
520 }
521 
522 void RB_body_set_linear_factor(rbRigidBody *object, float x, float y, float z)
523 {
524  btRigidBody *body = object->body;
525  body->setLinearFactor(btVector3(x, y, z));
526 }
527 
528 void RB_body_set_angular_factor(rbRigidBody *object, float x, float y, float z)
529 {
530  btRigidBody *body = object->body;
531  body->setAngularFactor(btVector3(x, y, z));
532 }
533 
534 /* ............ */
535 
536 void RB_body_set_kinematic_state(rbRigidBody *object, int kinematic)
537 {
538  btRigidBody *body = object->body;
539  if (kinematic) {
540  body->setCollisionFlags(body->getCollisionFlags() | btCollisionObject::CF_KINEMATIC_OBJECT);
541  }
542  else {
543  body->setCollisionFlags(body->getCollisionFlags() & ~btCollisionObject::CF_KINEMATIC_OBJECT);
544  }
545 }
546 
547 /* ............ */
548 
549 void RB_body_set_activation_state(rbRigidBody *object, int use_deactivation)
550 {
551  btRigidBody *body = object->body;
552  if (use_deactivation) {
553  body->forceActivationState(ACTIVE_TAG);
554  }
555  else {
556  body->setActivationState(DISABLE_DEACTIVATION);
557  }
558 }
560 {
561  btRigidBody *body = object->body;
562  body->setActivationState(ACTIVE_TAG);
563 }
565 {
566  btRigidBody *body = object->body;
567  body->setActivationState(ISLAND_SLEEPING);
568 }
569 
570 /* ............ */
571 
572 /* Simulation ----------------------- */
573 
574 /* The transform matrices Blender uses are OpenGL-style matrices,
575  * while Bullet uses the Right-Handed coordinate system style instead.
576  */
577 
578 void RB_body_get_transform_matrix(rbRigidBody *object, float m_out[4][4])
579 {
580  btRigidBody *body = object->body;
581  btMotionState *ms = body->getMotionState();
582 
583  btTransform trans;
584  ms->getWorldTransform(trans);
585 
586  trans.getOpenGLMatrix((btScalar *)m_out);
587 }
588 
589 void RB_body_set_loc_rot(rbRigidBody *object, const float loc[3], const float rot[4])
590 {
591  btRigidBody *body = object->body;
592  btMotionState *ms = body->getMotionState();
593 
594  /* set transform matrix */
595  btTransform trans;
596  trans.setIdentity();
597  trans.setOrigin(btVector3(loc[0], loc[1], loc[2]));
598  trans.setRotation(btQuaternion(rot[1], rot[2], rot[3], rot[0]));
599 
600  ms->setWorldTransform(trans);
601 }
602 
603 void RB_body_set_scale(rbRigidBody *object, const float scale[3])
604 {
605  btRigidBody *body = object->body;
606 
607  /* apply scaling factor from matrix above to the collision shape */
608  btCollisionShape *cshape = body->getCollisionShape();
609  if (cshape) {
610  cshape->setLocalScaling(btVector3(scale[0], scale[1], scale[2]));
611 
612  /* GIimpact shapes have to be updated to take scaling into account */
613  if (cshape->getShapeType() == GIMPACT_SHAPE_PROXYTYPE) {
614  ((btGImpactMeshShape *)cshape)->updateBound();
615  }
616  }
617 }
618 
619 /* ............ */
620 /* Read-only state info about status of simulation */
621 
622 void RB_body_get_position(rbRigidBody *object, float v_out[3])
623 {
624  btRigidBody *body = object->body;
625 
626  copy_v3_btvec3(v_out, body->getWorldTransform().getOrigin());
627 }
628 
629 void RB_body_get_orientation(rbRigidBody *object, float v_out[4])
630 {
631  btRigidBody *body = object->body;
632 
633  copy_quat_btquat(v_out, body->getWorldTransform().getRotation());
634 }
635 
636 void RB_body_get_scale(rbRigidBody *object, float v_out[3])
637 {
638  btRigidBody *body = object->body;
639 
640  btCollisionShape *cshape = body->getCollisionShape();
641  /* The body should have a collision shape when we try to set the scale. */
642  btAssert(cshape);
643  copy_v3_btvec3(v_out, cshape->getLocalScaling());
644 }
645 
646 /* ............ */
647 /* Overrides for simulation */
648 
649 void RB_body_apply_central_force(rbRigidBody *object, const float v_in[3])
650 {
651  btRigidBody *body = object->body;
652 
653  body->applyCentralForce(btVector3(v_in[0], v_in[1], v_in[2]));
654 }
655 
656 /* ********************************** */
657 /* Collision Shape Methods */
658 
659 /* Setup (Standard Shapes) ----------- */
660 
661 rbCollisionShape *RB_shape_new_box(float x, float y, float z)
662 {
663  rbCollisionShape *shape = new rbCollisionShape;
664  shape->cshape = new btBoxShape(btVector3(x, y, z));
665  shape->mesh = NULL;
666  shape->compoundChilds = 0;
667  shape->compoundChildShapes = NULL;
668  return shape;
669 }
670 
672 {
673  rbCollisionShape *shape = new rbCollisionShape;
674  shape->cshape = new btSphereShape(radius);
675  shape->mesh = NULL;
676  shape->compoundChilds = 0;
677  shape->compoundChildShapes = NULL;
678  return shape;
679 }
680 
682 {
683  rbCollisionShape *shape = new rbCollisionShape;
684  shape->cshape = new btCapsuleShapeZ(radius, height);
685  shape->mesh = NULL;
686  shape->compoundChilds = 0;
687  shape->compoundChildShapes = NULL;
688  return shape;
689 }
690 
692 {
693  rbCollisionShape *shape = new rbCollisionShape;
694  shape->cshape = new btConeShapeZ(radius, height);
695  shape->mesh = NULL;
696  shape->compoundChilds = 0;
697  shape->compoundChildShapes = NULL;
698  return shape;
699 }
700 
702 {
703  rbCollisionShape *shape = new rbCollisionShape;
704  shape->cshape = new btCylinderShapeZ(btVector3(radius, radius, height));
705  shape->mesh = NULL;
706  shape->compoundChilds = 0;
707  shape->compoundChildShapes = NULL;
708  return shape;
709 }
710 
711 /* Setup (Convex Hull) ------------ */
712 
714  float *verts, int stride, int count, float margin, bool *can_embed)
715 {
716  btConvexHullComputer hull_computer = btConvexHullComputer();
717 
718  // try to embed the margin, if that fails don't shrink the hull
719  if (hull_computer.compute(verts, stride, count, margin, 0.0f) < 0.0f) {
720  hull_computer.compute(verts, stride, count, 0.0f, 0.0f);
721  *can_embed = false;
722  }
723 
724  rbCollisionShape *shape = new rbCollisionShape;
725  btConvexHullShape *hull_shape = new btConvexHullShape(&(hull_computer.vertices[0].getX()),
726  hull_computer.vertices.size());
727 
728  shape->cshape = hull_shape;
729  shape->mesh = NULL;
730  shape->compoundChilds = 0;
731  shape->compoundChildShapes = NULL;
732  return shape;
733 }
734 
735 /* Setup (Triangle Mesh) ---------- */
736 
737 /* Need to call RB_trimesh_finish() after creating triangle mesh and adding vertices and triangles
738  */
739 
740 rbMeshData *RB_trimesh_data_new(int num_tris, int num_verts)
741 {
742  rbMeshData *mesh = new rbMeshData;
743  mesh->vertices = new rbVert[num_verts];
744  mesh->triangles = new rbTri[num_tris];
745  mesh->num_vertices = num_verts;
746  mesh->num_triangles = num_tris;
747 
748  return mesh;
749 }
750 
752 {
753  delete mesh->index_array;
754  delete[] mesh->vertices;
755  delete[] mesh->triangles;
756  delete mesh;
757 }
758 
759 void RB_trimesh_add_vertices(rbMeshData *mesh, float *vertices, int num_verts, int vert_stride)
760 {
761  for (int i = 0; i < num_verts; i++) {
762  float *vert = (float *)(((char *)vertices + i * vert_stride));
763  mesh->vertices[i].x = vert[0];
764  mesh->vertices[i].y = vert[1];
765  mesh->vertices[i].z = vert[2];
766  }
767 }
768 void RB_trimesh_add_triangle_indices(rbMeshData *mesh, int num, int index0, int index1, int index2)
769 {
770  mesh->triangles[num].v0 = index0;
771  mesh->triangles[num].v1 = index1;
772  mesh->triangles[num].v2 = index2;
773 }
774 
776 {
778  (int *)mesh->triangles,
779  sizeof(rbTri),
780  mesh->num_vertices,
781  (btScalar *)mesh->vertices,
782  sizeof(rbVert));
783 }
784 
786 {
787  rbCollisionShape *shape = new rbCollisionShape;
788 
789  /* triangle-mesh we create is a BVH wrapper for triangle mesh data (for faster lookups) */
790  // RB_TODO perhaps we need to allow saving out this for performance when rebuilding?
791  btBvhTriangleMeshShape *unscaledShape = new btBvhTriangleMeshShape(
792  mesh->index_array, true, true);
793 
794  shape->cshape = new btScaledBvhTriangleMeshShape(unscaledShape, btVector3(1.0f, 1.0f, 1.0f));
795  shape->mesh = mesh;
796  shape->compoundChilds = 0;
797  shape->compoundChildShapes = NULL;
798  return shape;
799 }
800 
802  float *vertices,
803  int num_verts,
804  int vert_stride,
805  const float min[3],
806  const float max[3])
807 {
808  if (shape->mesh == NULL || num_verts != shape->mesh->num_vertices) {
809  return;
810  }
811 
812  for (int i = 0; i < num_verts; i++) {
813  float *vert = (float *)(((char *)vertices + i * vert_stride));
814  shape->mesh->vertices[i].x = vert[0];
815  shape->mesh->vertices[i].y = vert[1];
816  shape->mesh->vertices[i].z = vert[2];
817  }
818 
819  if (shape->cshape->getShapeType() == SCALED_TRIANGLE_MESH_SHAPE_PROXYTYPE) {
821  btBvhTriangleMeshShape *mesh_shape = scaled_shape->getChildShape();
822  mesh_shape->refitTree(btVector3(min[0], min[1], min[2]), btVector3(max[0], max[1], max[2]));
823  }
824  else if (shape->cshape->getShapeType() == GIMPACT_SHAPE_PROXYTYPE) {
825  btGImpactMeshShape *mesh_shape = (btGImpactMeshShape *)shape->cshape;
826  mesh_shape->updateBound();
827  }
828 }
829 
831 {
832  rbCollisionShape *shape = new rbCollisionShape;
833 
834  btGImpactMeshShape *gimpactShape = new btGImpactMeshShape(mesh->index_array);
835  gimpactShape->updateBound(); // TODO: add this to the update collision margin call?
836 
837  shape->cshape = gimpactShape;
838  shape->mesh = mesh;
839  shape->compoundChilds = 0;
840  shape->compoundChildShapes = NULL;
841  return shape;
842 }
843 
844 /* Compound Shape ---------------- */
845 
847 {
848  rbCollisionShape *shape = new rbCollisionShape;
849  btCompoundShape *compoundShape = new btCompoundShape();
850 
851  shape->cshape = compoundShape;
852  shape->mesh = NULL;
853  shape->compoundChilds = 0;
854  shape->compoundChildShapes = NULL;
855  return shape;
856 }
857 
859  rbCollisionShape *shape,
860  const float loc[3],
861  const float rot[4])
862 {
863  /* set transform matrix */
864  btTransform trans;
865  trans.setIdentity();
866  trans.setOrigin(btVector3(loc[0], loc[1], loc[2]));
867  trans.setRotation(btQuaternion(rot[1], rot[2], rot[3], rot[0]));
868 
869  btCompoundShape *compoundShape = (btCompoundShape *)(parentShape->cshape);
870  compoundShape->addChildShape(trans, shape->cshape);
871 
872  /* Store shapes for deletion later */
873  parentShape->compoundChildShapes = (rbCollisionShape **)(realloc(
874  parentShape->compoundChildShapes,
875  sizeof(rbCollisionShape *) * (++parentShape->compoundChilds)));
876  parentShape->compoundChildShapes[parentShape->compoundChilds - 1] = shape;
877 }
878 
879 /* Cleanup --------------------------- */
880 
882 {
883  if (shape->cshape->getShapeType() == SCALED_TRIANGLE_MESH_SHAPE_PROXYTYPE) {
884  btBvhTriangleMeshShape *child_shape =
885  ((btScaledBvhTriangleMeshShape *)shape->cshape)->getChildShape();
886 
887  delete child_shape;
888  }
889  if (shape->mesh) {
891  }
892  delete shape->cshape;
893 
894  /* Delete compound child shapes if there are any */
895  for (int i = 0; i < shape->compoundChilds; i++) {
897  }
898  if (shape->compoundChildShapes != NULL) {
899  free(shape->compoundChildShapes);
900  }
901 
902  delete shape;
903 }
904 
905 /* Settings --------------------------- */
906 
908 {
909  return shape->cshape->getMargin();
910 }
911 
912 void RB_shape_set_margin(rbCollisionShape *shape, float value)
913 {
914  shape->cshape->setMargin(value);
915 }
916 
917 /* ********************************** */
918 /* Constraints */
919 
920 /* Setup ----------------------------- */
921 
922 void RB_dworld_add_constraint(rbDynamicsWorld *world, rbConstraint *con, int disable_collisions)
923 {
924  btTypedConstraint *constraint = reinterpret_cast<btTypedConstraint *>(con);
925 
926  world->dynamicsWorld->addConstraint(constraint, disable_collisions);
927 }
928 
930 {
931  btTypedConstraint *constraint = reinterpret_cast<btTypedConstraint *>(con);
932 
933  world->dynamicsWorld->removeConstraint(constraint);
934 }
935 
936 /* ............ */
937 
938 static void make_constraint_transforms(btTransform &transform1,
939  btTransform &transform2,
940  btRigidBody *body1,
941  btRigidBody *body2,
942  float pivot[3],
943  float orn[4])
944 {
945  btTransform pivot_transform = btTransform();
946  pivot_transform.setIdentity();
947  pivot_transform.setOrigin(btVector3(pivot[0], pivot[1], pivot[2]));
948  pivot_transform.setRotation(btQuaternion(orn[1], orn[2], orn[3], orn[0]));
949 
950  transform1 = body1->getWorldTransform().inverse() * pivot_transform;
951  transform2 = body2->getWorldTransform().inverse() * pivot_transform;
952 }
953 
955 {
956  btRigidBody *body1 = rb1->body;
957  btRigidBody *body2 = rb2->body;
958 
959  btVector3 pivot1 = body1->getWorldTransform().inverse() *
960  btVector3(pivot[0], pivot[1], pivot[2]);
961  btVector3 pivot2 = body2->getWorldTransform().inverse() *
962  btVector3(pivot[0], pivot[1], pivot[2]);
963 
964  btTypedConstraint *con = new btPoint2PointConstraint(*body1, *body2, pivot1, pivot2);
965 
966  return (rbConstraint *)con;
967 }
968 
970  float orn[4],
971  rbRigidBody *rb1,
972  rbRigidBody *rb2)
973 {
974  btRigidBody *body1 = rb1->body;
975  btRigidBody *body2 = rb2->body;
976  btTransform transform1;
977  btTransform transform2;
978 
979  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
980 
981  btFixedConstraint *con = new btFixedConstraint(*body1, *body2, transform1, transform2);
982 
983  return (rbConstraint *)con;
984 }
985 
987  float orn[4],
988  rbRigidBody *rb1,
989  rbRigidBody *rb2)
990 {
991  btRigidBody *body1 = rb1->body;
992  btRigidBody *body2 = rb2->body;
993  btTransform transform1;
994  btTransform transform2;
995 
996  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
997 
998  btHingeConstraint *con = new btHingeConstraint(*body1, *body2, transform1, transform2);
999 
1000  return (rbConstraint *)con;
1001 }
1002 
1004  float orn[4],
1005  rbRigidBody *rb1,
1006  rbRigidBody *rb2)
1007 {
1008  btRigidBody *body1 = rb1->body;
1009  btRigidBody *body2 = rb2->body;
1010  btTransform transform1;
1011  btTransform transform2;
1012 
1013  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
1014 
1015  btSliderConstraint *con = new btSliderConstraint(*body1, *body2, transform1, transform2, true);
1016 
1017  return (rbConstraint *)con;
1018 }
1019 
1021  float orn[4],
1022  rbRigidBody *rb1,
1023  rbRigidBody *rb2)
1024 {
1025  btRigidBody *body1 = rb1->body;
1026  btRigidBody *body2 = rb2->body;
1027  btTransform transform1;
1028  btTransform transform2;
1029 
1030  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
1031 
1032  btSliderConstraint *con = new btSliderConstraint(*body1, *body2, transform1, transform2, true);
1033  con->setUpperAngLimit(-1.0f); // unlock rotation axis
1034 
1035  return (rbConstraint *)con;
1036 }
1037 
1039  float orn[4],
1040  rbRigidBody *rb1,
1041  rbRigidBody *rb2)
1042 {
1043  btRigidBody *body1 = rb1->body;
1044  btRigidBody *body2 = rb2->body;
1045  btTransform transform1;
1046  btTransform transform2;
1047 
1048  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
1049 
1051  *body1, *body2, transform1, transform2, true);
1052 
1053  return (rbConstraint *)con;
1054 }
1055 
1057  float orn[4],
1058  rbRigidBody *rb1,
1059  rbRigidBody *rb2)
1060 {
1061  btRigidBody *body1 = rb1->body;
1062  btRigidBody *body2 = rb2->body;
1063  btTransform transform1;
1064  btTransform transform2;
1065 
1066  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
1067 
1069  *body1, *body2, transform1, transform2, true);
1070 
1071  return (rbConstraint *)con;
1072 }
1073 
1075  float orn[4],
1076  rbRigidBody *rb1,
1077  rbRigidBody *rb2)
1078 {
1079  btRigidBody *body1 = rb1->body;
1080  btRigidBody *body2 = rb2->body;
1081  btTransform transform1;
1082  btTransform transform2;
1083 
1084  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
1085 
1087  *body1, *body2, transform1, transform2);
1088 
1089  return (rbConstraint *)con;
1090 }
1091 
1093  float orn[4],
1094  rbRigidBody *rb1,
1095  rbRigidBody *rb2)
1096 {
1097  btRigidBody *body1 = rb1->body;
1098  btRigidBody *body2 = rb2->body;
1099  btTransform transform1;
1100  btTransform transform2;
1101 
1102  make_constraint_transforms(transform1, transform2, body1, body2, pivot, orn);
1103 
1105  *body1, *body2, transform1, transform2, true);
1106 
1107  /* unlock constraint axes */
1108  for (int i = 0; i < 6; i++) {
1109  con->setLimit(i, 0.0f, -1.0f);
1110  }
1111  /* unlock motor axes */
1112  con->getTranslationalLimitMotor()->m_upperLimit.setValue(-1.0f, -1.0f, -1.0f);
1113 
1114  return (rbConstraint *)con;
1115 }
1116 
1117 /* Cleanup ----------------------------- */
1118 
1120 {
1121  btTypedConstraint *constraint = reinterpret_cast<btTypedConstraint *>(con);
1122  delete constraint;
1123 }
1124 
1125 /* Settings ------------------------- */
1126 
1128 {
1129  btTypedConstraint *constraint = reinterpret_cast<btTypedConstraint *>(con);
1130 
1131  constraint->setEnabled(enabled);
1132 }
1133 
1134 void RB_constraint_set_limits_hinge(rbConstraint *con, float lower, float upper)
1135 {
1136  btHingeConstraint *constraint = reinterpret_cast<btHingeConstraint *>(con);
1137 
1138  // RB_TODO expose these
1139  float softness = 0.9f;
1140  float bias_factor = 0.3f;
1141  float relaxation_factor = 1.0f;
1142 
1143  constraint->setLimit(lower, upper, softness, bias_factor, relaxation_factor);
1144 }
1145 
1146 void RB_constraint_set_limits_slider(rbConstraint *con, float lower, float upper)
1147 {
1148  btSliderConstraint *constraint = reinterpret_cast<btSliderConstraint *>(con);
1149 
1150  constraint->setLowerLinLimit(lower);
1151  constraint->setUpperLinLimit(upper);
1152 }
1153 
1155  rbConstraint *con, float lin_lower, float lin_upper, float ang_lower, float ang_upper)
1156 {
1157  btSliderConstraint *constraint = reinterpret_cast<btSliderConstraint *>(con);
1158 
1159  constraint->setLowerLinLimit(lin_lower);
1160  constraint->setUpperLinLimit(lin_upper);
1161  constraint->setLowerAngLimit(ang_lower);
1162  constraint->setUpperAngLimit(ang_upper);
1163 }
1164 
1165 void RB_constraint_set_limits_6dof(rbConstraint *con, int axis, float lower, float upper)
1166 {
1167  btGeneric6DofConstraint *constraint = reinterpret_cast<btGeneric6DofConstraint *>(con);
1168 
1169  constraint->setLimit(axis, lower, upper);
1170 }
1171 
1172 void RB_constraint_set_limits_6dof_spring2(rbConstraint *con, int axis, float lower, float upper)
1173 {
1174  btGeneric6DofSpring2Constraint *constraint = reinterpret_cast<btGeneric6DofSpring2Constraint *>(
1175  con);
1176 
1177  constraint->setLimit(axis, lower, upper);
1178 }
1179 
1180 void RB_constraint_set_stiffness_6dof_spring(rbConstraint *con, int axis, float stiffness)
1181 {
1182  btGeneric6DofSpringConstraint *constraint = reinterpret_cast<btGeneric6DofSpringConstraint *>(
1183  con);
1184 
1185  constraint->setStiffness(axis, stiffness);
1186 }
1187 
1188 void RB_constraint_set_damping_6dof_spring(rbConstraint *con, int axis, float damping)
1189 {
1190  btGeneric6DofSpringConstraint *constraint = reinterpret_cast<btGeneric6DofSpringConstraint *>(
1191  con);
1192 
1193  // invert damping range so that 0 = no damping
1194  damping = (damping > 1.0f) ? 0.0f : 1.0f - damping;
1195 
1196  constraint->setDamping(axis, damping);
1197 }
1198 
1199 void RB_constraint_set_spring_6dof_spring(rbConstraint *con, int axis, int enable)
1200 {
1201  btGeneric6DofSpringConstraint *constraint = reinterpret_cast<btGeneric6DofSpringConstraint *>(
1202  con);
1203 
1204  constraint->enableSpring(axis, enable);
1205 }
1206 
1208 {
1209  btGeneric6DofSpringConstraint *constraint = reinterpret_cast<btGeneric6DofSpringConstraint *>(
1210  con);
1211 
1212  constraint->setEquilibriumPoint();
1213 }
1214 
1215 void RB_constraint_set_stiffness_6dof_spring2(rbConstraint *con, int axis, float stiffness)
1216 {
1217  btGeneric6DofSpring2Constraint *constraint = reinterpret_cast<btGeneric6DofSpring2Constraint *>(
1218  con);
1219 
1220  constraint->setStiffness(axis, stiffness);
1221 }
1222 
1223 void RB_constraint_set_damping_6dof_spring2(rbConstraint *con, int axis, float damping)
1224 {
1225  btGeneric6DofSpring2Constraint *constraint = reinterpret_cast<btGeneric6DofSpring2Constraint *>(
1226  con);
1227 
1228  constraint->setDamping(axis, damping);
1229 }
1230 
1231 void RB_constraint_set_spring_6dof_spring2(rbConstraint *con, int axis, int enable)
1232 {
1233  btGeneric6DofSpring2Constraint *constraint = reinterpret_cast<btGeneric6DofSpring2Constraint *>(
1234  con);
1235 
1236  constraint->enableSpring(axis, enable);
1237 }
1238 
1240 {
1241  btGeneric6DofSpring2Constraint *constraint = reinterpret_cast<btGeneric6DofSpring2Constraint *>(
1242  con);
1243 
1244  constraint->setEquilibriumPoint();
1245 }
1246 
1247 void RB_constraint_set_solver_iterations(rbConstraint *con, int num_solver_iterations)
1248 {
1249  btTypedConstraint *constraint = reinterpret_cast<btTypedConstraint *>(con);
1250 
1251  constraint->setOverrideNumSolverIterations(num_solver_iterations);
1252 }
1253 
1255 {
1256  btTypedConstraint *constraint = reinterpret_cast<btTypedConstraint *>(con);
1257 
1258  constraint->setBreakingImpulseThreshold(threshold);
1259 }
1260 
1261 void RB_constraint_set_enable_motor(rbConstraint *con, int enable_lin, int enable_ang)
1262 {
1263  btGeneric6DofConstraint *constraint = reinterpret_cast<btGeneric6DofConstraint *>(con);
1264 
1265  constraint->getTranslationalLimitMotor()->m_enableMotor[0] = enable_lin;
1266  constraint->getRotationalLimitMotor(0)->m_enableMotor = enable_ang;
1267 }
1268 
1270  float max_impulse_lin,
1271  float max_impulse_ang)
1272 {
1273  btGeneric6DofConstraint *constraint = reinterpret_cast<btGeneric6DofConstraint *>(con);
1274 
1275  constraint->getTranslationalLimitMotor()->m_maxMotorForce.setX(max_impulse_lin);
1276  constraint->getRotationalLimitMotor(0)->m_maxMotorForce = max_impulse_ang;
1277 }
1278 
1280  float velocity_lin,
1281  float velocity_ang)
1282 {
1283  btGeneric6DofConstraint *constraint = reinterpret_cast<btGeneric6DofConstraint *>(con);
1284 
1285  constraint->getTranslationalLimitMotor()->m_targetVelocity.setX(velocity_lin);
1286  constraint->getRotationalLimitMotor(0)->m_targetVelocity = velocity_ang;
1287 }
1288 
1289 /* ********************************** */
typedef float(TangentPoint)[2]
void BLI_kdtree_nd_() free(KDTree *tree)
Definition: kdtree_impl.h:102
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_BOOL GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLushort pattern _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble u2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLdouble GLdouble v2 _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLdouble GLdouble nz _GL_VOID_RET _GL_VOID GLfloat GLfloat nz _GL_VOID_RET _GL_VOID GLint GLint nz _GL_VOID_RET _GL_VOID GLshort GLshort nz _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const GLfloat *values _GL_VOID_RET _GL_VOID GLsizei const GLushort *values _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID const GLuint const GLclampf *priorities _GL_VOID_RET _GL_VOID GLdouble y _GL_VOID_RET _GL_VOID GLfloat y _GL_VOID_RET _GL_VOID GLint y _GL_VOID_RET _GL_VOID GLshort y _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLfloat GLfloat z _GL_VOID_RET _GL_VOID GLint GLint z _GL_VOID_RET _GL_VOID GLshort GLshort z _GL_VOID_RET _GL_VOID GLdouble GLdouble z
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei height
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint y
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei stride
Rigid Body API for interfacing with external Physics Engines.
struct rbCollisionShape rbCollisionShape
Definition: RBI_api.h:37
struct rbMeshData rbMeshData
Definition: RBI_api.h:40
struct rbRigidBody rbRigidBody
Definition: RBI_api.h:34
struct rbDynamicsWorld rbDynamicsWorld
Definition: RBI_api.h:31
struct rbConstraint rbConstraint
Definition: RBI_api.h:43
btBoxShape(const btVector3 &boxHalfExtents)
Definition: btBoxShape.cpp:17
@ GIMPACT_SHAPE_PROXYTYPE
Used for GIMPACT Trimesh integration.
@ SCALED_TRIANGLE_MESH_SHAPE_PROXYTYPE
btBroadphaseProxy
btBvhTriangleMeshShape(btStridingMeshInterface *meshInterface, bool useQuantizedAabbCompression, bool buildBvh=true)
#define ACTIVE_TAG
#define DISABLE_DEACTIVATION
@ CF_KINEMATIC_OBJECT
void * getUserPointer() const
users can point to their objects, userPointer is not used by Bullet
#define ISLAND_SLEEPING
btCollisionShape
The btCollisionShape class provides an interface for collision shapes that can be shared among btColl...
btCompoundShape(bool enableDynamicAabbTree=true, const int initialChildCapacity=0)
btConvexHullShape(const btScalar *points=0, int numPoints=0, int stride=sizeof(btVector3))
btConvexShape()
not supported on IBM SDK, until we fix the alignment of btVector3
btDefaultMotionState(const btTransform &startTrans=btTransform::getIdentity(), const btTransform &centerOfMassOffset=btTransform::getIdentity())
btDiscreteDynamicsWorld(btDispatcher *dispatcher, btBroadphaseInterface *pairCache, btConstraintSolver *constraintSolver, btCollisionConfiguration *collisionConfiguration)
this btDiscreteDynamicsWorld constructor gets created objects from the user, and will not delete thos...
btGeneric6DofConstraint(btRigidBody &rbA, btRigidBody &rbB, const btTransform &frameInA, const btTransform &frameInB, bool useLinearReferenceFrameA)
btGeneric6DofSpring2Constraint(btRigidBody &rbA, btRigidBody &rbB, const btTransform &frameInA, const btTransform &frameInB, RotateOrder rotOrder=RO_XYZ)
btGeneric6DofSpringConstraint(btRigidBody &rbA, btRigidBody &rbB, const btTransform &frameInA, const btTransform &frameInB, bool useLinearReferenceFrameA)
btHingeConstraint(btRigidBody &rbA, btRigidBody &rbB, const btVector3 &pivotInA, const btVector3 &pivotInB, const btVector3 &axisInA, const btVector3 &axisInB, bool useReferenceFrameA=false)
btPoint2PointConstraint(btRigidBody &rbA, btRigidBody &rbB, const btVector3 &pivotInA, const btVector3 &pivotInB)
float btScalar
The btScalar type abstracts floating point numbers, to easily switch between double and single floati...
Definition: btScalar.h:314
#define btAssert(x)
Definition: btScalar.h:295
btScaledBvhTriangleMeshShape(btBvhTriangleMeshShape *childShape, const btVector3 &localScaling)
btSliderConstraint(btRigidBody &rbA, btRigidBody &rbB, const btTransform &frameInA, const btTransform &frameInB, bool useLinearReferenceFrameA)
btSphereShape(btScalar radius)
Definition: btSphereShape.h:29
btTransform
The btTransform class supports rigid transforms with only translation and rotation and no scaling/she...
Definition: btTransform.h:30
btTriangleIndexVertexArray()
btTypedConstraint(btTypedConstraintType type, btRigidBody &rbA)
btVector3
btVector3 can be used to represent 3D points and vectors. It has an un-used w component to suit 16-by...
Definition: btVector3.h:82
SIMD_FORCE_INLINE int size() const
return the number of elements in the array
btConeShapeZ implements a Cone shape, around the Z axis
Definition: btConeShape.h:124
btAlignedObjectArray< btVector3 > vertices
virtual const unsigned char * getBufferPointer() const
Definition: btSerializer.h:564
virtual int getCurrentBufferSize() const
Definition: btSerializer.h:569
static void registerAlgorithm(btCollisionDispatcher *dispatcher)
Use this function for register the algorithm externally.
This class manages a mesh supplied by the btStridingMeshInterface interface.
SIMD_FORCE_INLINE void updateBound()
performs refit operation
virtual void getWorldTransform(btTransform &worldTrans) const =0
virtual void setWorldTransform(const btTransform &worldTrans)=0
The btQuaternion implements quaternion to perform linear algebra rotations in combination with btMatr...
Definition: btQuaternion.h:50
SIMD_FORCE_INLINE const btScalar & getW() const
Definition: btQuaternion.h:614
void setLinearFactor(const btVector3 &linearFactor)
Definition: btRigidBody.h:258
SIMD_FORCE_INLINE const btCollisionShape * getCollisionShape() const
Definition: btRigidBody.h:242
const btVector3 & getAngularVelocity() const
Definition: btRigidBody.h:437
btMotionState * getMotionState()
Definition: btRigidBody.h:549
btScalar getLinearSleepingThreshold() const
Definition: btRigidBody.h:230
void applyCentralForce(const btVector3 &force)
Definition: btRigidBody.h:274
btScalar getInvMass() const
Definition: btRigidBody.h:263
btScalar getAngularDamping() const
Definition: btRigidBody.h:225
int getNumConstraintRefs() const
Definition: btRigidBody.h:598
void removeConstraintRef(btTypedConstraint *c)
void setSleepingThresholds(btScalar linear, btScalar angular)
Definition: btRigidBody.h:299
void setMassProps(btScalar mass, const btVector3 &inertia)
const btVector3 & getLinearVelocity() const
Definition: btRigidBody.h:433
btScalar getAngularSleepingThreshold() const
Definition: btRigidBody.h:235
void setAngularFactor(const btVector3 &angFac)
Definition: btRigidBody.h:568
btScalar getLinearDamping() const
Definition: btRigidBody.h:220
btTypedConstraint * getConstraintRef(int index)
Definition: btRigidBody.h:593
void setAngularVelocity(const btVector3 &ang_vel)
Definition: btRigidBody.h:451
void setDamping(btScalar lin_damping, btScalar ang_damping)
void setLinearVelocity(const btVector3 &lin_vel)
Definition: btRigidBody.h:442
void updateInertiaTensor()
FILE * file
World world
#define rot(x, k)
static float verts[][3]
bool enabled
int count
ccl_gpu_kernel_postfix ccl_global float int int int int float threshold
void RB_constraint_set_max_impulse_motor(rbConstraint *con, float max_impulse_lin, float max_impulse_ang)
float RB_body_get_angular_damping(rbRigidBody *object)
rbConstraint * RB_constraint_new_point(float pivot[3], rbRigidBody *rb1, rbRigidBody *rb2)
float RB_body_get_linear_damping(rbRigidBody *object)
void RB_dworld_set_solver_iterations(rbDynamicsWorld *world, int num_solver_iterations)
void RB_dworld_add_body(rbDynamicsWorld *world, rbRigidBody *object, int col_groups)
void RB_dworld_set_split_impulse(rbDynamicsWorld *world, int split_impulse)
rbCollisionShape * RB_shape_new_convex_hull(float *verts, int stride, int count, float margin, bool *can_embed)
void RB_dworld_delete(rbDynamicsWorld *world)
rbCollisionShape * RB_shape_new_cone(float radius, float height)
rbCollisionShape * RB_shape_new_compound()
void RB_constraint_set_stiffness_6dof_spring(rbConstraint *con, int axis, float stiffness)
void RB_body_set_restitution(rbRigidBody *object, float value)
void RB_body_set_friction(rbRigidBody *object, float value)
void RB_body_set_mass(rbRigidBody *object, float value)
void RB_body_set_activation_state(rbRigidBody *object, int use_deactivation)
rbCollisionShape * RB_shape_new_box(float x, float y, float z)
void RB_shape_trimesh_update(rbCollisionShape *shape, float *vertices, int num_verts, int vert_stride, const float min[3], const float max[3])
void RB_dworld_add_constraint(rbDynamicsWorld *world, rbConstraint *con, int disable_collisions)
void RB_constraint_set_damping_6dof_spring(rbConstraint *con, int axis, float damping)
rbConstraint * RB_constraint_new_motor(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
void RB_shape_delete(rbCollisionShape *shape)
void RB_body_delete(rbRigidBody *object)
rbConstraint * RB_constraint_new_piston(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
void RB_body_get_linear_velocity(rbRigidBody *object, float v_out[3])
void RB_constraint_set_enabled(rbConstraint *con, int enabled)
void RB_body_set_angular_sleep_thresh(rbRigidBody *object, float value)
rbConstraint * RB_constraint_new_6dof_spring(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
void RB_constraint_set_stiffness_6dof_spring2(rbConstraint *con, int axis, float stiffness)
static void RB_trimesh_data_delete(rbMeshData *mesh)
void RB_constraint_set_equilibrium_6dof_spring(rbConstraint *con)
void RB_body_apply_central_force(rbRigidBody *object, const float v_in[3])
void RB_constraint_set_limits_slider(rbConstraint *con, float lower, float upper)
void RB_body_set_angular_damping(rbRigidBody *object, float value)
rbCollisionShape * RB_shape_new_sphere(float radius)
void RB_constraint_set_breaking_threshold(rbConstraint *con, float threshold)
void RB_dworld_remove_constraint(rbDynamicsWorld *world, rbConstraint *con)
void RB_dworld_remove_body(rbDynamicsWorld *world, rbRigidBody *object)
rbConstraint * RB_constraint_new_hinge(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
rbConstraint * RB_constraint_new_fixed(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
rbDynamicsWorld * RB_dworld_new(const float gravity[3])
void RB_world_convex_sweep_test(rbDynamicsWorld *world, rbRigidBody *object, const float loc_start[3], const float loc_end[3], float v_location[3], float v_hitpoint[3], float v_normal[3], int *r_hit)
void RB_constraint_set_enable_motor(rbConstraint *con, int enable_lin, int enable_ang)
void RB_body_get_orientation(rbRigidBody *object, float v_out[4])
void RB_body_set_linear_damping(rbRigidBody *object, float value)
void RB_dworld_set_gravity(rbDynamicsWorld *world, const float g_in[3])
void RB_compound_add_child_shape(rbCollisionShape *parentShape, rbCollisionShape *shape, const float loc[3], const float rot[4])
rbCollisionShape * RB_shape_new_gimpact_mesh(rbMeshData *mesh)
void RB_trimesh_add_triangle_indices(rbMeshData *mesh, int num, int index0, int index1, int index2)
void RB_trimesh_add_vertices(rbMeshData *mesh, float *vertices, int num_verts, int vert_stride)
void RB_constraint_set_limits_6dof_spring2(rbConstraint *con, int axis, float lower, float upper)
float RB_body_get_mass(rbRigidBody *object)
void RB_constraint_set_solver_iterations(rbConstraint *con, int num_solver_iterations)
void RB_constraint_set_damping_6dof_spring2(rbConstraint *con, int axis, float damping)
void RB_constraint_delete(rbConstraint *con)
void RB_body_set_collision_shape(rbRigidBody *object, rbCollisionShape *shape)
static void copy_quat_btquat(float quat[4], const btQuaternion &btquat)
void RB_body_set_scale(rbRigidBody *object, const float scale[3])
void RB_body_set_damping(rbRigidBody *object, float linear, float angular)
void RB_body_get_angular_velocity(rbRigidBody *object, float v_out[3])
void RB_constraint_set_spring_6dof_spring(rbConstraint *con, int axis, int enable)
void RB_shape_set_margin(rbCollisionShape *shape, float value)
void RB_body_set_linear_sleep_thresh(rbRigidBody *object, float value)
void RB_body_set_linear_velocity(rbRigidBody *object, const float v_in[3])
void RB_body_deactivate(rbRigidBody *object)
rbRigidBody * RB_body_new(rbCollisionShape *shape, const float loc[3], const float rot[4])
void RB_body_set_kinematic_state(rbRigidBody *object, int kinematic)
void RB_trimesh_finish(rbMeshData *mesh)
void RB_body_get_position(rbRigidBody *object, float v_out[3])
void RB_dworld_export(rbDynamicsWorld *world, const char *filename)
float RB_shape_get_margin(rbCollisionShape *shape)
rbCollisionShape * RB_shape_new_cylinder(float radius, float height)
rbConstraint * RB_constraint_new_6dof_spring2(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
void RB_constraint_set_limits_piston(rbConstraint *con, float lin_lower, float lin_upper, float ang_lower, float ang_upper)
static void copy_v3_btvec3(float vec[3], const btVector3 &btvec)
void RB_dworld_get_gravity(rbDynamicsWorld *world, float g_out[3])
void RB_body_get_transform_matrix(rbRigidBody *object, float m_out[4][4])
void RB_constraint_set_limits_6dof(rbConstraint *con, int axis, float lower, float upper)
void RB_body_set_loc_rot(rbRigidBody *object, const float loc[3], const float rot[4])
void RB_constraint_set_limits_hinge(rbConstraint *con, float lower, float upper)
rbMeshData * RB_trimesh_data_new(int num_tris, int num_verts)
void RB_constraint_set_target_velocity_motor(rbConstraint *con, float velocity_lin, float velocity_ang)
float RB_body_get_friction(rbRigidBody *object)
rbCollisionShape * RB_shape_new_trimesh(rbMeshData *mesh)
void RB_body_set_angular_velocity(rbRigidBody *object, const float v_in[3])
static void make_constraint_transforms(btTransform &transform1, btTransform &transform2, btRigidBody *body1, btRigidBody *body2, float pivot[3], float orn[4])
void RB_body_activate(rbRigidBody *object)
void RB_body_set_linear_factor(rbRigidBody *object, float x, float y, float z)
void RB_body_set_sleep_thresh(rbRigidBody *object, float linear, float angular)
rbConstraint * RB_constraint_new_slider(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
void RB_dworld_step_simulation(rbDynamicsWorld *world, float timeStep, int maxSubSteps, float timeSubStep)
void RB_constraint_set_equilibrium_6dof_spring2(rbConstraint *con)
float RB_body_get_linear_sleep_thresh(rbRigidBody *object)
void RB_body_get_scale(rbRigidBody *object, float v_out[3])
rbConstraint * RB_constraint_new_6dof(float pivot[3], float orn[4], rbRigidBody *rb1, rbRigidBody *rb2)
void RB_constraint_set_spring_6dof_spring2(rbConstraint *con, int axis, int enable)
rbCollisionShape * RB_shape_new_capsule(float radius, float height)
void RB_body_set_angular_factor(rbRigidBody *object, float x, float y, float z)
float RB_body_get_angular_sleep_thresh(rbRigidBody *object)
float RB_body_get_restitution(rbRigidBody *object)
#define min(a, b)
Definition: sort.c:35
size_t num_triangles() const
Definition: scene/mesh.h:79
rbCollisionShape ** compoundChildShapes
btCollisionShape * cshape
rbMeshData * mesh
btBroadphaseInterface * pairCache
btConstraintSolver * constraintSolver
btDefaultCollisionConfiguration * collisionConfiguration
btDiscreteDynamicsWorld * dynamicsWorld
btOverlapFilterCallback * filterCallback
btDispatcher * dispatcher
virtual bool needBroadphaseCollision(btBroadphaseProxy *proxy0, btBroadphaseProxy *proxy1) const
rbVert * vertices
rbTri * triangles
btTriangleIndexVertexArray * index_array
btRigidBody * body
btScalar y
btScalar x
btScalar z
float max