Fixed several bugs: python refcounting related and Bullet related (basic add/remove...
[blender.git] / extern / bullet / Bullet / CollisionShapes / BvhTriangleMeshShape.cpp
1 /*
2  * Copyright (c) 2006 Erwin Coumans http://continuousphysics.com/Bullet/
3  *
4  * Permission to use, copy, modify, distribute and sell this software
5  * and its documentation for any purpose is hereby granted without fee,
6  * provided that the above copyright notice appear in all copies.
7  * Erwin Coumans makes no representations about the suitability 
8  * of this software for any purpose.  
9  * It is provided "as is" without express or implied warranty.
10 */
11
12 //#define DISABLE_BVH
13
14
15 #include "CollisionShapes/BvhTriangleMeshShape.h"
16 #include "CollisionShapes/OptimizedBvh.h"
17
18 ///Bvh Concave triangle mesh is a static-triangle mesh shape with Bounding Volume Hierarchy optimization.
19 ///Uses an interface to access the triangles to allow for sharing graphics/physics triangles.
20 BvhTriangleMeshShape::BvhTriangleMeshShape(StridingMeshInterface* meshInterface)
21 :TriangleMeshShape(meshInterface)
22 {
23         //construct bvh from meshInterface
24 #ifndef DISABLE_BVH
25
26         m_bvh = new OptimizedBvh();
27         m_bvh->Build(meshInterface);
28
29 #endif //DISABLE_BVH
30
31 }
32
33 BvhTriangleMeshShape::~BvhTriangleMeshShape()
34 {
35         delete m_bvh;
36 }
37
38 //perform bvh tree traversal and report overlapping triangles to 'callback'
39 void    BvhTriangleMeshShape::ProcessAllTriangles(TriangleCallback* callback,const SimdVector3& aabbMin,const SimdVector3& aabbMax) const
40 {
41
42 #ifdef DISABLE_BVH
43         //brute force traverse all triangles
44         TriangleMeshShape::ProcessAllTriangles(callback,aabbMin,aabbMax);
45 #else
46
47         //first get all the nodes
48
49         
50         struct  MyNodeOverlapCallback : public NodeOverlapCallback
51         {
52                 StridingMeshInterface*  m_meshInterface;
53                 TriangleCallback*               m_callback;
54                 SimdVector3                             m_triangle[3];
55
56
57                 MyNodeOverlapCallback(TriangleCallback* callback,StridingMeshInterface* meshInterface)
58                         :m_callback(callback),
59                         m_meshInterface(meshInterface)
60                 {
61                 }
62                                 
63                 virtual void ProcessNode(const OptimizedBvhNode* node)
64                 {
65                         const unsigned char *vertexbase;
66                         int numverts;
67                         PHY_ScalarType type;
68                         int stride;
69                         const unsigned char *indexbase;
70                         int indexstride;
71                         int numfaces;
72                         PHY_ScalarType indicestype;
73                         
74
75                         m_meshInterface->getLockedReadOnlyVertexIndexBase(
76                                 &vertexbase,
77                                 numverts,
78                                 type,
79                                 stride,
80                                 &indexbase,
81                                 indexstride,
82                                 numfaces,
83                                 indicestype,
84                                 node->m_subPart);
85
86                         int* gfxbase = (int*)(indexbase+node->m_triangleIndex*indexstride);
87                         
88                         const SimdVector3& meshScaling = m_meshInterface->getScaling();
89                         for (int j=2;j>=0;j--)
90                         {
91                                 
92                                 int graphicsindex = gfxbase[j];
93 #ifdef DEBUG_TRIANGLE_MESH
94                                 printf("%d ,",graphicsindex);
95 #endif //DEBUG_TRIANGLE_MESH
96                                 float* graphicsbase = (float*)(vertexbase+graphicsindex*stride);
97
98                                 m_triangle[j] = SimdVector3(
99                                         graphicsbase[0]*meshScaling.getX(),
100                                         graphicsbase[1]*meshScaling.getY(),
101                                         graphicsbase[2]*meshScaling.getZ());
102 #ifdef DEBUG_TRIANGLE_MESH
103                                 printf("triangle vertices:%f,%f,%f\n",triangle[j].x(),triangle[j].y(),triangle[j].z());
104 #endif //DEBUG_TRIANGLE_MESH
105                         }
106
107                         m_callback->ProcessTriangle(m_triangle);
108                         m_meshInterface->unLockReadOnlyVertexBase(node->m_subPart);
109                 }
110
111         };
112
113         MyNodeOverlapCallback   myNodeCallback(callback,m_meshInterface);
114
115         m_bvh->ReportAabbOverlappingNodex(&myNodeCallback,aabbMin,aabbMax);
116
117
118 #endif//DISABLE_BVH
119
120
121 }
122
123
124 void    BvhTriangleMeshShape::setLocalScaling(const SimdVector3& scaling)
125 {
126         if ((getLocalScaling() -scaling).length2() > SIMD_EPSILON)
127         {
128                 TriangleMeshShape::setLocalScaling(scaling);
129                 delete m_bvh;
130                 m_bvh = new OptimizedBvh();
131                 m_bvh->Build(m_meshInterface);
132                 //rebuild the bvh...
133         }
134 }