游戏开发论坛

 找回密码
 立即注册
搜索
查看: 2838|回复: 4

DirectX里关于射线与面相交的一段代码,求解释,实在看不懂~

[复制链接]

2

主题

5

帖子

20

积分

注册会员

Rank: 2

积分
20
发表于 2013-5-19 00:09:55 | 显示全部楼层 |阅读模式
我理解的部分后面写了注释了,不知道理解的对不对,从/////开始后面的部分就看不懂了~

BOOL IntersectTriangle( const D3DXVECTOR3& orig,
                                           const D3DXVECTOR3& dir, const D3DXVECTOR3& v0,
                                           const D3DXVECTOR3& v1, const D3DXVECTOR3& v2,
                                           FLOAT* t, FLOAT* u, FLOAT* v )                  
//传入一个射线起点,一个射线方向,面的3个顶点,返回一个距离T,交点位置所受3个点影响的权重u,权重v(另外一个为1-u-v)
{
        D3DXVECTOR3 edge1 = v1 - v0;   
        D3DXVECTOR3 edge2 = v2 - v0;   //求出面的两条边

        D3DXVECTOR3 pvec;         
        D3DXVec3Cross( &pvec, &dir, &edge2 );        //求出面上任意一条边与射线方向所成平面的垂线

        FLOAT det = D3DXVec3Dot( &edge1, &pvec );        //求出上述垂线与面上另一条边所成的夹角的COS值

        D3DXVECTOR3 tvec;
        if( det > 0 )            //如果该夹角的COS值大于0,说明射线是射向该面的,并求出?????
        {
                tvec = orig - v0;
        }
        else                       //如果该夹角的COS值大于0,说明射线是向面反方向走的,并求出????
        {        
                tvec = v0 - orig;
                det = -det;
        }

        if( det < 0.0001f )  //如果该夹角的COS值接近于0,说明射线是与面几乎平行的,没有交点,直接返回FALSE
                return FALSE;

        *u = D3DXVec3Dot( &tvec, &pvec );   //求交点位置所受面上三个顶点影响的权重U,怎么求得???
        if( *u < 0.0f || *u > det )               //为何满足该条件就返回FALSE???
                return FALSE;

        D3DXVECTOR3 qvec;
        D3DXVec3Cross( &qvec, &tvec, &edge1 );   //这是在干什么???

        *v = D3DXVec3Dot( &dir, &qvec );   //求交点位置所受面上三个顶点影响的权重U,怎么求得???
        if( *v < 0.0f || *u + *v > det )         //为何满足该条件就返回FALSE???
                return FALSE;

        *t = D3DXVec3Dot( &edge2, &qvec );  //求距离T,怎么求得???

        FLOAT fInvDet = 1.0f / det;        //这又是什么意思?
        *t *= fInvDet;
        *u *= fInvDet;
        *v *= fInvDet;
        if(*t<0) return FALSE;

        return TRUE;
};

拜托各位大神有时间帮帮忙解释一下阿,现在急着写东西~

33

主题

159

帖子

272

积分

中级会员

Rank: 3Rank: 3

积分
272
QQ
发表于 2013-5-19 11:40:20 | 显示全部楼层
光看这个程序当然看不懂了,看懂了就神奇了,程序里用的公式是个推导公式,名称忘记了,推导过程你自己看下面的网址,老实说感觉不用研究的太深,能用推导公式自己写就行

http://blog.csdn.net/xiaosaret/article/details/6698305

希望对你有用

2

主题

5

帖子

20

积分

注册会员

Rank: 2

积分
20
 楼主| 发表于 2013-5-19 17:07:49 | 显示全部楼层
dana9919 发表于 2013-5-19 11:40
光看这个程序当然看不懂了,看懂了就神奇了,程序里用的公式是个推导公式,名称忘记了,推导过程你自己看下 ...

感谢,就是它了,已经看懂了,这篇文章很不错~

0

主题

1

帖子

6

积分

新手上路

Rank: 1

积分
6
发表于 2013-6-5 01:19:04 | 显示全部楼层
能单独解释一下这儿吗??
D3DXVECTOR3 tvec;
        if( det > 0 )            //如果该夹角的COS值大于0,说明射线是射向该面的,并求出?????
        {
                tvec = orig - v0;
        }
        else                       //如果该夹角的COS值大于0,说明射线是向面反方向走的,并求出????
        {        
                tvec = v0 - orig;
                det = -det;
        }

谢谢了

11

主题

1238

帖子

1782

积分

金牌会员

Rank: 6Rank: 6

积分
1782
发表于 2013-6-5 14:27:48 | 显示全部楼层
设三角形三个顶点为V0,V1,V2,射线为O+Dt,则三角形与射线可组成方程

O + Dt = V0 + (V1 – V0)u + (V2 – V0)v                       
其中u, v, t 为未知数,设E1 = V1 – V0, E2 = V2 – V0, B = O – V0,则
B = E1u + E2v – Dt
于是有一个三元一次方程组,其解为
det = | E1, E2, -D | = dot( -D, cross( E1, E2 ) ) = dot( E2, cross( -D, E1 ) ) = dot( E1, cross( E2, -D ) )

det(E1) = | B, E2, -D | = dot( -D, cross( B, E2 ) ) = dot( E2, cross( -D, B ) ) = dot( B, cross( E2, -D ) )

det(E2) = | E1, B, -D | = dot( -D, cross( E1, B ) ) = dot( B, cross( -D, E1 ) ) = dot( E1, cross( B, -D ) )

det(-D) = | E1, E2, B | = dot( B, cross( E1, E2 ) ) = dot( E2, cross( B, E1 ) ) = dot( E1, cross( E2, B ) )

u = det(E1) / det
v = det(E2) / det
t = det(-D) / det

如果 det != 0 && u >= 0 && u <= det && v >= 0 && u+v <= det,那么相交点则在三角形内部
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

作品发布|文章投稿|广告合作|关于本站|游戏开发论坛 ( 闽ICP备17032699号-3 )

GMT+8, 2025-2-26 19:13

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表