bullet: Update to current svn, r2636
[blender.git] / extern / bullet2 / src / BulletCollision / CollisionDispatch / btCollisionWorld.h
1 /*
2 Bullet Continuous Collision Detection and Physics Library
3 Copyright (c) 2003-2006 Erwin Coumans  http://bulletphysics.com/Bullet/
4
5 This software is provided 'as-is', without any express or implied warranty.
6 In no event will the authors be held liable for any damages arising from the use of this software.
7 Permission is granted to anyone to use this software for any purpose, 
8 including commercial applications, and to alter it and redistribute it freely, 
9 subject to the following restrictions:
10
11 1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
12 2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
13 3. This notice may not be removed or altered from any source distribution.
14 */
15
16
17 /**
18  * @mainpage Bullet Documentation
19  *
20  * @section intro_sec Introduction
21  * Bullet Collision Detection & Physics SDK
22  *
23  * Bullet is a Collision Detection and Rigid Body Dynamics Library. The Library is Open Source and free for commercial use, under the ZLib license ( http://opensource.org/licenses/zlib-license.php ).
24  *
25  * The main documentation is Bullet_User_Manual.pdf, included in the source code distribution.
26  * There is the Physics Forum for feedback and general Collision Detection and Physics discussions.
27  * Please visit http://www.bulletphysics.com
28  *
29  * @section install_sec Installation
30  *
31  * @subsection step1 Step 1: Download
32  * You can download the Bullet Physics Library from the Google Code repository: http://code.google.com/p/bullet/downloads/list
33  *
34  * @subsection step2 Step 2: Building
35  * Bullet main build system for all platforms is cmake, you can download http://www.cmake.org
36  * cmake can autogenerate projectfiles for Microsoft Visual Studio, Apple Xcode, KDevelop and Unix Makefiles.
37  * The easiest is to run the CMake cmake-gui graphical user interface and choose the options and generate projectfiles.
38  * You can also use cmake in the command-line. Here are some examples for various platforms:
39  * cmake . -G "Visual Studio 9 2008"
40  * cmake . -G Xcode
41  * cmake . -G "Unix Makefiles"
42  * Although cmake is recommended, you can also use autotools for UNIX: ./autogen.sh ./configure to create a Makefile and then run make.
43  * 
44  * @subsection step3 Step 3: Testing demos
45  * Try to run and experiment with BasicDemo executable as a starting point.
46  * Bullet can be used in several ways, as Full Rigid Body simulation, as Collision Detector Library or Low Level / Snippets like the GJK Closest Point calculation.
47  * The Dependencies can be seen in this documentation under Directories
48  * 
49  * @subsection step4 Step 4: Integrating in your application, full Rigid Body and Soft Body simulation
50  * Check out BasicDemo how to create a btDynamicsWorld, btRigidBody and btCollisionShape, Stepping the simulation and synchronizing your graphics object transform.
51  * Check out SoftDemo how to use soft body dynamics, using btSoftRigidDynamicsWorld.
52  * @subsection step5 Step 5 : Integrate the Collision Detection Library (without Dynamics and other Extras)
53  * Bullet Collision Detection can also be used without the Dynamics/Extras.
54  * Check out btCollisionWorld and btCollisionObject, and the CollisionInterfaceDemo.
55  * @subsection step6 Step 6 : Use Snippets like the GJK Closest Point calculation.
56  * Bullet has been designed in a modular way keeping dependencies to a minimum. The ConvexHullDistance demo demonstrates direct use of btGjkPairDetector.
57  *
58  * @section copyright Copyright
59  * For up-to-data information and copyright and contributors list check out the Bullet_User_Manual.pdf
60  * 
61  */
62  
63  
64
65 #ifndef BT_COLLISION_WORLD_H
66 #define BT_COLLISION_WORLD_H
67
68 class btStackAlloc;
69 class btCollisionShape;
70 class btConvexShape;
71 class btBroadphaseInterface;
72 class btSerializer;
73
74 #include "LinearMath/btVector3.h"
75 #include "LinearMath/btTransform.h"
76 #include "btCollisionObject.h"
77 #include "btCollisionDispatcher.h"
78 #include "BulletCollision/BroadphaseCollision/btOverlappingPairCache.h"
79 #include "LinearMath/btAlignedObjectArray.h"
80
81 ///CollisionWorld is interface and container for the collision detection
82 class btCollisionWorld
83 {
84
85         
86 protected:
87
88         btAlignedObjectArray<btCollisionObject*>        m_collisionObjects;
89         
90         btDispatcher*   m_dispatcher1;
91
92         btDispatcherInfo        m_dispatchInfo;
93
94         btStackAlloc*   m_stackAlloc;
95
96         btBroadphaseInterface*  m_broadphasePairCache;
97
98         btIDebugDraw*   m_debugDrawer;
99
100         ///m_forceUpdateAllAabbs can be set to false as an optimization to only update active object AABBs
101         ///it is true by default, because it is error-prone (setting the position of static objects wouldn't update their AABB)
102         bool m_forceUpdateAllAabbs;
103
104         void    serializeCollisionObjects(btSerializer* serializer);
105
106 public:
107
108         //this constructor doesn't own the dispatcher and paircache/broadphase
109         btCollisionWorld(btDispatcher* dispatcher,btBroadphaseInterface* broadphasePairCache, btCollisionConfiguration* collisionConfiguration);
110
111         virtual ~btCollisionWorld();
112
113         void    setBroadphase(btBroadphaseInterface*    pairCache)
114         {
115                 m_broadphasePairCache = pairCache;
116         }
117
118         const btBroadphaseInterface*    getBroadphase() const
119         {
120                 return m_broadphasePairCache;
121         }
122
123         btBroadphaseInterface*  getBroadphase()
124         {
125                 return m_broadphasePairCache;
126         }
127
128         btOverlappingPairCache* getPairCache()
129         {
130                 return m_broadphasePairCache->getOverlappingPairCache();
131         }
132
133
134         btDispatcher*   getDispatcher()
135         {
136                 return m_dispatcher1;
137         }
138
139         const btDispatcher*     getDispatcher() const
140         {
141                 return m_dispatcher1;
142         }
143
144         void    updateSingleAabb(btCollisionObject* colObj);
145
146         virtual void    updateAabbs();
147
148         ///the computeOverlappingPairs is usually already called by performDiscreteCollisionDetection (or stepSimulation)
149         ///it can be useful to use if you perform ray tests without collision detection/simulation
150         virtual void    computeOverlappingPairs();
151
152         
153         virtual void    setDebugDrawer(btIDebugDraw*    debugDrawer)
154         {
155                         m_debugDrawer = debugDrawer;
156         }
157
158         virtual btIDebugDraw*   getDebugDrawer()
159         {
160                 return m_debugDrawer;
161         }
162
163         virtual void    debugDrawWorld();
164
165         virtual void debugDrawObject(const btTransform& worldTransform, const btCollisionShape* shape, const btVector3& color);
166
167
168         ///LocalShapeInfo gives extra information for complex shapes
169         ///Currently, only btTriangleMeshShape is available, so it just contains triangleIndex and subpart
170         struct  LocalShapeInfo
171         {
172                 int     m_shapePart;
173                 int     m_triangleIndex;
174                 
175                 //const btCollisionShape*       m_shapeTemp;
176                 //const btTransform*    m_shapeLocalTransform;
177         };
178
179         struct  LocalRayResult
180         {
181                 LocalRayResult(const btCollisionObject* collisionObject, 
182                         LocalShapeInfo* localShapeInfo,
183                         const btVector3&                hitNormalLocal,
184                         btScalar hitFraction)
185                 :m_collisionObject(collisionObject),
186                 m_localShapeInfo(localShapeInfo),
187                 m_hitNormalLocal(hitNormalLocal),
188                 m_hitFraction(hitFraction)
189                 {
190                 }
191
192                 const btCollisionObject*                m_collisionObject;
193                 LocalShapeInfo*                 m_localShapeInfo;
194                 btVector3                               m_hitNormalLocal;
195                 btScalar                                m_hitFraction;
196
197         };
198
199         ///RayResultCallback is used to report new raycast results
200         struct  RayResultCallback
201         {
202                 btScalar        m_closestHitFraction;
203                 const btCollisionObject*                m_collisionObject;
204                 short int       m_collisionFilterGroup;
205                 short int       m_collisionFilterMask;
206                 //@BP Mod - Custom flags, currently used to enable backface culling on tri-meshes, see btRaycastCallback.h. Apply any of the EFlags defined there on m_flags here to invoke.
207                 unsigned int m_flags;
208
209                 virtual ~RayResultCallback()
210                 {
211                 }
212                 bool    hasHit() const
213                 {
214                         return (m_collisionObject != 0);
215                 }
216
217                 RayResultCallback()
218                         :m_closestHitFraction(btScalar(1.)),
219                         m_collisionObject(0),
220                         m_collisionFilterGroup(btBroadphaseProxy::DefaultFilter),
221                         m_collisionFilterMask(btBroadphaseProxy::AllFilter),
222                         //@BP Mod
223                         m_flags(0)
224                 {
225                 }
226
227                 virtual bool needsCollision(btBroadphaseProxy* proxy0) const
228                 {
229                         bool collides = (proxy0->m_collisionFilterGroup & m_collisionFilterMask) != 0;
230                         collides = collides && (m_collisionFilterGroup & proxy0->m_collisionFilterMask);
231                         return collides;
232                 }
233
234
235                 virtual btScalar        addSingleResult(LocalRayResult& rayResult,bool normalInWorldSpace) = 0;
236         };
237
238         struct  ClosestRayResultCallback : public RayResultCallback
239         {
240                 ClosestRayResultCallback(const btVector3&       rayFromWorld,const btVector3&   rayToWorld)
241                 :m_rayFromWorld(rayFromWorld),
242                 m_rayToWorld(rayToWorld)
243                 {
244                 }
245
246                 btVector3       m_rayFromWorld;//used to calculate hitPointWorld from hitFraction
247                 btVector3       m_rayToWorld;
248
249                 btVector3       m_hitNormalWorld;
250                 btVector3       m_hitPointWorld;
251                         
252                 virtual btScalar        addSingleResult(LocalRayResult& rayResult,bool normalInWorldSpace)
253                 {
254                         //caller already does the filter on the m_closestHitFraction
255                         btAssert(rayResult.m_hitFraction <= m_closestHitFraction);
256                         
257                         m_closestHitFraction = rayResult.m_hitFraction;
258                         m_collisionObject = rayResult.m_collisionObject;
259                         if (normalInWorldSpace)
260                         {
261                                 m_hitNormalWorld = rayResult.m_hitNormalLocal;
262                         } else
263                         {
264                                 ///need to transform normal into worldspace
265                                 m_hitNormalWorld = m_collisionObject->getWorldTransform().getBasis()*rayResult.m_hitNormalLocal;
266                         }
267                         m_hitPointWorld.setInterpolate3(m_rayFromWorld,m_rayToWorld,rayResult.m_hitFraction);
268                         return rayResult.m_hitFraction;
269                 }
270         };
271
272         struct  AllHitsRayResultCallback : public RayResultCallback
273         {
274                 AllHitsRayResultCallback(const btVector3&       rayFromWorld,const btVector3&   rayToWorld)
275                 :m_rayFromWorld(rayFromWorld),
276                 m_rayToWorld(rayToWorld)
277                 {
278                 }
279
280                 btAlignedObjectArray<const btCollisionObject*>          m_collisionObjects;
281
282                 btVector3       m_rayFromWorld;//used to calculate hitPointWorld from hitFraction
283                 btVector3       m_rayToWorld;
284
285                 btAlignedObjectArray<btVector3> m_hitNormalWorld;
286                 btAlignedObjectArray<btVector3> m_hitPointWorld;
287                 btAlignedObjectArray<btScalar> m_hitFractions;
288                         
289                 virtual btScalar        addSingleResult(LocalRayResult& rayResult,bool normalInWorldSpace)
290                 {
291                         m_collisionObject = rayResult.m_collisionObject;
292                         m_collisionObjects.push_back(rayResult.m_collisionObject);
293                         btVector3 hitNormalWorld;
294                         if (normalInWorldSpace)
295                         {
296                                 hitNormalWorld = rayResult.m_hitNormalLocal;
297                         } else
298                         {
299                                 ///need to transform normal into worldspace
300                                 hitNormalWorld = m_collisionObject->getWorldTransform().getBasis()*rayResult.m_hitNormalLocal;
301                         }
302                         m_hitNormalWorld.push_back(hitNormalWorld);
303                         btVector3 hitPointWorld;
304                         hitPointWorld.setInterpolate3(m_rayFromWorld,m_rayToWorld,rayResult.m_hitFraction);
305                         m_hitPointWorld.push_back(hitPointWorld);
306                         m_hitFractions.push_back(rayResult.m_hitFraction);
307                         return m_closestHitFraction;
308                 }
309         };
310
311
312         struct LocalConvexResult
313         {
314                 LocalConvexResult(const btCollisionObject*      hitCollisionObject, 
315                         LocalShapeInfo* localShapeInfo,
316                         const btVector3&                hitNormalLocal,
317                         const btVector3&                hitPointLocal,
318                         btScalar hitFraction
319                         )
320                 :m_hitCollisionObject(hitCollisionObject),
321                 m_localShapeInfo(localShapeInfo),
322                 m_hitNormalLocal(hitNormalLocal),
323                 m_hitPointLocal(hitPointLocal),
324                 m_hitFraction(hitFraction)
325                 {
326                 }
327
328                 const btCollisionObject*                m_hitCollisionObject;
329                 LocalShapeInfo*                 m_localShapeInfo;
330                 btVector3                               m_hitNormalLocal;
331                 btVector3                               m_hitPointLocal;
332                 btScalar                                m_hitFraction;
333         };
334
335         ///RayResultCallback is used to report new raycast results
336         struct  ConvexResultCallback
337         {
338                 btScalar        m_closestHitFraction;
339                 short int       m_collisionFilterGroup;
340                 short int       m_collisionFilterMask;
341                 
342                 ConvexResultCallback()
343                         :m_closestHitFraction(btScalar(1.)),
344                         m_collisionFilterGroup(btBroadphaseProxy::DefaultFilter),
345                         m_collisionFilterMask(btBroadphaseProxy::AllFilter)
346                 {
347                 }
348
349                 virtual ~ConvexResultCallback()
350                 {
351                 }
352                 
353                 bool    hasHit() const
354                 {
355                         return (m_closestHitFraction < btScalar(1.));
356                 }
357
358                 
359
360                 virtual bool needsCollision(btBroadphaseProxy* proxy0) const
361                 {
362                         bool collides = (proxy0->m_collisionFilterGroup & m_collisionFilterMask) != 0;
363                         collides = collides && (m_collisionFilterGroup & proxy0->m_collisionFilterMask);
364                         return collides;
365                 }
366
367                 virtual btScalar        addSingleResult(LocalConvexResult& convexResult,bool normalInWorldSpace) = 0;
368         };
369
370         struct  ClosestConvexResultCallback : public ConvexResultCallback
371         {
372                 ClosestConvexResultCallback(const btVector3&    convexFromWorld,const btVector3&        convexToWorld)
373                 :m_convexFromWorld(convexFromWorld),
374                 m_convexToWorld(convexToWorld),
375                 m_hitCollisionObject(0)
376                 {
377                 }
378
379                 btVector3       m_convexFromWorld;//used to calculate hitPointWorld from hitFraction
380                 btVector3       m_convexToWorld;
381
382                 btVector3       m_hitNormalWorld;
383                 btVector3       m_hitPointWorld;
384                 const btCollisionObject*        m_hitCollisionObject;
385                 
386                 virtual btScalar        addSingleResult(LocalConvexResult& convexResult,bool normalInWorldSpace)
387                 {
388 //caller already does the filter on the m_closestHitFraction
389                         btAssert(convexResult.m_hitFraction <= m_closestHitFraction);
390                                                 
391                         m_closestHitFraction = convexResult.m_hitFraction;
392                         m_hitCollisionObject = convexResult.m_hitCollisionObject;
393                         if (normalInWorldSpace)
394                         {
395                                 m_hitNormalWorld = convexResult.m_hitNormalLocal;
396                         } else
397                         {
398                                 ///need to transform normal into worldspace
399                                 m_hitNormalWorld = m_hitCollisionObject->getWorldTransform().getBasis()*convexResult.m_hitNormalLocal;
400                         }
401                         m_hitPointWorld = convexResult.m_hitPointLocal;
402                         return convexResult.m_hitFraction;
403                 }
404         };
405
406         ///ContactResultCallback is used to report contact points
407         struct  ContactResultCallback
408         {
409                 short int       m_collisionFilterGroup;
410                 short int       m_collisionFilterMask;
411                 
412                 ContactResultCallback()
413                         :m_collisionFilterGroup(btBroadphaseProxy::DefaultFilter),
414                         m_collisionFilterMask(btBroadphaseProxy::AllFilter)
415                 {
416                 }
417
418                 virtual ~ContactResultCallback()
419                 {
420                 }
421                 
422                 virtual bool needsCollision(btBroadphaseProxy* proxy0) const
423                 {
424                         bool collides = (proxy0->m_collisionFilterGroup & m_collisionFilterMask) != 0;
425                         collides = collides && (m_collisionFilterGroup & proxy0->m_collisionFilterMask);
426                         return collides;
427                 }
428
429                 virtual btScalar        addSingleResult(btManifoldPoint& cp,    const btCollisionObjectWrapper* colObj0Wrap,int partId0,int index0,const btCollisionObjectWrapper* colObj1Wrap,int partId1,int index1) = 0;
430         };
431
432
433
434         int     getNumCollisionObjects() const
435         {
436                 return int(m_collisionObjects.size());
437         }
438
439         /// rayTest performs a raycast on all objects in the btCollisionWorld, and calls the resultCallback
440         /// This allows for several queries: first hit, all hits, any hit, dependent on the value returned by the callback.
441         virtual void rayTest(const btVector3& rayFromWorld, const btVector3& rayToWorld, RayResultCallback& resultCallback) const; 
442
443         /// convexTest performs a swept convex cast on all objects in the btCollisionWorld, and calls the resultCallback
444         /// This allows for several queries: first hit, all hits, any hit, dependent on the value return by the callback.
445         void    convexSweepTest (const btConvexShape* castShape, const btTransform& from, const btTransform& to, ConvexResultCallback& resultCallback,  btScalar allowedCcdPenetration = btScalar(0.)) const;
446
447         ///contactTest performs a discrete collision test between colObj against all objects in the btCollisionWorld, and calls the resultCallback.
448         ///it reports one or more contact points for every overlapping object (including the one with deepest penetration)
449         void    contactTest(btCollisionObject* colObj, ContactResultCallback& resultCallback);
450
451         ///contactTest performs a discrete collision test between two collision objects and calls the resultCallback if overlap if detected.
452         ///it reports one or more contact points (including the one with deepest penetration)
453         void    contactPairTest(btCollisionObject* colObjA, btCollisionObject* colObjB, ContactResultCallback& resultCallback);
454
455
456         /// rayTestSingle performs a raycast call and calls the resultCallback. It is used internally by rayTest.
457         /// In a future implementation, we consider moving the ray test as a virtual method in btCollisionShape.
458         /// This allows more customization.
459         static void     rayTestSingle(const btTransform& rayFromTrans,const btTransform& rayToTrans,
460                                           btCollisionObject* collisionObject,
461                                           const btCollisionShape* collisionShape,
462                                           const btTransform& colObjWorldTransform,
463                                           RayResultCallback& resultCallback);
464
465         static void     rayTestSingleInternal(const btTransform& rayFromTrans,const btTransform& rayToTrans,
466                                           const btCollisionObjectWrapper* collisionObjectWrap,
467                                           RayResultCallback& resultCallback);
468
469         /// objectQuerySingle performs a collision detection query and calls the resultCallback. It is used internally by rayTest.
470         static void     objectQuerySingle(const btConvexShape* castShape, const btTransform& rayFromTrans,const btTransform& rayToTrans,
471                                           btCollisionObject* collisionObject,
472                                           const btCollisionShape* collisionShape,
473                                           const btTransform& colObjWorldTransform,
474                                           ConvexResultCallback& resultCallback, btScalar        allowedPenetration);
475
476         static void     objectQuerySingleInternal(const btConvexShape* castShape,const btTransform& convexFromTrans,const btTransform& convexToTrans,
477                                                                                         const btCollisionObjectWrapper* colObjWrap,
478                                                                                         ConvexResultCallback& resultCallback, btScalar allowedPenetration);
479
480         virtual void    addCollisionObject(btCollisionObject* collisionObject,short int collisionFilterGroup=btBroadphaseProxy::DefaultFilter,short int collisionFilterMask=btBroadphaseProxy::AllFilter);
481
482         btCollisionObjectArray& getCollisionObjectArray()
483         {
484                 return m_collisionObjects;
485         }
486
487         const btCollisionObjectArray& getCollisionObjectArray() const
488         {
489                 return m_collisionObjects;
490         }
491
492
493         virtual void    removeCollisionObject(btCollisionObject* collisionObject);
494
495         virtual void    performDiscreteCollisionDetection();
496
497         btDispatcherInfo& getDispatchInfo()
498         {
499                 return m_dispatchInfo;
500         }
501
502         const btDispatcherInfo& getDispatchInfo() const
503         {
504                 return m_dispatchInfo;
505         }
506         
507         bool    getForceUpdateAllAabbs() const
508         {
509                 return m_forceUpdateAllAabbs;
510         }
511         void setForceUpdateAllAabbs( bool forceUpdateAllAabbs)
512         {
513                 m_forceUpdateAllAabbs = forceUpdateAllAabbs;
514         }
515
516         ///Preliminary serialization test for Bullet 2.76. Loading those files requires a separate parser (Bullet/Demos/SerializeDemo)
517         virtual void    serialize(btSerializer* serializer);
518
519 };
520
521
522 #endif //BT_COLLISION_WORLD_H