-     D3DXVECTOR3 vec1(-10,0,-10);
 
 -     D3DXVECTOR3 vec2(  0,0, 10);
 
 -     D3DXVECTOR3 vec3( 10,0,-10);
 
  
-     D3DXVECTOR3 vecOrg(0,10,0);
 
 -     D3DXVECTOR3 vecDir(0,-2,0);
 
  
-     //求射线长度
 
 -     D3DXVECTOR3 _vecDir;
 
 -     D3DXVec3Subtract(&_vecDir, &vecDir, &vecOrg);
 
 -     float dis_Ray = D3DXVec3Length(&_vecDir);
 
  
-     D3DXVec3Normalize(&vecDir,&vecDir);
 
  
-     float u;
 
 -     float v;
 
 -     float dis;
 
 -     bool bInt = D3DXIntersectTri(&vec1, &vec2, &vec3, &vecOrg, &vecDir,&u, &v, &dis );
 
 -     if (bInt && dis <= dis_Ray)
 
 -     {
 
 -         //求交点
 
 -         D3DXVECTOR3 vecIntPoint =  vec1 + u * (vec2 - vec1) + v * (vec3 - vec1);
 
 -         return S_OK;
 
 -     }
 
  复制代码 BOOL D3DXIntersectTri( 
         CONST D3DXVECTOR3* p0,                           //顶点1 
         CONST D3DXVECTOR3* p1, 
         CONST D3DXVECTOR3* p2, 
         CONST D3DXVECTOR3* pRayPos,               //射线起始位置 
         CONST D3DXVECTOR3* pRayDir,               //射线方向 
         FLOAT*             pU,                                          //三个点比重 
         FLOAT*             pV, 
         FLOAT*             pDist                                       //射线起点到交点位置 
         );  
 
para :其中p0, p1, p2分别指向三角形的三个顶点,position为射线起点,direction为射线方向向量,u,v,为交点重心坐标,因为不可能只点到顶点上,可能点在三角形范围内,distance为起点到交点距离,成功返回TRUE,失败返回FALSE。 
 
vPickPos = v0 * ( 1-u-v) + v1*u + v2*v = v0 + u * (v1 - v0) + v * (v3 - v0);  
 
特别注意:方向向量必须为单位向量,即pRayDir - pRayPos  为单位向量否则,pDist的值和向量长度成正比关系-  D3DXVECTOR3    rayDir;
 
 -     D3DXVECTOR3 vDest( 10,200,0.f);
 
 -     D3DXVECTOR3 vSour( 10,200,-10.f );
 
 -     rayDir = vDest - vSour;
 
 -     D3DXVec3Normalize( &rayDir, &rayDir );                                    //将方向向量化
 
 -     BOOL bHit = D3DXIntersectTri( &D3DXVECTOR3(0.0f,  0.0f, 0.5f),
 
 -                                 &D3DXVECTOR3(250.0f, 250.0f, 0.5f),
 
 -                                 &D3DXVECTOR3(0.0f, 250.0f, 0.5f),        //pos
 
 -                                 &D3DXVECTOR3(10,200,-10.f ),            //dir
 
 -                                 &rayDir, 
 
 -                                 &fu, 
 
 -                                 &fv, 
 
 -                                 &t );
 
  复制代码游戏中应用 -  float CTerrain::GetZByXY( float fx,float fy  )
 
 -     {
 
 -         //求出第几个方格
 
 -         int x,y;
 
 -         x = fx / MAPTILESIZE;
 
 -         y = fy / MAPTILESIZE;
 
 -         if( x < 0 || x >= m_iMapWidth-1  )
 
 -             return 0;
 
 -         if( y < 0 || y >= m_iMapHeight-1 )
 
 -             return 0;    
 
 -         
 
 -         //方格四顶点
 
 -         D3DXVECTOR3 *pos[4];
 
 -         pos[0] = &m_ppPointPos[ y ][ x ];
 
 -         pos[1] = &m_ppPointPos[ y ][ x + 1];
 
 -         pos[2] = &m_ppPointPos[ y + 1][ x + 1];
 
 -         pos[3] = &m_ppPointPos[ y + 1][ x ];
 
  
-         float fMaxZ;
 
 -         fMaxZ = pos[ 0 ]->z ;
 
 -         int iLoop;
 
 -         for( iLoop = 1 ; iLoop < 4 ; iLoop ++ )
 
 -         {
 
 -             if( fMaxZ < pos[ iLoop ]->z )
 
 -                 fMaxZ = pos[ iLoop ]->z;
 
 -         }
 
  
-         // 求眼睛和地形相交位置,注意单位化方向向量
 
 -         D3DXVECTOR3 vEye,vDir(0,0,-1);
 
  
-         vEye.x = fx;
 
 -         vEye.y = fy;
 
 -         vEye.z = fMaxZ + 10;
 
  
-         float fU,fV,fDis;
 
  
-         if( !D3DXIntersectTri( pos[0],pos[1] ,pos[2],&vEye,&vDir,            //三角形1
 
 -             &fU,&fV,&fDis ) )
 
 -         {    
 
 -             if( !D3DXIntersectTri( pos[2],pos[3],pos[0],&vEye,&vDir,        //三角形2
 
 -                 &fU,&fV,&fDis ) )
 
 -             {
 
 -                 return 0.0f;
 
 -             }
 
 -             else
 
 -             {
 
 -                 return vEye.z - fDis;
 
 -             }
 
 -         }
 
 -         else
 
 -         {
 
 -             return vEye.z - fDis;
 
 -         }
 
 -     }
 
  复制代码 参考: 
地形碰撞计算: 
一.如果是鼠标点击地面, 
可将射线固定长度并分段,然后用射线与每一个分段上的点所落在的地面tile(两个三角形)进行求交, 
相交则返回对应位置,否则继续与下一个段上的点所落在的地面tile求交 
/* 
      0      1 
       ----> 
      | \  | 
      |  \ | 
    2 V ---  3     
*/ 
这里不讨论点击屏幕求射线方法与射线分段处理,只算求交 
如下d3d求交得出uv,再求位置: 
 VECTOR3 vPickPos; 
 // 右边: 
 if( D3DXIntersectTri(&v0, &v1, &v3, &vOrig, &vDir, &u, &v, NULL) == TRUE) 
 { 
  vPickPos = v0 + u * (v1 - v0) + v * (v3 - v0);  
  return vPickPos.z; 
 } 
 // 左边: 
 if( D3DXIntersectTri(&v0, &v3, &v2, &vOrig, &vDir, &u, &v, NULL) == TRUE) 
 { 
  vPickPos = v0 + u * (v3 - v0) + v * (v2 - v0);   
  return vPickPos.z; 
 } 二.如果是仅是求地表某点高度 
则可用uv重心求法(注意上述第一点的d3d的那个uv重心求法不太一样,他的uv跟他的向量走?) 
 float u = (fX-(int)fX); 
 float v = (fY-(int)fY);  float p0 = fHeight[0]; 
 float p1 = fHeight[1]; 
 float p2 = fHeight[2]; 
 float p3 = fHeight[3];  if(u>v){ // 右边 
  return p0 + u * (p1 - p0) + v * (p3 - p1);;  
 } 
 else{  // 左边 
  return  p0 + u * (p3 - p2) + v * (p2 - p0); 
 }  
 |