Need help with gluUnproject

Hi all, heres my problem.

When I call gluProject in my application, it returns the correct window values perfectly. However, when I call gluUnproject, the results are completely wrong.

When I call gluGetScreenLocation(-1, -2, -2, &sx, &sy, &sz), the values returned are

x:  216.362305  y:  391.235901  z: 10.285913 

These values are correct and work perfectly.

However, when I call gluGetOpenGLLocation(216.362305, 391.235901, 10.285913, &sx, &sy, &sz), the values returned are

x:  0.001047    y:  5.002304    z:  -10.010890

But it should return -1,-2,-2. Any ideas?


void gluGetScreenLocation(GLfloat xa, GLfloat ya, GLfloat za, GLfloat *sx, GLfloat *sy, GLfloat *sz)
{
    GLfloat mvmatrix[16];
    GLfloat projmatrix[16];
    GLfloat x,y,z;
    GLint viewport[4];
	
    glGetIntegerv(GL_VIEWPORT, viewport);
    glGetFloatv(GL_MODELVIEW_MATRIX, mvmatrix);
    glGetFloatv(GL_PROJECTION_MATRIX, projmatrix);
	
    gluProject(xa, ya, za, mvmatrix, projmatrix, viewport, &x, &y, &z);
	
    y = viewport[3] - y;
    
    *sx = x;
    *sy = y;
    
    if (sz != NULL)
        *sz=z;
}

void gluGetOpenGLLocation(GLfloat xa, GLfloat ya, GLfloat za, GLfloat *sx, GLfloat *sy, GLfloat *sz)
{
    GLfloat mvmatrix[16];
    GLfloat projmatrix[16];
    GLfloat x, y, z;
    GLint viewport[4];
	
    glGetIntegerv(GL_VIEWPORT,viewport);
    glGetFloatv(GL_MODELVIEW_MATRIX,mvmatrix);
    glGetFloatv(GL_PROJECTION_MATRIX,projmatrix);
    
    gluUnProject(xa, ya, za, mvmatrix, projmatrix, viewport, &x, &y, &z);
    
    y = viewport[3] - y; // subtract Y coordinate from screen height
    
    *sx = x;
    *sy = y;
    
    glReadPixels(xa, viewport[3] - ya, 1, 1, GL_DEPTH_COMPONENT, GL_FLOAT, &sz); // get z component via depth buffer
}

gluUnproject is higly dependent on the z-buffer. Keep you near and far values as close to each outer as possible to maximize the z-buffer range.
I find gluUnproject is only good for coarse picking. For fine picking you need other methods like object search around the pick point or a second buffer with world x,y,z stored in some form as a fragment is rendered