PDA

View Full Version : Frustum Culling help



jono_123
01-15-2003, 12:42 AM
i've got this function :

bool CFrustum::CubeInFrustum( float x, float y, float z, float size )
{
for(int i = 0; i < 6; i++ )
{
if(m_Frustum[i][A] * (x - size) + m_Frustum[i][B] * (y - size) + m_Frustum[i][C] * (z - size) + m_Frustum[i][D] > 0)
continue;
if(m_Frustum[i][A] * (x + size) + m_Frustum[i][B] * (y - size) + m_Frustum[i][C] * (z - size) + m_Frustum[i][D] > 0)
continue;
if(m_Frustum[i][A] * (x - size) + m_Frustum[i][B] * (y + size) + m_Frustum[i][C] * (z - size) + m_Frustum[i][D] > 0)
continue;
if(m_Frustum[i][A] * (x + size) + m_Frustum[i][B] * (y + size) + m_Frustum[i][C] * (z - size) + m_Frustum[i][D] > 0)
continue;
if(m_Frustum[i][A] * (x - size) + m_Frustum[i][B] * (y - size) + m_Frustum[i][C] * (z + size) + m_Frustum[i][D] > 0)
continue;
if(m_Frustum[i][A] * (x + size) + m_Frustum[i][B] * (y - size) + m_Frustum[i][C] * (z + size) + m_Frustum[i][D] > 0)
continue;
if(m_Frustum[i][A] * (x - size) + m_Frustum[i][B] * (y + size) + m_Frustum[i][C] * (z + size) + m_Frustum[i][D] > 0)
continue;
if(m_Frustum[i][A] * (x + size) + m_Frustum[i][B] * (y + size) + m_Frustum[i][C] * (z + size) + m_Frustum[i][D] > 0)
continue;

// If we get here, it isn't in the frustum
return false;
}

return true;
}

now i want to change this so i can test for a rectange that has x,y,z size not just one radius that a cube has
does anyone know how to change the function to do this?
thanks

[This message has been edited by jono_123 (edited 01-15-2003).]

[This message has been edited by jono_123 (edited 01-18-2003).]

MickeyMouse
01-15-2003, 02:53 AM
Seems that you don't really understand how it works. I suppose you should replace size being next to x, y, z to size_x, size_y, size_z respectively.
BTW frustum test is not very cheap and the one you post here especially (6*8=32 dots).
A very well known optimization to that looks more or less like that:



bool TestBBox(const BBox_c &amp;BBox) const {
for (int i = 0; i < 6; i++) {
if (Planes[i].GetDistance(
Vec3_c((Planes[i].Normal[0] > 0) ? BBox.Min[0] : BBox.Max[0],
(Planes[i].Normal[1] > 0) ? BBox.Min[1] : BBox.Max[1],
(Planes[i].Normal[2] > 0) ? BBox.Min[2] : BBox.Max[2])) <= 0) {
return 0;
}
}
return 1;
}

So you have 6*1=6 dots:]

Hope it helps.

Luminous Blue
01-15-2003, 01:37 PM
Hello

is this what you need jono_123 ?

bool CFrustum::BoxInFrustum( const Vector3D *vmin, const Vector3D *vmax )
{
static int i=0;
for(i = 0; i < 6; i++)
{
if(m_Frustum[i][0] * vmin->x + m_Frustum[i][1] * vmin->y + m_Frustum[i][2] * vmin->z + m_Frustum[i][3] > 0)
continue;
if(m_Frustum[i][0] * vmax->x + m_Frustum[i][1] * vmin->y + m_Frustum[i][2] * vmin->z + m_Frustum[i][3] > 0)
continue;
if(m_Frustum[i][0] * vmin->x + m_Frustum[i][1] * vmax->y + m_Frustum[i][2] * vmin->z + m_Frustum[i][3] > 0) continue;
if(m_Frustum[i][0] * vmax->x + m_Frustum[i][1] * vmax->y + m_Frustum[i][2] * vmin->z + m_Frustum[i][3] > 0)
continue;
if(m_Frustum[i][0] * vmin->x + m_Frustum[i][1] * vmin->y + m_Frustum[i][2] * vmax->z + m_Frustum[i][3] > 0) continue;
if(m_Frustum[i][0] * vmax->x + m_Frustum[i][1] * vmin->y + m_Frustum[i][2] * vmax->z + m_Frustum[i][3] > 0)
continue;
if(m_Frustum[i][0] * vmin->x + m_Frustum[i][1] * vmax->y + m_Frustum[i][2] * vmax->z + m_Frustum[i][3] > 0)
continue;
if(m_Frustum[i][0] * vmax->x + m_Frustum[i][1] * vmax->y + m_Frustum[i][2] * vmax->z + m_Frustum[i][3] > 0)
continue;
// If we get here, it isn't in the frustum
return FALSE;
}
return TRUE;
}

MickeyMouse

please give me a tip (iam ill & my head hurts) ->Planes[i].GetDistance<- / ->Planes[i].Normal[0]<-

MickeyMouse
01-16-2003, 01:23 AM
I'm ill as well and have about 7 exams next week http://www.opengl.org/discussion_boards/ubb/frown.gif
Plane has normal vector and distance from origin.
Plane->GetDistance(point) returns (point dot plane_normal - plane_distance) - distance from plane to point

HamsterofDeath
01-17-2003, 02:40 AM
i dont understand how frustum culling works, but i know it's important to make it fast...

therefore, an idea :
it's a simlple calculation to test if a cube contacts another cube... now, what about taking the smallest cube that contains the frustum and calculating the frustum test with this box if the correct function is very mhz-expensive ?