Part of the Khronos Group
OpenGL.org

The Industry's Foundation for High Performance Graphics

from games to virtual reality, mobile phones to supercomputers

Page 1 of 2 12 LastLast
Results 1 to 10 of 12

Thread: Weird Depth Testing?

  1. #1

    Weird Depth Testing?

    Using OpenGL 4.4 and GLSL,

    I have an icosahedron at position (0, 0, 0) and a plane at height = 1 with camera at (0, 2, 0). The depth testing seems to be backwards. Don't know what to do. When I flip the depth test to GREATER, nothing draws.

    ...
    glClearColor(0.0f, 0.0f, 0.0f, 0.0f);

    glEnable(GL_CULL_FACE);
    glCullFace(GL_BACK);
    glFrontFace(GL_CW);

    glEnable(GL_DEPTH_TEST);
    glDepthFunc(GL_LESS);
    glEnable(GL_DEPTH_CLAMP);

    glEnable(GL_TEXTURE_2D);
    ...


    Click image for larger version. 

Name:	ico.jpg 
Views:	195 
Size:	5.1 KB 
ID:	1521


    Any thoughts?
    Last edited by ParagonArcade; 12-01-2014 at 10:49 PM.

  2. #2
    Junior Member Regular Contributor uwi2k2's Avatar
    Join Date
    Mar 2011
    Posts
    138
    hi,

    if you set glFrontFace to CW
    and cull BACK you normaly see the inside of something ... assuming your data is normal vertex order ..

    cu
    kai
    uwi2k2 - OpenGL Trainer: www.opengl-trainer.com
    ---------------------------------------------------------
    The OpenGL and VULKAN Podcast ( OpenGL2GO ) : OpenGL & Vulkan Podcast
    ---------------------------------------------------------
    timbling.com - Indie TeamUp

  3. #3
    For some reason I thought I tried this and it didn't work. I went back and wrote a function which inverts the normals of my object and its fixed. Thanks!

  4. #4
    Quote Originally Posted by ParagonArcade View Post
    For some reason I thought I tried this and it didn't work. I went back and wrote a function which inverts the normals of my object and its fixed. Thanks!
    Maybe I spoke too soon. It's still doing it. The hallway on the right should be hidden by the wall. Its not being clipped either. It's the depth.

    Code :
    glEnable(GL_CULL_FACE);
    glCullFace(GL_BACK);
    glFrontFace(GL_CCW);
     
    glEnable(GL_DEPTH_TEST);
    glDepthFunc(GL_LESS);
    glEnable(GL_DEPTH_CLAMP);
     
    glEnable(GL_TEXTURE_2D);
     
    ...
     
    createScreen("PARAGON 3D", false, 1366, 768, 1.0f, 1000.0f);
     
    ...
     
    zNear = 1.0f;
    zFar = 1000.0f;
     
    ...
     
    Matrix4f Matrix4f::initProjection(float left, float right, float bottom, float top, float zNear, float zFar)
    {
    	float width = right - left;
    	float height = top - bottom;
    	float depth = zNear - zFar;
     
    	m[0][0] = (2 * zNear) / width;			m[0][1] = 0;						m[0][2] = (right + left) / width;			m[0][3] = 0;
    	m[1][0] = 0;					m[1][1] = (2 * zNear) / height;				m[1][2] = (top + bottom) / height;			m[1][3] = 0;
    	m[2][0] = 0;					m[2][1] = 0;						m[2][2] = (-1.0f * zFar + zNear) / depth;		m[2][3] = (-2.0f * zFar * zNear) / depth;
    	m[3][0] = 0;					m[3][1] = 0;						m[3][2] = -1.0f;					m[3][3] = 0;
     
    	return *this;
    }
     
    ...
     
    void Level::generateLeft(int i, int j)
    {
    	int size = mesh->getNumOfVertices();
     
    	mesh->addElement(size + 0); mesh->addElement(size + 1); mesh->addElement(size + 2);
    	mesh->addElement(size + 0); mesh->addElement(size + 2); mesh->addElement(size + 3);
     
    	int halfWidth = level->getWidth() / 2;
    	int halfHeight = level->getHeight() / 2;
     
    	//Left Plane
    	mesh->addVertex(Vertex(Vector3f((i - halfWidth - 0.5) * SPOT_W, SPOT_H, (j - halfHeight + 0.5) * SPOT_L), Vector3f(1, 1, 1), Vector3f(1, 0, 0), Vector2f(0, 0)));
    	mesh->addVertex(Vertex(Vector3f((i - halfWidth - 0.5) * SPOT_W, 0.0f, (j - halfHeight + 0.5) * SPOT_L), Vector3f(1, 1, 1), Vector3f(1, 0, 0), Vector2f(1, 0)));
    	mesh->addVertex(Vertex(Vector3f((i - halfWidth - 0.5) * SPOT_W, 0.0f, (j - halfHeight - 0.5) * SPOT_L), Vector3f(1, 1, 1), Vector3f(1, 0, 0), Vector2f(1, 1)));
    	mesh->addVertex(Vertex(Vector3f((i - halfWidth - 0.5) * SPOT_W, SPOT_H, (j - halfHeight - 0.5) * SPOT_L), Vector3f(1, 1, 1), Vector3f(1, 0, 0), Vector2f(0, 1)));
    }

    Click image for larger version. 

