# ray distance to plane

4 replies to this topic

### #1rouncer

Senior Member

• Members
• 2722 posts

Posted 03 January 2009 - 11:34 AM

How do you compute the distance of a ray starting from a position to hit an infinite plane.
I need to fit it in a shader too, so it has to be minimal, and what would the best way to describe a plane inside a shader?

### #2v71

Valued Member

• Members
• 354 posts

Posted 03 January 2009 - 12:14 PM

/////////////////////////////////////////////////
// intersection beetween plane and line
// returns point of intersection

void RayPlaneIntr( const Vec3f &A ,const Vec3f &B,
const Vec3f &P0,const Vec3f &N ,
Vec3f &Pi )
{
Vec3f D;
float t,denum;
D=B-A;
denum=dot( N,D );
if ( denum==0.0f )
denum=_VT_BSPEPSILON_;
t=dot( N,P0-A );
t/=denum;
Pi=A+t*D;
}

This is the function i use in my engine, to compute intersection point ,
you can easily substituite (sp??)
the Vec3f with a float[3] and the plane with a float[4] , think the rest is clear
If you want only the distance use this

///////////////////////////////////////////////
// distance from plane
// assumes plane is normalized

double DistanceFromPlane( const Vec3f&P ,
const Vec3f& P0,
const Vec3f& Normal )
{
return FastAbs ( dot ( P-P0, Normal ) );
}

By the way i have started a blog where i will put all of my 3d work
along with code snippets like that , and also more advanced stuff
for 3d engine programming, all free of charge of course

http://www.vp8671.blogspot.com/

### #3rouncer

Senior Member

• Members
• 2722 posts

Posted 03 January 2009 - 12:22 PM

Thats a big help, but also i need calculate plane from 3 points, then id be right to get started.
Hang on, is that easy. just find the normal and use one of the points - does that work?

### #4v71

Valued Member

• Members
• 354 posts

Posted 03 January 2009 - 01:14 PM

basically yes, this is a function i wrote compute plane normal(s) , just use what you need

/////////////////////////////////////
// compute normals ,edge normals ,
// center , area and volume

bool ComputeNormals( CSurface *Surface,
Vec3f V0, Vec3f V1,Vec3f V2 )
{
if ( Surface==NULL )
return false;

/////////////////////////////////////
// normal

Vec3f u,v;

u=V1-V0;
v=V2-V0;

Surface->Normal=cross(u,v);
Surface->Normal.normalize();
Surface->D0=-dot( Surface->Normal,V0 );

//////////////////////////////////////////////
// compute edge normals

Vec3f p,n1,n2,n3;

//////////////////////////////////////////////
// compute first edge normal

p=V0+Surface->Normal ;
u=p-V0;
v=V2-V0;
Surface->EdgeNormal1=cross(u,v);
Surface->EdgeNormal1.normalize();

//////////////////////////////////////////////
// compute second edge normal

p=V1+Surface->Normal ;
u=p-V1;
v=V0-V1;
Surface->EdgeNormal2=cross(u,v);
Surface->EdgeNormal2.normalize();

//////////////////////////////////////////////
// compute third edge normal

p=V1+Surface->Normal ;
u=p-V2;
v=V1-V2;
Surface->EdgeNormal3=cross(u,v);
Surface->EdgeNormal3.normalize();

////////////////////////////
// compute center

Surface->Center=(V0+V1+V2)/3.0f;

////////////////////////////
// compute area and volume

u=V1-V0;
v=V2-V0;

p= cross ( u,v );

///////////////////////////
// compute area

Surface->Area= 0.5f *sqrt ( p.length() ) ;

//////////////////////////////
// compute volume

Surface->Volume =dot(V0,cross(V1,V2));

return true;
}
Check my code in the c/c++ section :
http://www.binpress.com/browse/c

### #5imerso

Senior Member

• Members
• 431 posts
• LocationBrasil

Posted 03 January 2009 - 01:24 PM

This one is old, but still works:


//

// Plane from three vertices

//

void CPlane::Determine(CVector *v1, CVector *v2, CVector *v3)

{

CVector Normal = CMath3D::Normal(v1,v2,v3);

m_fA = Normal.x;

m_fB = Normal.y;

m_fC = Normal.z;

// Ax + By + Cz - D = 0  ==>

// Ax + By + Cz = D

m_fD = m_fA*v2->x + m_fB*v2->y + m_fC*v2->z;

}



Normal is computed by:


//

// Normal of three vectors

//

CVector CMath3D::Normal(const CVector *v1, const CVector *v2, const CVector *v3)

{

CVector vt1;

vt1.x = v2->x - v1->x;

vt1.y = v2->y - v1->y;

vt1.z = v2->z - v1->z;

CVector vt2;

vt2.x = v3->x - v2->x;

vt2.y = v3->y - v2->y;

vt2.z = v3->z - v2->z;

CVector Normal = CrossProduct(&vt1,&vt2);

//

// Normalize normal vector

//

float fLen = (float)sqrt(Normal.x*Normal.x + Normal.y*Normal.y + Normal.z*Normal.z);

if (fLen == 0) fLen = 1;

Normal.x /= fLen;

Normal.y /= fLen;

Normal.z /= fLen;

return Normal;

}



CVector is a basic x,y,z class. I think it may be relatively easy to translate into shader code, as it has built-in support for normals and vectors, so you just need to translate the logic.

Hope this helps as well.

#### 1 user(s) are reading this topic

0 members, 1 guests, 0 anonymous users