orx 1.16
Portable Game Engine
Loading...
Searching...
No Matches
orxOBox.h
Go to the documentation of this file.
1/* Orx - Portable Game Engine
2 *
3 * Copyright (c) 2008- Orx-Project
4 *
5 * This software is provided 'as-is', without any express or implied
6 * warranty. In no event will the authors be held liable for any damages
7 * arising from the use of this software.
8 *
9 * Permission is granted to anyone to use this software for any purpose,
10 * including commercial applications, and to alter it and redistribute it
11 * freely, subject to the following restrictions:
12 *
13 * 1. The origin of this software must not be misrepresented; you must not
14 * claim that you wrote the original software. If you use this software
15 * in a product, an acknowledgment in the product documentation would be
16 * appreciated but is not required.
17 *
18 * 2. Altered source versions must be plainly marked as such, and must not be
19 * misrepresented as being the original software.
20 *
21 * 3. This notice may not be removed or altered from any source
22 * distribution.
23 */
24
32
41
42
43#ifndef _orxOBOX_H_
44#define _orxOBOX_H_
45
46#include "orxInclude.h"
47
48#include "math/orxVector.h"
49
50
62
63
64/* *** OBox inlined functions *** */
65
66
75static orxINLINE orxOBOX * orxOBox_2DSet(orxOBOX *_pstRes, const orxVECTOR *_pvWorldPosition, const orxVECTOR *_pvPivot, const orxVECTOR *_pvSize, orxFLOAT _fAngle)
76{
77 orxFLOAT fCos, fSin;
78
79 /* Checks */
80 orxASSERT(_pstRes != orxNULL);
81 orxASSERT(_pvWorldPosition != orxNULL);
82 orxASSERT(_pvPivot != orxNULL);
83
84 /* Gets cosine and sine */
85 if(_fAngle == orxFLOAT_0)
86 {
87 fCos = orxFLOAT_1;
88 fSin = orxFLOAT_0;
89 }
90 else
91 {
92 fCos = orxMath_Cos(_fAngle);
93 fSin = orxMath_Sin(_fAngle);
94 }
95
96 /* Sets axis */
97 orxVector_Set(&(_pstRes->vX), fCos * _pvSize->fX, fSin * _pvSize->fX, orxFLOAT_0);
98 orxVector_Set(&(_pstRes->vY), -fSin * _pvSize->fY, fCos * _pvSize->fY, orxFLOAT_0);
99 orxVector_Set(&(_pstRes->vZ), orxFLOAT_0, orxFLOAT_0, _pvSize->fZ);
100
101 /* Sets pivot */
102 orxVector_Set(&(_pstRes->vPivot), (fCos * _pvPivot->fX) - (fSin * _pvPivot->fY), (fSin * _pvPivot->fX) + (fCos * _pvPivot->fY), _pvPivot->fZ);
103
104 /* Sets box position */
105 orxVector_Copy(&(_pstRes->vPosition), _pvWorldPosition);
106
107 /* Done! */
108 return _pstRes;
109}
110
116static orxINLINE orxOBOX * orxOBox_Copy(orxOBOX *_pstDst, const orxOBOX *_pstSrc)
117{
118 /* Checks */
119 orxASSERT(_pstDst != orxNULL);
120 orxASSERT(_pstSrc != orxNULL);
121
122 /* Copies it */
123 orxMemory_Copy(_pstDst, _pstSrc, sizeof(orxOBOX));
124
125 /* Done! */
126 return _pstDst;
127}
128
134static orxINLINE orxVECTOR * orxOBox_GetCenter(const orxOBOX *_pstOp, orxVECTOR *_pvRes)
135{
136 /* Checks */
137 orxASSERT(_pstOp != orxNULL);
138 orxASSERT(_pvRes != orxNULL);
139
140 /* Gets box center */
141 orxVector_Add(_pvRes, orxVector_Add(_pvRes, &(_pstOp->vX), &(_pstOp->vY)), &(_pstOp->vZ));
142 orxVector_Mulf(_pvRes, _pvRes, orx2F(0.5f));
143 orxVector_Sub(_pvRes, orxVector_Add(_pvRes, _pvRes, &(_pstOp->vPosition)), &(_pstOp->vPivot));
144
145 /* Done! */
146 return _pvRes;
147}
148
155static orxINLINE orxOBOX * orxOBox_Move(orxOBOX *_pstRes, const orxOBOX *_pstOp, const orxVECTOR *_pvMove)
156{
157 /* Checks */
158 orxASSERT(_pstRes != orxNULL);
159 orxASSERT(_pstOp != orxNULL);
160 orxASSERT(_pvMove != orxNULL);
161
162 /* Updates result */
163 orxVector_Add(&(_pstRes->vPosition), &(_pstOp->vPosition), _pvMove);
164
165 /* Done! */
166 return _pstRes;
167}
168
175static orxINLINE orxOBOX * orxOBox_2DRotate(orxOBOX *_pstRes, const orxOBOX *_pstOp, orxFLOAT _fAngle)
176{
177 orxFLOAT fSin, fCos;
178
179 /* Checks */
180 orxASSERT(_pstRes != orxNULL);
181 orxASSERT(_pstOp != orxNULL);
182
183 /* Gets cos & sin of angle */
184 if(_fAngle == orxFLOAT_0)
185 {
186 fCos = orxFLOAT_1;
187 fSin = orxFLOAT_0;
188 }
189 else
190 {
191 fCos = orxMath_Cos(_fAngle);
192 fSin = orxMath_Sin(_fAngle);
193 }
194
195 /* Updates axis */
196 orxVector_Set(&(_pstRes->vX), (fCos * _pstOp->vX.fX) - (fSin * _pstOp->vX.fY), (fSin * _pstOp->vX.fX) + (fCos * _pstOp->vX.fY), _pstOp->vX.fZ);
197 orxVector_Set(&(_pstRes->vY), (fCos * _pstOp->vY.fX) - (fSin * _pstOp->vY.fY), (fSin * _pstOp->vY.fX) + (fCos * _pstOp->vY.fY), _pstOp->vY.fZ);
198
199 /* Updates pivot */
200 orxVector_Set(&(_pstRes->vPivot), (fCos * _pstOp->vPivot.fX) - (fSin * _pstOp->vPivot.fY), (fSin * _pstOp->vPivot.fX) + (fCos * _pstOp->vPivot.fY), _pstOp->vPivot.fZ);
201
202 /* Done! */
203 return _pstRes;
204}
205
211static orxINLINE orxBOOL orxOBox_IsInside(const orxOBOX *_pstBox, const orxVECTOR *_pvPosition)
212{
213 orxBOOL bResult = orxFALSE;
214 orxFLOAT fProj;
215 orxVECTOR vToPos;
216
217 /* Checks */
218 orxASSERT(_pstBox != orxNULL);
219 orxASSERT(_pvPosition != orxNULL);
220
221 /* Gets origin to position vector */
222 orxVector_Sub(&vToPos, _pvPosition, orxVector_Sub(&vToPos, &(_pstBox->vPosition), &(_pstBox->vPivot)));
223
224 /* Z-axis test */
225 if(((fProj = orxVector_Dot(&vToPos, &(_pstBox->vZ))) >= orxFLOAT_0)
226 && (fProj <= orxVector_GetSquareSize(&(_pstBox->vZ))))
227 {
228 /* X-axis test */
229 if(((fProj = orxVector_Dot(&vToPos, &(_pstBox->vX))) >= orxFLOAT_0)
230 && (fProj <= orxVector_GetSquareSize(&(_pstBox->vX))))
231 {
232 /* Y-axis test */
233 if(((fProj = orxVector_Dot(&vToPos, &(_pstBox->vY))) >= orxFLOAT_0)
234 && (fProj <= orxVector_GetSquareSize(&(_pstBox->vY))))
235 {
236 /* Updates result */
237 bResult = orxTRUE;
238 }
239 }
240 }
241
242 /* Done! */
243 return bResult;
244}
245
251static orxINLINE orxBOOL orxOBox_2DIsInside(const orxOBOX *_pstBox, const orxVECTOR *_pvPosition)
252{
253 orxBOOL bResult = orxFALSE;
254 orxFLOAT fProj, fSize;
255 orxVECTOR vToPos;
256
257 /* Checks */
258 orxASSERT(_pstBox != orxNULL);
259 orxASSERT(_pvPosition != orxNULL);
260
261 /* Gets origin to position vector */
262 orxVector_Sub(&vToPos, _pvPosition, orxVector_Sub(&vToPos, &(_pstBox->vPosition), &(_pstBox->vPivot)));
263
264 /* X-axis test */
265 if(((fProj = orxVector_Dot(&vToPos, &(_pstBox->vX))) >= orxFLOAT_0)
266 && ((fSize = orxVector_GetSquareSize(&(_pstBox->vX))) > orxFLOAT_0)
267 && (fProj <= fSize))
268 {
269 /* Y-axis test */
270 if(((fProj = orxVector_Dot(&vToPos, &(_pstBox->vY))) >= orxFLOAT_0)
271 && ((fSize = orxVector_GetSquareSize(&(_pstBox->vY))) > orxFLOAT_0)
272 && (fProj <= fSize))
273 {
274 /* Updates result */
275 bResult = orxTRUE;
276 }
277 }
278
279 /* Done! */
280 return bResult;
281}
282
288static orxINLINE orxBOOL orxOBox_ZAlignedTestIntersection(const orxOBOX *_pstBox1, const orxOBOX *_pstBox2)
289{
290 orxBOOL bResult;
291
292 /* Checks */
293 orxASSERT(_pstBox1 != orxNULL);
294 orxASSERT(_pstBox2 != orxNULL);
295 orxASSERT(_pstBox1->vZ.fX == orxFLOAT_0);
296 orxASSERT(_pstBox1->vZ.fY == orxFLOAT_0);
297 orxASSERT(_pstBox1->vZ.fZ >= orxFLOAT_0);
298
299 /* Z intersected? */
300 if((_pstBox2->vPosition.fZ + _pstBox2->vZ.fZ >= _pstBox1->vPosition.fZ)
301 && (_pstBox2->vPosition.fZ <= _pstBox1->vPosition.fZ + _pstBox1->vZ.fZ))
302 {
303 orxU32 i;
304 orxVECTOR vOrigin1, vOrigin2, *pvOrigin1 = &vOrigin1, *pvOrigin2 = &vOrigin2, *pvTemp;
305 const orxOBOX *pstBox1 = _pstBox1, *pstBox2 = _pstBox2, *pstTemp;
306
307 /* Computes boxes origins */
308 vOrigin1.fX = _pstBox1->vPosition.fX - pstBox1->vPivot.fX;
309 vOrigin1.fY = _pstBox1->vPosition.fY - pstBox1->vPivot.fY;
310 vOrigin2.fX = _pstBox2->vPosition.fX - pstBox2->vPivot.fX;
311 vOrigin2.fY = _pstBox2->vPosition.fY - pstBox2->vPivot.fY;
312
313 /* Test each box against the other */
314 for(i = 2, bResult = orxTRUE;
315 i != 0;
316 i--, pstTemp = pstBox1, pstBox1 = pstBox2, pstBox2 = pstTemp, pvTemp = pvOrigin1, pvOrigin1 = pvOrigin2, pvOrigin2 = pvTemp)
317 {
318 orxVECTOR vToCorner[4];
319 const orxVECTOR *pvAxis;
320 orxU32 j;
321
322 /* Gets to-corner vectors */
323 vToCorner[0].fX = pvOrigin2->fX - pvOrigin1->fX;
324 vToCorner[0].fY = pvOrigin2->fY - pvOrigin1->fY;
325 vToCorner[1].fX = vToCorner[0].fX + pstBox2->vX.fX;
326 vToCorner[1].fY = vToCorner[0].fY + pstBox2->vX.fY;
327 vToCorner[2].fX = vToCorner[1].fX + pstBox2->vY.fX;
328 vToCorner[2].fY = vToCorner[1].fY + pstBox2->vY.fY;
329 vToCorner[3].fX = vToCorner[0].fX + pstBox2->vY.fX;
330 vToCorner[3].fY = vToCorner[0].fY + pstBox2->vY.fY;
331
332 /* For both axis */
333 for(j = 2, pvAxis = &(pstBox1->vX);
334 j != 0;
335 j--, pvAxis++)
336 {
337 orxFLOAT fMin, fMax, fProj;
338 orxU32 k;
339
340 /* Gets initial projected values */
341 fMin = fMax = fProj = orxVector_2DDot(&vToCorner[0], pvAxis);
342
343 /* For all remaining corners */
344 for(k = 1; k < 4; k++)
345 {
346 /* Gets projected value */
347 fProj = orxVector_2DDot(&vToCorner[k], pvAxis);
348
349 /* Updates extrema */
350 if(fProj > fMax)
351 {
352 fMax = fProj;
353 }
354 else if(fProj < fMin)
355 {
356 fMin = fProj;
357 }
358 }
359
360 /* Not intersecting? */
361 if((fMax < orxFLOAT_0)
362 || (fMin > orxVector_GetSquareSize(pvAxis)))
363 {
364 /* Updates result */
365 bResult = orxFALSE;
366 break;
367 }
368 }
369 }
370 }
371 else
372 {
373 /* Updates result */
374 bResult = orxFALSE;
375 }
376
377 /* Done! */
378 return bResult;
379}
380
381#endif /* _orxOBOX_H_ */
382
#define orxASSERT(TEST,...)
Definition orxDebug.h:378
static orxINLINE orxFLOAT orxMath_Cos(orxFLOAT _fOp)
Definition orxMath.h:430
static orxINLINE orxFLOAT orxMath_Sin(orxFLOAT _fOp)
Definition orxMath.h:415
static orxINLINE void * orxMemory_Copy(void *_pDest, const void *_pSrc, orxU32 _u32Size)
Definition orxMemory.h:165
static orxINLINE orxOBOX * orxOBox_2DRotate(orxOBOX *_pstRes, const orxOBOX *_pstOp, orxFLOAT _fAngle)
Definition orxOBox.h:175
static orxINLINE orxVECTOR * orxOBox_GetCenter(const orxOBOX *_pstOp, orxVECTOR *_pvRes)
Definition orxOBox.h:134
static orxINLINE orxOBOX * orxOBox_Move(orxOBOX *_pstRes, const orxOBOX *_pstOp, const orxVECTOR *_pvMove)
Definition orxOBox.h:155
static orxINLINE orxBOOL orxOBox_2DIsInside(const orxOBOX *_pstBox, const orxVECTOR *_pvPosition)
Definition orxOBox.h:251
static orxINLINE orxOBOX * orxOBox_2DSet(orxOBOX *_pstRes, const orxVECTOR *_pvWorldPosition, const orxVECTOR *_pvPivot, const orxVECTOR *_pvSize, orxFLOAT _fAngle)
Definition orxOBox.h:75
static orxINLINE orxBOOL orxOBox_ZAlignedTestIntersection(const orxOBOX *_pstBox1, const orxOBOX *_pstBox2)
Definition orxOBox.h:288
static orxINLINE orxBOOL orxOBox_IsInside(const orxOBOX *_pstBox, const orxVECTOR *_pvPosition)
Definition orxOBox.h:211
static orxINLINE orxOBOX * orxOBox_Copy(orxOBOX *_pstDst, const orxOBOX *_pstSrc)
Definition orxOBox.h:116
#define orxFALSE
Definition orxType.h:210
#define orxTRUE
Definition orxType.h:211
static const orxFLOAT orxFLOAT_1
Definition orxType.h:216
static const orxFLOAT orxFLOAT_0
Definition orxType.h:215
static orxINLINE orxVECTOR * orxVector_Mulf(orxVECTOR *_pvRes, const orxVECTOR *_pvOp1, orxFLOAT _fOp2)
Definition orxVector.h:198
static orxINLINE orxFLOAT orxVector_2DDot(const orxVECTOR *_pvOp1, const orxVECTOR *_pvOp2)
Definition orxVector.h:915
static orxINLINE orxVECTOR * orxVector_Copy(orxVECTOR *_pvDst, const orxVECTOR *_pvSrc)
Definition orxVector.h:135
static orxINLINE orxVECTOR * orxVector_Sub(orxVECTOR *_pvRes, const orxVECTOR *_pvOp1, const orxVECTOR *_pvOp2)
Definition orxVector.h:176
static orxINLINE orxFLOAT orxVector_GetSquareSize(const orxVECTOR *_pvOp)
Definition orxVector.h:551
static orxINLINE orxFLOAT orxVector_Dot(const orxVECTOR *_pvOp1, const orxVECTOR *_pvOp2)
Definition orxVector.h:895
static orxINLINE orxVECTOR * orxVector_Set(orxVECTOR *_pvVec, orxFLOAT _fX, orxFLOAT _fY, orxFLOAT _fZ)
Definition orxVector.h:105
static orxINLINE orxVECTOR * orxVector_Add(orxVECTOR *_pvRes, const orxVECTOR *_pvOp1, const orxVECTOR *_pvOp2)
Definition orxVector.h:154
orxVECTOR vX
Definition orxOBox.h:57
orxVECTOR vPosition
Definition orxOBox.h:55
orxVECTOR vY
Definition orxOBox.h:58
orxVECTOR vPivot
Definition orxOBox.h:56
orxVECTOR vZ
Definition orxOBox.h:59
orxFLOAT fY
Definition orxVector.h:77
orxFLOAT fX
Definition orxVector.h:69
orxFLOAT fZ
Definition orxVector.h:85

Generated for orx by doxygen 1.8.11