Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/ode/ode-0.9/OPCODE/OPC_RayTriOverlap.h @ 216

Last change on this file since 216 was 216, checked in by mathiask, 16 years ago

[Physik] add ode-0.9

File size: 3.4 KB
Line 
1#define LOCAL_EPSILON 0.000001f
2
3///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
4/**
5 *      Computes a ray-triangle intersection test.
6 *      Original code from Tomas Möller's "Fast Minimum Storage Ray-Triangle Intersection".
7 *      It's been optimized a bit with integer code, and modified to return a non-intersection if distance from
8 *      ray origin to triangle is negative.
9 *
10 *      \param          vert0   [in] triangle vertex
11 *      \param          vert1   [in] triangle vertex
12 *      \param          vert2   [in] triangle vertex
13 *      \return         true on overlap. mStabbedFace is filled with relevant info.
14 */
15///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
16inline_ BOOL RayCollider::RayTriOverlap(const Point& vert0, const Point& vert1, const Point& vert2)
17{
18        // Stats
19        mNbRayPrimTests++;
20
21        // Find vectors for two edges sharing vert0
22        Point edge1 = vert1 - vert0;
23        Point edge2 = vert2 - vert0;
24
25        // Begin calculating determinant - also used to calculate U parameter
26        Point pvec = mDir^edge2;
27
28        // If determinant is near zero, ray lies in plane of triangle
29        float det = edge1|pvec;
30
31        if(mCulling)
32        {
33                if(det<LOCAL_EPSILON)                                                                                                           return FALSE;
34                // From here, det is > 0. So we can use integer cmp.
35
36                // Calculate distance from vert0 to ray origin
37                Point tvec = mOrigin - vert0;
38
39                // Calculate U parameter and test bounds
40                mStabbedFace.mU = tvec|pvec;
41//              if(IR(u)&0x80000000 || u>det)                                   return FALSE;
42                if(IS_NEGATIVE_FLOAT(mStabbedFace.mU) || IR(mStabbedFace.mU)>IR(det))           return FALSE;
43
44                // Prepare to test V parameter
45                Point qvec = tvec^edge1;
46
47                // Calculate V parameter and test bounds
48                mStabbedFace.mV = mDir|qvec;
49                if(IS_NEGATIVE_FLOAT(mStabbedFace.mV) || mStabbedFace.mU+mStabbedFace.mV>det)   return FALSE;
50
51                // Calculate t, scale parameters, ray intersects triangle
52                mStabbedFace.mDistance = edge2|qvec;
53                // Det > 0 so we can early exit here
54                // Intersection point is valid if distance is positive (else it can just be a face behind the orig point)
55                if(IS_NEGATIVE_FLOAT(mStabbedFace.mDistance))                                                           return FALSE;
56                // Else go on
57                float OneOverDet = 1.0f / det;
58                mStabbedFace.mDistance *= OneOverDet;
59                mStabbedFace.mU *= OneOverDet;
60                mStabbedFace.mV *= OneOverDet;
61        }
62        else
63        {
64                // the non-culling branch
65                if(det>-LOCAL_EPSILON && det<LOCAL_EPSILON)                                                                     return FALSE;
66                float OneOverDet = 1.0f / det;
67
68                // Calculate distance from vert0 to ray origin
69                Point tvec = mOrigin - vert0;
70
71                // Calculate U parameter and test bounds
72                mStabbedFace.mU = (tvec|pvec) * OneOverDet;
73//              if(IR(u)&0x80000000 || u>1.0f)                                  return FALSE;
74                if(IS_NEGATIVE_FLOAT(mStabbedFace.mU) || IR(mStabbedFace.mU)>IEEE_1_0)          return FALSE;
75
76                // prepare to test V parameter
77                Point qvec = tvec^edge1;
78
79                // Calculate V parameter and test bounds
80                mStabbedFace.mV = (mDir|qvec) * OneOverDet;
81                if(IS_NEGATIVE_FLOAT(mStabbedFace.mV) || mStabbedFace.mU+mStabbedFace.mV>1.0f)  return FALSE;
82
83                // Calculate t, ray intersects triangle
84                mStabbedFace.mDistance = (edge2|qvec) * OneOverDet;
85                // Intersection point is valid if distance is positive (else it can just be a face behind the orig point)
86                if(IS_NEGATIVE_FLOAT(mStabbedFace.mDistance))                                                           return FALSE;
87        }
88        return TRUE;
89}
Note: See TracBrowser for help on using the repository browser.