Vegastrike 0.5.1 rc1  1.0
Original sources for Vegastrike Evolved
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
SphereCollider Class Reference

#include <OPC_SphereCollider.h>

Inheritance diagram for SphereCollider:
VolumeCollider Collider HybridSphereCollider

Public Member Functions

 SphereCollider ()
 
virtual ~SphereCollider ()
 
bool Collide (SphereCache &cache, const Sphere &sphere, const Model &model, const Matrix4x4 *worlds=null, const Matrix4x4 *worldm=null)
 
bool Collide (SphereCache &cache, const Sphere &sphere, const AABBTree *tree)
 
- Public Member Functions inherited from VolumeCollider
 VolumeCollider ()
 
virtual ~VolumeCollider ()=0
 
inline_ udword GetNbTouchedPrimitives () const
 
inline_ const udwordGetTouchedPrimitives () const
 
inline_ udword GetNbVolumeBVTests () const
 
inline_ udword GetNbVolumePrimTests () const
 
 override (Collider) const char *ValidateSettings()
 
- Public Member Functions inherited from Collider
 Collider ()
 
virtual ~Collider ()
 
inline_ BOOL GetContactStatus () const
 
inline_ BOOL FirstContactEnabled () const
 
inline_ BOOL TemporalCoherenceEnabled () const
 
inline_ BOOL ContactFound () const
 
inline_ BOOL TemporalHit () const
 
inline_ BOOL SkipPrimitiveTests () const
 
inline_ void SetFirstContact (bool flag)
 
inline_ void SetTemporalCoherence (bool flag)
 
inline_ void SetPrimitiveTests (bool flag)
 
virtual const char * ValidateSettings ()=0
 

Protected Member Functions

void _Collide (const AABBCollisionNode *node)
 
void _Collide (const AABBNoLeafNode *node)
 
void _Collide (const AABBQuantizedNode *node)
 
void _Collide (const AABBQuantizedNoLeafNode *node)
 
void _Collide (const AABBTreeNode *node)
 
void _CollideNoPrimitiveTest (const AABBCollisionNode *node)
 
void _CollideNoPrimitiveTest (const AABBNoLeafNode *node)
 
void _CollideNoPrimitiveTest (const AABBQuantizedNode *node)
 
void _CollideNoPrimitiveTest (const AABBQuantizedNoLeafNode *node)
 
inline_ bool SphereContainsBox (const Point &bc, const Point &be)
 
inline_ bool SphereAABBOverlap (const Point &center, const Point &extents)
 
bool SphereTriOverlap (const Point &vert0, const Point &vert1, const Point &vert2)
 
bool InitQuery (SphereCache &cache, const Sphere &sphere, const Matrix4x4 *worlds=null, const Matrix4x4 *worldm=null)
 
- Protected Member Functions inherited from VolumeCollider
void _Dump (const AABBCollisionNode *node)
 
void _Dump (const AABBNoLeafNode *node)
 
void _Dump (const AABBQuantizedNode *node)
 
void _Dump (const AABBQuantizedNoLeafNode *node)
 
 override (Collider) inline_ void InitQuery()
 
inline_ BOOL IsCacheValid (VolumeCache &cache)
 
- Protected Member Functions inherited from Collider
inline_ BOOL Setup (const BaseModel *model)
 
virtual inline_ void InitQuery ()
 

Protected Attributes

Point mCenter
 Sphere center. More...
 
float mRadius2
 Sphere radius squared. More...
 
- Protected Attributes inherited from VolumeCollider
ContainermTouchedPrimitives
 List of touched primitives. More...
 
Point mCenterCoeff
 
Point mExtentsCoeff
 
udword mNbVolumeBVTests
 Number of Volume-BV tests. More...
 
udword mNbVolumePrimTests
 Number of Volume-Primitive tests. More...
 
- Protected Attributes inherited from Collider
udword mFlags
 Bit flags. More...
 
const BaseModelmCurrentModel
 Current model for collision query (owner of touched faces) More...
 
const MeshInterfacemIMesh
 User-defined mesh interface. More...
 

Detailed Description

Contains a sphere-vs-tree collider. This class performs a collision test between a sphere and an AABB tree. You can use this to do a standard player vs world collision, in a Nettle/Telemachos way. It doesn't suffer from all reported bugs in those two classic codes - the "new" one by Paul Nettle is a debuggued version I think. Collision response can be driven by reported collision data - it works extremely well for me. In sake of efficiency, all meshes (that is, all AABB trees) should of course also be kept in an extra hierarchical structure (octree, whatever).

