planar shadow projection doesn't work for me :(

Hi everyone,

I try to make shadow cast of an object. I started with a simple element of the shadow casting method - trying to draw the objects projection on a plane. But something is going wrong. The scene is total mess with arbitrary directed planes stretching to infinity which obviously is not expected.


//Here is my code that retrieves the shadow matrix:
void shadowMatrix(GLfloat m[][4],
                  GLfloat plane[],
                  GLfloat light[])
{
    GLfloat dot = plane[0]*light[0] + plane[1]*light[1] +
                  plane[2]*light[2] + plane[3]*light[3];
    m[0][0] = dot - light[0]*plane[0];
    m[1][0] = - light[0]*plane[1];
    m[2][0] = - light[0]*plane[2];
    m[3][0] = - light[0]*plane[3];
    m[0][1] = - light[1]*plane[0];
    m[1][1] = dot - light[1]*plane[1];
    m[2][1] = - light[1]*plane[2];
    m[3][1] = - light[1]*plane[3];
    m[0][2] = - light[2]*plane[0];
    m[1][2] = - light[2]*plane[1];
    m[2][2] = dot - light[2]*plane[2];
    m[3][2] = - light[2]*plane[3];
    m[0][3] = - light[3]*plane[0];
    m[1][3] = - light[3]*plane[1];
    m[2][3] = - light[3]*plane[2];
    m[3][3] = dot - light[3]*plane[3];
}


//And here is the code that draws the scene
void drawScene() {
	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
	
	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();
	
	glTranslatef(0.0f, 0.0f, -20.0f);
	
	GLfloat ambientLight[] = {0.3f, 0.3f, 0.3f, 1.0f};
	glLightModelfv(GL_LIGHT_MODEL_AMBIENT, ambientLight);
	
	GLfloat lightColor[] = {1.0f, 1.0f, 1.0f, 1.0f};
	GLfloat lightPos[] = {-2 * BOX_SIZE, BOX_SIZE, 4 * BOX_SIZE, 1.0f};
	glLightfv(GL_LIGHT0, GL_DIFFUSE, lightColor);
	glLightfv(GL_LIGHT0, GL_POSITION, lightPos);
	
    //glRotatef(20, 1.0, 0.0, 0.0);

    glPushMatrix();
    GLfloat matrix [4][4];
    GLfloat groundPlaneEquation[4] = { 0.0, 1.0, 0.0,  BOX_SIZE/2};

    // Compute matrix based on light position and ground plane
    // equation. See Appendix B.
    shadowMatrix(matrix, lightPos, groundPlaneEquation);
    glMultMatrixf(&matrix[0][0]);

    drawCube();
    //drawPlane();
	glPopMatrix();

	glutSwapBuffers();
}

Any help will be appreciated. Thanx

oh my goodnes. How stupid am I. I ve swaped the places of lightPos and groundPlaneEquation arguments of shadowMatrix function:

shadowMatrix(matrix, lightPos, groundPlaneEquation);

Here again is the prototype:
void shadowMatrix(GLfloat m[][4],
GLfloat plane[],
GLfloat light[])

Hi again. Here is another problem. Im suspisious about my stencil buffer. I thing it doesen’t work properly. In order to test it I do the folowing steps. So I draw a cube on a quadric plane with the following code:


void drawScene() {
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
	
    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();
	
    glTranslatef(0.0f, 0.0f, -20.0f);
    glRotatef(20.0, 1.0, 0.0, 0.0);

    drawCube();
    drawPlane();

    glutSwapBuffers();
}

After that I add some code to test if the stencil buffer works properly. The test consists of drawing the cube. Then drawing the plane with enabled depth test and tagging those pixels that belong to the cube. After disabling the depth test and redrawing the plane using some stensil buffering to skip rendering of tagged pixels I expect to have the same scene obtained with the code above but I dont. Instead, the redrawn plane just cover all the scene. Here is the test code issued from the code above.


void drawScene() {

    glClearStencil(0);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
    
    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();
	
    glTranslatef(0.0f, 0.0f, -20.0f);
    glRotatef(20.0, 1.0, 0.0, 0.0);
	
    drawCube();

    glEnable(GL_STENCIL_TEST);
    glStencilFunc(GL_ALWAYS, (GLbyte)64, ~0);
    glStencilOp(GL_KEEP, GL_REPLACE, GL_KEEP);
    drawPlane();
    glDisable(GL_STENCIL_TEST);

    glEnable(GL_STENCIL_TEST);
    glDisable(GL_DEPTH_TEST);
    glStencilFunc(GL_NOTEQUAL, (GLbyte)64, ~0);
    glStencilOp(GL_KEEP, GL_KEEP, GL_INCR);
    drawPlane();
    glDisable(GL_STENCIL_TEST);
    glEnable(GL_DEPTH_TEST);

    glutSwapBuffers();
}

So I found out again where the problem is. In main funcion i call
glutInitDisplayMode without GLUT_STENCIL mask. After adding it everithing is OK.


glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH | GLUT_STENCIL)