Hi,
I'm trying to implement frustum culling on opengl ES. I have read online tutorials
http://www.crownandcutlass.com/features/technicaldetails/frustum.html
http://zach.in.tu-clausthal.de/teaching/cg_literatur/lighthouse3d_view_frustum_culling/index.html
and it looks straightforward. But has you can see on the video capture, it does not work well.
http://www.screencast.com/t/e6L2JYJapzb
Here is my build planes function:
void CFrustum::BuildPlanes( const mat4& ModelView, const mat4& Proj )
{
mat4 clip, modl = ModelView, proj = Proj;
float t = 0;
clip[ 0] = modl[ 0] * proj[ 0] + modl[ 1] * proj[ 4] + modl[ 2] * proj[ 8] + modl[ 3] * proj[12];
clip[ 1] = modl[ 0] * proj[ 1] + modl[ 1] * proj[ 5] + modl[ 2] * proj[ 9] + modl[ 3] * proj[13];
clip[ 2] = modl[ 0] * proj[ 2] + modl[ 1] * proj[ 6] + modl[ 2] * proj[10] + modl[ 3] * proj[14];
clip[ 3] = modl[ 0] * proj[ 3] + modl[ 1] * proj[ 7] + modl[ 2] * proj[11] + modl[ 3] * proj[15];
clip[ 4] = modl[ 4] * proj[ 0] + modl[ 5] * proj[ 4] + modl[ 6] * proj[ 8] + modl[ 7] * proj[12];
clip[ 5] = modl[ 4] * proj[ 1] + modl[ 5] * proj[ 5] + modl[ 6] * proj[ 9] + modl[ 7] * proj[13];
clip[ 6] = modl[ 4] * proj[ 2] + modl[ 5] * proj[ 6] + modl[ 6] * proj[10] + modl[ 7] * proj[14];
clip[ 7] = modl[ 4] * proj[ 3] + modl[ 5] * proj[ 7] + modl[ 6] * proj[11] + modl[ 7] * proj[15];
clip[ 8] = modl[ 8] * proj[ 0] + modl[ 9] * proj[ 4] + modl[10] * proj[ 8] + modl[11] * proj[12];
clip[ 9] = modl[ 8] * proj[ 1] + modl[ 9] * proj[ 5] + modl[10] * proj[ 9] + modl[11] * proj[13];
clip[10] = modl[ 8] * proj[ 2] + modl[ 9] * proj[ 6] + modl[10] * proj[10] + modl[11] * proj[14];
clip[11] = modl[ 8] * proj[ 3] + modl[ 9] * proj[ 7] + modl[10] * proj[11] + modl[11] * proj[15];
clip[12] = modl[12] * proj[ 0] + modl[13] * proj[ 4] + modl[14] * proj[ 8] + modl[15] * proj[12];
clip[13] = modl[12] * proj[ 1] + modl[13] * proj[ 5] + modl[14] * proj[ 9] + modl[15] * proj[13];
clip[14] = modl[12] * proj[ 2] + modl[13] * proj[ 6] + modl[14] * proj[10] + modl[15] * proj[14];
clip[15] = modl[12] * proj[ 3] + modl[13] * proj[ 7] + modl[14] * proj[11] + modl[15] * proj[15];
/* Extract the numbers for the RIGHT plane */
vPlanes[0][0] = clip[ 3] - clip[ 0];
vPlanes[0][1] = clip[ 7] - clip[ 4];
vPlanes[0][2] = clip[11] - clip[ 8];
vPlanes[0][3] = clip[15] - clip[12];
/* Normalize the result */
t = sqrt( vPlanes[0][0] * vPlanes[0][0] + vPlanes[0][1] * vPlanes[0][1] + vPlanes[0][2] * vPlanes[0][2] );
vPlanes[0][0] /= t;
vPlanes[0][1] /= t;
vPlanes[0][2] /= t;
vPlanes[0][3] /= t;
/* Extract the numbers for the LEFT plane */
vPlanes[1][0] = clip[ 3] + clip[ 0];
vPlanes[1][1] = clip[ 7] + clip[ 4];
vPlanes[1][2] = clip[11] + clip[ 8];
vPlanes[1][3] = clip[15] + clip[12];
/* Normalize the result */
t = sqrt( vPlanes[1][0] * vPlanes[1][0] + vPlanes[1][1] * vPlanes[1][1] + vPlanes[1][2] * vPlanes[1][2] );
vPlanes[1][0] /= t;
vPlanes[1][1] /= t;
vPlanes[1][2] /= t;
vPlanes[1][3] /= t;
/* Extract the BOTTOM plane */
vPlanes[2][0] = clip[ 3] + clip[ 1];
vPlanes[2][1] = clip[ 7] + clip[ 5];
vPlanes[2][2] = clip[11] + clip[ 9];
vPlanes[2][3] = clip[15] + clip[13];
/* Normalize the result */
t = sqrt( vPlanes[2][0] * vPlanes[2][0] + vPlanes[2][1] * vPlanes[2][1] + vPlanes[2][2] * vPlanes[2][2] );
vPlanes[2][0] /= t;
vPlanes[2][1] /= t;
vPlanes[2][2] /= t;
vPlanes[2][3] /= t;
/* Extract the TOP plane */
vPlanes[3][0] = clip[ 3] - clip[ 1];
vPlanes[3][1] = clip[ 7] - clip[ 5];
vPlanes[3][2] = clip[11] - clip[ 9];
vPlanes[3][3] = clip[15] - clip[13];
/* Normalize the result */
t = sqrt( vPlanes[3][0] * vPlanes[3][0] + vPlanes[3][1] * vPlanes[3][1] + vPlanes[3][2] * vPlanes[3][2] );
vPlanes[3][0] /= t;
vPlanes[3][1] /= t;
vPlanes[3][2] /= t;
vPlanes[3][3] /= t;
/* Extract the FAR plane */
vPlanes[4][0] = clip[ 3] - clip[ 2];
vPlanes[4][1] = clip[ 7] - clip[ 6];
vPlanes[4][2] = clip[11] - clip[10];
vPlanes[4][3] = clip[15] - clip[14];
/* Normalize the result */
t = sqrt( vPlanes[4][0] * vPlanes[4][0] + vPlanes[4][1] * vPlanes[4][1] + vPlanes[4][2] * vPlanes[4][2] );
vPlanes[4][0] /= t;
vPlanes[4][1] /= t;
vPlanes[4][2] /= t;
vPlanes[4][3] /= t;
/* Extract the NEAR plane */
vPlanes[5][0] = clip[ 3] + clip[ 2];
vPlanes[5][1] = clip[ 7] + clip[ 6];
vPlanes[5][2] = clip[11] + clip[10];
vPlanes[5][3] = clip[15] + clip[14];
/* Normalize the result */
t = sqrt( vPlanes[5][0] * vPlanes[5][0] + vPlanes[5][1] * vPlanes[5][1] + vPlanes[5][2] * vPlanes[5][2] );
vPlanes[5][0] /= t;
vPlanes[5][1] /= t;
vPlanes[5][2] /= t;
vPlanes[5][3] /= t;
}
The camera is a simple FPS cam, that uses produces lookat matrix for ( Pos, Up, Forward ).
I use this function to check the sphere collision with the frustum
int CFrustum::SphereInFrustum( float x, float y, float z, float radius )
{
int p;
int c = 0;
float d;
for( p = 0; p < NUM_PLANES; p++ )
{
d = vPlanes[p][0] * x + vPlanes[p][1] * x + vPlanes[p][2] * z + vPlanes[p][3];
if( d <= -radius )
return 0;
if( d > radius )
c++;
}
return (c == 6) ? 2 : 1;
}
What I'm doing wrong? it is all seems to be the same as the tutorials.
Edited by masterbubu, 15 March 2013 - 04:01 AM.