Author
Pierre Terdiman
Version
1.3
Date
June, 2, 2001

Definition at line 35 of file OPC_SphereCollider.h.

Constructor & Destructor Documentation

SphereCollider::SphereCollider ( )
virtual SphereCollider::~SphereCollider ( )
virtual

Member Function Documentation

void SphereCollider::_Collide ( const AABBCollisionNode node)
protected
void SphereCollider::_Collide ( const AABBNoLeafNode node)
protected
void SphereCollider::_Collide ( const AABBQuantizedNode node)
protected
void SphereCollider::_Collide ( const AABBQuantizedNoLeafNode node)
protected
void SphereCollider::_Collide ( const AABBTreeNode node)
protected
void SphereCollider::_CollideNoPrimitiveTest ( const AABBCollisionNode node)
protected
void SphereCollider::_CollideNoPrimitiveTest ( const AABBNoLeafNode node)
protected
void SphereCollider::_CollideNoPrimitiveTest ( const AABBQuantizedNode node)
protected
void SphereCollider::_CollideNoPrimitiveTest ( const AABBQuantizedNoLeafNode node)
protected
bool SphereCollider::Collide ( SphereCache cache,
const Sphere sphere,
const Model model,
const Matrix4x4 worlds = null,
const Matrix4x4 worldm = null 
)

Generic collision query for generic OPCODE models. After the call, access the results:

Parameters
cache[in/out] a sphere cache
sphere[in] collision sphere in local space
model[in] Opcode model to collide with
worlds[in] sphere's world matrix, or null
worldm[in] model's world matrix, or null
Returns
true if success
Warning
SCALE NOT SUPPORTED. The matrices must contain rotation & translation parts only.
bool SphereCollider::Collide ( SphereCache cache,
const Sphere sphere,
const AABBTree tree 
)
bool SphereCollider::InitQuery ( SphereCache cache,
const Sphere sphere,
const Matrix4x4 worlds = null,
const Matrix4x4 worldm = null 
)
protected
inline_ bool SphereCollider::SphereAABBOverlap ( const Point center,
const Point extents 
)
protected

Sphere-AABB overlap test, based on Jim Arvo's code.

Parameters
center[in] box center
extents[in] box extents
Returns
TRUE on overlap

Definition at line 9 of file OPC_SphereAABBOverlap.h.

10 {
11  // Stats
13 
14  float d = 0.0f;
15 
16  //find the square of the distance
17  //from the sphere to the box
18 #ifdef OLDIES
19  for(udword i=0;i<3;i++)
20  {
21  float tmp = mCenter[i] - center[i];
22  float s = tmp + extents[i];
23 
24  if(s<0.0f) d += s*s;
25  else
26  {
27  s = tmp - extents[i];
28  if(s>0.0f) d += s*s;
29  }
30  }
31 #endif
32 
33 //#ifdef NEW_TEST
34 
35 // float tmp = mCenter.x - center.x;
36 // float s = tmp + extents.x;
37 
38  float tmp,s;
39 
40  tmp = mCenter.x - center.x;
41  s = tmp + extents.x;
42 
43  if(s<0.0f)
44  {
45  d += s*s;
46  if(d>mRadius2) return FALSE;
47  }
48  else
49  {
50  s = tmp - extents.x;
51  if(s>0.0f)
52  {
53  d += s*s;
54  if(d>mRadius2) return FALSE;
55  }
56  }
57 
58  tmp = mCenter.y - center.y;
59  s = tmp + extents.y;
60 
61  if(s<0.0f)
62  {
63  d += s*s;
64  if(d>mRadius2) return FALSE;
65  }
66  else
67  {
68  s = tmp - extents.y;
69  if(s>0.0f)
70  {
71  d += s*s;
72  if(d>mRadius2) return FALSE;
73  }
74  }
75 
76  tmp = mCenter.z - center.z;
77  s = tmp + extents.z;
78 
79  if(s<0.0f)
80  {
81  d += s*s;
82  if(d>mRadius2) return FALSE;
83  }
84  else
85  {
86  s = tmp - extents.z;
87  if(s>0.0f)
88  {
89  d += s*s;
90  if(d>mRadius2) return FALSE;
91  }
92  }
93 //#endif
94 
95 #ifdef OLDIES
96 // Point Min = center - extents;
97 // Point Max = center + extents;
98 
99  float d = 0.0f;
100 
101  //find the square of the distance
102  //from the sphere to the box
103  for(udword i=0;i<3;i++)
104  {
105 float Min = center[i] - extents[i];
106 
107 // if(mCenter[i]<Min[i])
108  if(mCenter[i]<Min)
109  {
110 // float s = mCenter[i] - Min[i];
111  float s = mCenter[i] - Min;
112  d += s*s;
113  }
114  else
115  {
116 float Max = center[i] + extents[i];
117 
118 // if(mCenter[i]>Max[i])
119  if(mCenter[i]>Max)
120  {
121  float s = mCenter[i] - Max;
122  d += s*s;
123  }
124  }
125  }
126 #endif
127  return d <= mRadius2;
128 }
inline_ bool SphereCollider::SphereContainsBox ( const Point bc,
const Point be 
)
protected
bool SphereCollider::SphereTriOverlap ( const Point vert0,
const Point vert1,
const Point vert2 
)
protected

