00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #ifndef B2_COLLISION_H
00020 #define B2_COLLISION_H
00021
00022 #include <Box2D/Common/b2Math.h>
00023 #include <limits.h>
00024
00028
00029 class b2Shape;
00030 class b2CircleShape;
00031 class b2EdgeShape;
00032 class b2PolygonShape;
00033
00034 const uint8 b2_nullFeature = UCHAR_MAX;
00035
00038 struct b2ContactFeature
00039 {
00040 enum Type
00041 {
00042 e_vertex = 0,
00043 e_face = 1
00044 };
00045
00046 uint8 indexA;
00047 uint8 indexB;
00048 uint8 typeA;
00049 uint8 typeB;
00050 };
00051
00053 union b2ContactID
00054 {
00055 b2ContactFeature cf;
00056 uint32 key;
00057 };
00058
00069 struct b2ManifoldPoint
00070 {
00071 b2Vec2 localPoint;
00072 float32 normalImpulse;
00073 float32 tangentImpulse;
00074 b2ContactID id;
00075 };
00076
00093 struct b2Manifold
00094 {
00095 enum Type
00096 {
00097 e_circles,
00098 e_faceA,
00099 e_faceB
00100 };
00101
00102 b2ManifoldPoint points[b2_maxManifoldPoints];
00103 b2Vec2 localNormal;
00104 b2Vec2 localPoint;
00105 Type type;
00106 int32 pointCount;
00107 };
00108
00110 struct b2WorldManifold
00111 {
00116 void Initialize(const b2Manifold* manifold,
00117 const b2Transform& xfA, float32 radiusA,
00118 const b2Transform& xfB, float32 radiusB);
00119
00120 b2Vec2 normal;
00121 b2Vec2 points[b2_maxManifoldPoints];
00122 float32 separations[b2_maxManifoldPoints];
00123 };
00124
00126 enum b2PointState
00127 {
00128 b2_nullState,
00129 b2_addState,
00130 b2_persistState,
00131 b2_removeState
00132 };
00133
00136 void b2GetPointStates(b2PointState state1[b2_maxManifoldPoints], b2PointState state2[b2_maxManifoldPoints],
00137 const b2Manifold* manifold1, const b2Manifold* manifold2);
00138
00140 struct b2ClipVertex
00141 {
00142 b2Vec2 v;
00143 b2ContactID id;
00144 };
00145
00147 struct b2RayCastInput
00148 {
00149 b2Vec2 p1, p2;
00150 float32 maxFraction;
00151 };
00152
00155 struct b2RayCastOutput
00156 {
00157 b2Vec2 normal;
00158 float32 fraction;
00159 };
00160
00162 struct b2AABB
00163 {
00165 bool IsValid() const;
00166
00168 b2Vec2 GetCenter() const
00169 {
00170 return 0.5f * (lowerBound + upperBound);
00171 }
00172
00174 b2Vec2 GetExtents() const
00175 {
00176 return 0.5f * (upperBound - lowerBound);
00177 }
00178
00180 float32 GetPerimeter() const
00181 {
00182 float32 wx = upperBound.x - lowerBound.x;
00183 float32 wy = upperBound.y - lowerBound.y;
00184 return 2.0f * (wx + wy);
00185 }
00186
00188 void Combine(const b2AABB& aabb)
00189 {
00190 lowerBound = b2Min(lowerBound, aabb.lowerBound);
00191 upperBound = b2Max(upperBound, aabb.upperBound);
00192 }
00193
00195 void Combine(const b2AABB& aabb1, const b2AABB& aabb2)
00196 {
00197 lowerBound = b2Min(aabb1.lowerBound, aabb2.lowerBound);
00198 upperBound = b2Max(aabb1.upperBound, aabb2.upperBound);
00199 }
00200
00202 bool Contains(const b2AABB& aabb) const
00203 {
00204 bool result = true;
00205 result = result && lowerBound.x <= aabb.lowerBound.x;
00206 result = result && lowerBound.y <= aabb.lowerBound.y;
00207 result = result && aabb.upperBound.x <= upperBound.x;
00208 result = result && aabb.upperBound.y <= upperBound.y;
00209 return result;
00210 }
00211
00212 bool RayCast(b2RayCastOutput* output, const b2RayCastInput& input) const;
00213
00214 b2Vec2 lowerBound;
00215 b2Vec2 upperBound;
00216 };
00217
00219 void b2CollideCircles(b2Manifold* manifold,
00220 const b2CircleShape* circleA, const b2Transform& xfA,
00221 const b2CircleShape* circleB, const b2Transform& xfB);
00222
00224 void b2CollidePolygonAndCircle(b2Manifold* manifold,
00225 const b2PolygonShape* polygonA, const b2Transform& xfA,
00226 const b2CircleShape* circleB, const b2Transform& xfB);
00227
00229 void b2CollidePolygons(b2Manifold* manifold,
00230 const b2PolygonShape* polygonA, const b2Transform& xfA,
00231 const b2PolygonShape* polygonB, const b2Transform& xfB);
00232
00234 void b2CollideEdgeAndCircle(b2Manifold* manifold,
00235 const b2EdgeShape* polygonA, const b2Transform& xfA,
00236 const b2CircleShape* circleB, const b2Transform& xfB);
00237
00239 void b2CollideEdgeAndPolygon(b2Manifold* manifold,
00240 const b2EdgeShape* edgeA, const b2Transform& xfA,
00241 const b2PolygonShape* circleB, const b2Transform& xfB);
00242
00244 int32 b2ClipSegmentToLine(b2ClipVertex vOut[2], const b2ClipVertex vIn[2],
00245 const b2Vec2& normal, float32 offset, int32 vertexIndexA);
00246
00248 bool b2TestOverlap( const b2Shape* shapeA, int32 indexA,
00249 const b2Shape* shapeB, int32 indexB,
00250 const b2Transform& xfA, const b2Transform& xfB);
00251
00252
00253
00254 inline bool b2AABB::IsValid() const
00255 {
00256 b2Vec2 d = upperBound - lowerBound;
00257 bool valid = d.x >= 0.0f && d.y >= 0.0f;
00258 valid = valid && lowerBound.IsValid() && upperBound.IsValid();
00259 return valid;
00260 }
00261
00262 inline bool b2TestOverlap(const b2AABB& a, const b2AABB& b)
00263 {
00264 b2Vec2 d1, d2;
00265 d1 = b.lowerBound - a.upperBound;
00266 d2 = a.lowerBound - b.upperBound;
00267
00268 if (d1.x > 0.0f || d1.y > 0.0f)
00269 return false;
00270
00271 if (d2.x > 0.0f || d2.y > 0.0f)
00272 return false;
00273
00274 return true;
00275 }
00276
00277 #endif