Name:	depth.jpg 
Views:	178 
Size:	18.1 KB 
ID:	1532

  5. #5
    Senior Member OpenGL Guru
    Join Date
    Jun 2013
    Posts
    2,926
    Quote Originally Posted by ParagonArcade View Post
    Code :
    Matrix4f Matrix4f::initProjection(float left, float right, float bottom, float top, float zNear, float zFar)
    {
    	float width = right - left;
    	float height = top - bottom;
    	float depth = zNear - zFar;
     
    	m[0][0] = (2 * zNear) / width;	m[0][1] = 0;			m[0][2] = (right + left) / width;		m[0][3] = 0;
    	m[1][0] = 0;			m[1][1] = (2 * zNear) / height;	m[1][2] = (top + bottom) / height;		m[1][3] = 0;
    	m[2][0] = 0;			m[2][1] = 0;			m[2][2] = (-1.0f * zFar + zNear) / depth;	m[2][3] = (-2.0f * zFar * zNear) / depth;
    	m[3][0] = 0;			m[3][1] = 0;			m[3][2] = -1.0f;				m[3][3] = 0;
     
    	return *this;
    }
    If this is supposed to behave like glFrustum, m[2][2] and m[2][3] are wrong. They should be
    Code :
    m[2][2] = (zFar + zNear) / depth;	m[2][3] = (2.0f * zFar * zNear) / depth;
    The minus signs which appear in the glFrustum manual page are absent because your depth has the opposite sign to the denominator there.

    If you're trying to construct a left-handed coordinate system for eye space (with the view direction along the positive Z axis rather than the negative Z axis), all 4 of the entries in column 2 (i.e. m[...][2]) need to be negated.

    Also, your matrix is in row-major order, so it needs to be transposed (e.g. by setting transpose=GL_TRUE when calling glUniformMatrix4f).

  6. #6
    Quote Originally Posted by GClements View Post
    If this is supposed to behave like glFrustum, m[2][2] and m[2][3] are wrong. They should be
    Code :
    m[2][2] = (zFar + zNear) / depth;	m[2][3] = (2.0f * zFar * zNear) / depth;
    The minus signs which appear in the glFrustum manual page are absent because your depth has the opposite sign to the denominator there.

    If you're trying to construct a left-handed coordinate system for eye space (with the view direction along the positive Z axis rather than the negative Z axis), all 4 of the entries in column 2 (i.e. m[...][2]) need to be negated.

    Also, your matrix is in row-major order, so it needs to be transposed (e.g. by setting transpose=GL_TRUE when calling glUniformMatrix4f).
    Thank you for the response. I am piece-ing this all together from a youtube series which a great guide, but little changes are made which arent referenced I believe.

    I corrected the code to the following and the depth testing works.

    Code :
    Matrix4f Matrix4f::initProjection(float left, float right, float bottom, float top, float zNear, float zFar)
    {
    	float width = right - left;
    	float height = top - bottom;
    	float depth = zNear - zFar;
     
    	m[0][0] = (2 * zNear) / width;			m[0][1] = 0;						m[0][2] = (right + left) / width;			m[0][3] = 0;
    	m[1][0] = 0;					m[1][1] = (2 * zNear) / height;				m[1][2] = (top + bottom) / height;			m[1][3] = 0;
    	m[2][0] = 0;					m[2][1] = 0;						m[2][2] = (1.0f * zFar + zNear) / depth;		m[2][3] = (2.0f * zFar * zNear) / depth;
    	m[3][0] = 0;					m[3][1] = 0;						m[3][2] = -1.0f;					m[3][3] = 0;
     
    	return *this;
    }

    I want to create a right-handed system, so the right-hand rule applies, +i cross +j = +k; Will I need to transpose from row-major order no matter what? Or just for a left or right handed system?

  7. #7
    Senior Member OpenGL Guru
    Join Date
    Jun 2013
    Posts
    2,926
    Quote Originally Posted by ParagonArcade View Post
    I want to create a right-handed system, so the right-hand rule applies, +i cross +j = +k; Will I need to transpose from row-major order no matter what? Or just for a left or right handed system?
    The updated matrix matches that generated by glFrustum(), which results in eye-space being a right-handed coordinate system ("forward" is along the negative Z axis).

    Regardless of left- or right-handed coordinate system, you need to either pass the matrix to OpenGL in column-major order (i.e. m[0][0] is followed by m[1][0] in memory) or have OpenGL transpose the matrix.

  8. #8
    Quote Originally Posted by GClements View Post
    The updated matrix matches that generated by glFrustum(), which results in eye-space being a right-handed coordinate system ("forward" is along the negative Z axis).

    Regardless of left- or right-handed coordinate system, you need to either pass the matrix to OpenGL in column-major order (i.e. m[0][0] is followed by m[1][0] in memory) or have OpenGL transpose the matrix.
    When I transposed the matrix, everything broke. What else would I need to change to get back to normal? Transpose all my other matrices? If so, what advantage to I gain?

    Here is how I am passing the Matrix4f to the GLSL as a mat4 uniform as a float array.

    Code :
    float* Matrix4f::getFloats()
    {
    	float* mat4x4 = new float[16];
     
    	for (int k = 0; k < 16; k++)
    	{
    		int i = k % 4;
    		int j = floor(k / 4);
     
    		mat4x4[k] = m[i][j];
    	}
     
    	return mat4x4;
    }

    Also, is there a limitation on the maximum amount of Uniforms one can send?

    I think I might have reached the maximum or something. When I try to set a new "int" uniform, I lose some of my point lights, like the uniform data is corrupt.

  9. #9
    Senior Member OpenGL Guru
    Join Date
    Jun 2013
    Posts
    2,926
    Quote Originally Posted by ParagonArcade View Post
    Code :
    float* Matrix4f::getFloats()
    {
    	float* mat4x4 = new float[16];
     
    	for (int k = 0; k < 16; k++)
    	{
    		int i = k % 4;
    		int j = floor(k / 4);
     
    		mat4x4[k] = m[i][j];
    	}
     
    	return mat4x4;
    }
    That's returning the matrix in column-major order, which is what OpenGL wants. If you were just casting m to a float* then it would be in row-major order and need to be transposed.

    BTW, there's no need for the floor() in the above code; In C and C++, dividing two integers produces an integer result (any fractional part is discarded, i.e. the result is rounded toward zero).

    Quote Originally Posted by ParagonArcade View Post
    Also, is there a limitation on the maximum amount of Uniforms one can send?
    It depends upon the implementation. There is a required minimum value which depends upon the OpenGL version. You're guaranteed at least 16 vectors in the fragment shader and 128 vectors in the vertex shader. OpenGL 3 increased this to at least 256 vectors in each shader.

    The actual values can be queried with glGetIntegerv().

  10. #10
    Quote Originally Posted by GClements View Post
    That's returning the matrix in column-major order, which is what OpenGL wants. If you were just casting m to a float* then it would be in row-major order and need to be transposed.
    I once again went back and tried to visually transpose all my of matrices just for convenience. I wrote all of them out beforehand and then commented out the original ones. All the Matrix4f functions look correct, triple checked, but it only sorta worked cause my quaternion rotation system broke on my camera, translation works, projection works too, objects don't change sizes from improper matrices multiplication. For now I switched it back cause I need it to work right now. Any ideas what could be mixing me up?

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •