Jump to content
  • Advertisement
Sign in to follow this  
akaitora

OpenGL Corrupted Vertex Buffer

This topic is 1034 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hi!  I am  trying to render 2 vertex buffers.  Each is setup a bit different.  The first only has positions whereas the second has both positions and uv coordinates.  If I only try to render one, the one I render looks great.  It doesn't matter which I render.  But if I render both together,  both vertex buffer become corrupt.  On screen, they both look like triangles even though they are suppose to be quads.  When I try making both use the same vertex format,  (I.E. verts and uvs) they render correctly.  This almost makes me think that they are somehow referencing each other somehow which is breaking the stride.  I am not explicitly unbinding my VBOs.  According to the OpenGL docs, I shouldn't need to.  However even when I do, it causes a crash.  Below are the classes for the 2 VBOs in question.

 

#include "QuadGeometry.h"
 
#include <iostream>
using namespace std;
 
const float QuadGeometry::verts[] =
{
    -1.0f, 1.0f, 0.0f,
    -1.0f, -1.0f, 0.0f,
    1.0f, -1.0f, 0.0f,
    -1.0f, 1.0f, 0.0f,
    1.0, 1.0, 0.0f
};
 
//---------------------------------------------------------------------
void QuadGeometry::Initialize()
{
    glGenBuffers(1, &vertexBuffer);
    glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
    glBufferData(GL_ARRAY_BUFFER, sizeof(verts), verts, GL_STATIC_DRAW);
}
 
//---------------------------------------------------------------------
void QuadGeometry::Render()
{
    glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
    glDrawArrays(GL_TRIANGLE_STRIP, 0, 5);
}

 

 

//---------------------------------------------------------------------
DisplayText::DisplayText()
{
    shaderFx = new ShaderFx();
    shaderFx->Load( "shaders/font/vertex.glsl", "shaders/font/fragment.glsl", true );
    
    vertexBuffer = 0;
    
    textureSurface = nullptr;
    textureSurface = SDL_LoadBMP("assets/textures/ddrsmall.bmp");
    if( !textureSurface )
    {
        cout<< "Failed to Load Texture!\n";
    }
    
    /*
    glGenTextures(1, &textureId);
    glBindTexture(GL_TEXTURE_2D, textureId);
    
    glTexImage2D(GL_TEXTURE_2D , 0 , 3 , textureSurface->w,
                 textureSurface->h , 0 , GL_RGB , GL_UNSIGNED_BYTE ,
                 textureSurface->pixels);
    
    glTexParameteri(GL_TEXTURE_2D , GL_TEXTURE_MIN_FILTER , GL_LINEAR);
    glTexParameteri(GL_TEXTURE_2D , GL_TEXTURE_MAG_FILTER , GL_LINEAR);
    */
}
 
//---------------------------------------------------------------------
void DisplayText::CreateNewVertexBuffer()
{
    float verts[] =
    {
        //x    //y    //z   //u   //v
        -1.0f,  1.0f,  0.0f, 0.0,  1.0,
        -1.0f, -1.0f,  0.0f, 0.0,  0.0,
         1.0f, -1.0f,  0.0f, 1.0,  0.0,
        -1.0f,  1.0f,  0.0f, 0.0,  1.0,
         1.0f,  1.0f,  0.0f, 1.0,  1.0
    };
    
    glGenBuffers(1, &vertexBuffer);
    glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
    glBufferData(GL_ARRAY_BUFFER, sizeof(verts), verts, GL_STATIC_DRAW);
}
 
 
//---------------------------------------------------------------------
void DisplayText::DrawString(std::string string, int x, int y)
{
    if( vertexBuffer <= 0 )
    {
        CreateNewVertexBuffer();
    }
    
    shaderFx->BeginPass();
    
    glm::mat4 Projection = glm::perspective(45.0f, 800.0f/600.0f, 0.1f, 1000.f);
    glm::mat4 View = glm::translate(glm::mat4(1.0f), glm::vec3(0.0f, 0.0f, -7.0f));
    glm::mat4 Model = glm::scale(glm::mat4(1.0f), glm::vec3(1.0f));
    glm::mat4 modelViewMat = View * Model;
    
    shaderFx->SetMatrix4x4Parameter("modelViewMatrix", &modelViewMat[0][0]);
    shaderFx->SetMatrix4x4Parameter("projectionMatrix", &Projection[0][0]);
    
    glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
    glDrawArrays(GL_TRIANGLE_STRIP, 0, 5);
    
    shaderFx->EndPass();
    
    oldString = string;
}

 

Any ideas would be helpful!  Thanks!

Share this post


Link to post
Share on other sites
Advertisement

In one of them, you are binding a shader. In the other, it doesn't look like you are, so the same bound shader is getting used by both of them. If the shader is expecting UVs and positions, and you are only passing it positions, then it might be messing things up.

 

If you bind one shader, you can't unbind it and expect to be able to render something else correctly without binding a new one.

Share this post


Link to post
Share on other sites

Good catch!  Unfortunately I forgot to mention that I am handing the shader for the QuadGeom in a higher level class like so.

 

 
void onRenderImage(ApplicationContext &context)
{
    glClearColor(0.0, 0.3, 0, 1);
    glEnable(GL_DEPTH_TEST);
    
    glViewport(0, 0, context.ResolutionWidth, context.ResolutionHeight);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    
    context.ShaderFx->BeginPass();
    
    context.ShaderFx->SetVector2Parameter("resolution", context.ResolutionWidth, context.ResolutionHeight);
    
    context.ShaderFx->SetFloatParameter("time", context.TimeInSecondsSinceStartup);
    
    
    float mouseX = (float)((context.MouseX - context.WindowPosX)) / context.ResolutionWidth;
    float mouseY = (float)(-(context.MouseY - context.WindowPosY)) / context.ResolutionHeight;
    
    context.ShaderFx->SetVector2Parameter("mouse", mouseX, mouseY);
    
    context.QuadGeo->Render();
    
    context.ShaderFx->EndPass();
    
    glDisable(GL_DEPTH_TEST);
    context.DisplayText->DrawString("", 0, 0);
}
 

 

Any other ideas?  Thanks!

Share this post


Link to post
Share on other sites

btw, for my Begin/End shader code,  I am doing the following

 

 
//---------------------------------------------------------------------
void ShaderFx::BeginPass()
{
    glUseProgram(shaderProgram);
    
    if( !modelHasUvs )
    {
        GLint vertexAttribLocation = glGetAttribLocation(shaderProgram, "vertex");
        glEnableVertexAttribArray(vertexAttribLocation);
        glVertexAttribPointer(vertexAttribLocation, 3, GL_FLOAT, GL_FALSE, 0, 0);
    }
    else
    {
        
        GLint vertexAttribLocation = glGetAttribLocation(shaderProgram, "vertex");
        glEnableVertexAttribArray(vertexAttribLocation);
        glVertexAttribPointer(vertexAttribLocation, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(GLfloat), 0);
        
        GLuint texCoordAttribLocation = glGetAttribLocation(shaderProgram, "uv");
        glEnableVertexAttribArray(texCoordAttribLocation);
        glVertexAttribPointer(texCoordAttribLocation, 2, GL_FLOAT, GL_FALSE, 5 * sizeof(GLfloat), (const GLvoid*)(3 * sizeof(GLfloat)));
        
    }
}
 
//---------------------------------------------------------------------
void ShaderFx::EndPass()
{
    GLint vertexAttribLocation = glGetAttribLocation(shaderProgram, "vertex");
    GLuint texCoordAttribLocation = glGetAttribLocation(shaderProgram, "uv");
    
    glDisableVertexAttribArray(vertexAttribLocation);
    glDisableVertexAttribArray(texCoordAttribLocation);
}
 

Share this post


Link to post
Share on other sites

Nothing stands out to me.

 

You're saying that if you draw just the Position triangle-pair, it looks fine.

And if you draw just the UV+Position triangle-pair, it looks fine.

 

Have you tried drawing two Position triangle-pairs in different locations, with no UV+Position pair?

That might help narrow it down.

 

Someone else might have a better idea.

Share this post


Link to post
Share on other sites

Your glVertexAttribPointer calls depend on the currently bound buffer object.  So you must therefore call glBindBuffer before you call glVertexAttribPointer; you're calling them the in the wrong order so hence things get messed-up.

Share this post


Link to post
Share on other sites

mhagain, thanks for the solution!  That fixed it!  I didn't realized that glVertexAttribPointer required the buffer to be bound before use.  Thanks for the heads up!

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!