Definition at line 9 of file OPC_SphereTriOverlap.h.

References f, MAX_FLOAT, mCenter, VolumeCollider::mNbVolumePrimTests, mRadius2, Point::SquareMagnitude(), TRUE, and v.

10 {
11  // Stats
13 
14  // Early exit if one of the vertices is inside the sphere
15  Point kDiff = vert2 - mCenter;
16  float fC = kDiff.SquareMagnitude();
17  if(fC <= mRadius2) return TRUE;
18 
19  kDiff = vert1 - mCenter;
20  fC = kDiff.SquareMagnitude();
21  if(fC <= mRadius2) return TRUE;
22 
23  kDiff = vert0 - mCenter;
24  fC = kDiff.SquareMagnitude();
25  if(fC <= mRadius2) return TRUE;
26 
27  // Else do the full distance test
28  Point TriEdge0 = vert1 - vert0;
29  Point TriEdge1 = vert2 - vert0;
30 
31 //Point kDiff = vert0 - mCenter;
32  float fA00 = TriEdge0.SquareMagnitude();
33  float fA01 = TriEdge0 | TriEdge1;
34  float fA11 = TriEdge1.SquareMagnitude();
35  float fB0 = kDiff | TriEdge0;
36  float fB1 = kDiff | TriEdge1;
37 //float fC = kDiff.SquareMagnitude();
38  float fDet = fabsf(fA00*fA11 - fA01*fA01);
39  float u = fA01*fB1-fA11*fB0;
40  float v = fA01*fB0-fA00*fB1;
41  float SqrDist;
42 
43  if(u + v <= fDet)
44  {
45  if(u < 0.0f)
46  {
47  if(v < 0.0f) // region 4
48  {
49  if(fB0 < 0.0f)
50  {
51 // v = 0.0f;
52  if(-fB0>=fA00) { /*u = 1.0f;*/ SqrDist = fA00+2.0f*fB0+fC; }
53  else { u = -fB0/fA00; SqrDist = fB0*u+fC; }
54  }
55  else
56  {
57 // u = 0.0f;
58  if(fB1>=0.0f) { /*v = 0.0f;*/ SqrDist = fC; }
59  else if(-fB1>=fA11) { /*v = 1.0f;*/ SqrDist = fA11+2.0f*fB1+fC; }
60  else { v = -fB1/fA11; SqrDist = fB1*v+fC; }
61  }
62  }
63  else // region 3
64  {
65 // u = 0.0f;
66  if(fB1>=0.0f) { /*v = 0.0f;*/ SqrDist = fC; }
67  else if(-fB1>=fA11) { /*v = 1.0f;*/ SqrDist = fA11+2.0f*fB1+fC; }
68  else { v = -fB1/fA11; SqrDist = fB1*v+fC; }
69  }
70  }
71  else if(v < 0.0f) // region 5
72  {
73 // v = 0.0f;
74  if(fB0>=0.0f) { /*u = 0.0f;*/ SqrDist = fC; }
75  else if(-fB0>=fA00) { /*u = 1.0f;*/ SqrDist = fA00+2.0f*fB0+fC; }
76  else { u = -fB0/fA00; SqrDist = fB0*u+fC; }
77  }
78  else // region 0
79  {
80  // minimum at interior point
81  if(fDet==0.0f)
82  {
83 // u = 0.0f;
84 // v = 0.0f;
85  SqrDist = MAX_FLOAT;
86  }
87  else
88  {
89  float fInvDet = 1.0f/fDet;
90  u *= fInvDet;
91  v *= fInvDet;
92  SqrDist = u*(fA00*u+fA01*v+2.0f*fB0) + v*(fA01*u+fA11*v+2.0f*fB1)+fC;
93  }
94  }
95  }
96  else
97  {
98  float fTmp0, fTmp1, fNumer, fDenom;
99 
100  if(u < 0.0f) // region 2
101  {
102  fTmp0 = fA01 + fB0;
103  fTmp1 = fA11 + fB1;
104  if(fTmp1 > fTmp0)
105  {
106  fNumer = fTmp1 - fTmp0;
107  fDenom = fA00-2.0f*fA01+fA11;
108  if(fNumer >= fDenom)
109  {
110 // u = 1.0f;
111 // v = 0.0f;
112  SqrDist = fA00+2.0f*fB0+fC;
113  }
114  else
115  {
116  u = fNumer/fDenom;
117  v = 1.0f - u;
118  SqrDist = u*(fA00*u+fA01*v+2.0f*fB0) + v*(fA01*u+fA11*v+2.0f*fB1)+fC;
119  }
120  }
121  else
122  {
123 // u = 0.0f;
124  if(fTmp1 <= 0.0f) { /*v = 1.0f;*/ SqrDist = fA11+2.0f*fB1+fC; }
125  else if(fB1 >= 0.0f) { /*v = 0.0f;*/ SqrDist = fC; }
126  else { v = -fB1/fA11; SqrDist = fB1*v+fC; }
127  }
128  }
129  else if(v < 0.0f) // region 6
130  {
131  fTmp0 = fA01 + fB1;
132  fTmp1 = fA00 + fB0;
133  if(fTmp1 > fTmp0)
134  {
135  fNumer = fTmp1 - fTmp0;
136  fDenom = fA00-2.0f*fA01+fA11;
137  if(fNumer >= fDenom)
138  {
139 // v = 1.0f;
140 // u = 0.0f;
141  SqrDist = fA11+2.0f*fB1+fC;
142  }
143  else
144  {
145  v = fNumer/fDenom;
146  u = 1.0f - v;
147  SqrDist = u*(fA00*u+fA01*v+2.0f*fB0) + v*(fA01*u+fA11*v+2.0f*fB1)+fC;
148  }
149  }
150  else
151  {
152 // v = 0.0f;
153  if(fTmp1 <= 0.0f) { /*u = 1.0f;*/ SqrDist = fA00+2.0f*fB0+fC; }
154  else if(fB0 >= 0.0f) { /*u = 0.0f;*/ SqrDist = fC; }
155  else { u = -fB0/fA00; SqrDist = fB0*u+fC; }
156  }
157  }
158  else // region 1
159  {
160  fNumer = fA11 + fB1 - fA01 - fB0;
161  if(fNumer <= 0.0f)
162  {
163 // u = 0.0f;
164 // v = 1.0f;
165  SqrDist = fA11+2.0f*fB1+fC;
166  }
167  else
168  {
169  fDenom = fA00-2.0f*fA01+fA11;
170  if(fNumer >= fDenom)
171  {
172 // u = 1.0f;
173 // v = 0.0f;
174  SqrDist = fA00+2.0f*fB0+fC;
175  }
176  else
177  {
178  u = fNumer/fDenom;
179  v = 1.0f - u;
180  SqrDist = u*(fA00*u+fA01*v+2.0f*fB0) + v*(fA01*u+fA11*v+2.0f*fB1)+fC;
181  }
182  }
183  }
184  }
185 
186  return fabsf(SqrDist) < mRadius2;
187 }

Member Data Documentation

Point SphereCollider::mCenter
protected

Sphere center.

Definition at line 64 of file OPC_SphereCollider.h.

Referenced by SphereTriOverlap().

float SphereCollider::mRadius2
protected

Sphere radius squared.

Definition at line 65 of file OPC_SphereCollider.h.

Referenced by SphereTriOverlap().


The documentation for this class was generated from the following files: