Matrix VBO未被顶点着色器

时间:2017-04-20 15:55:37

标签: c++ opengl

所以我的顶点着色器需要3个glm :: mat4对象才能在正确的位置渲染。我正在逐个绘制每个模型,每个渲染均匀矩阵,但绘制调用的数量开始减慢我的帧速率。所以我改为使用3 matrix4 vbo。现在一切都在编译,我可以看到我的一些对象,但是我的矩阵没有传播到着色器。如果有人能的话,我会喜欢这方面的帮助。我的代码如下,

常数

static enum BUFFERS {
        VERTEX_BUFFER, TEXCOORD_BUFFER, NORMAL_BUFFER, INDEX_BUFFER, 
        MVP_MAT_VB, MODELVIEW_MAT_VB, NORMAL_MAT_VB
    };
#define POSITION_LOCATION 0
#define TEX_COORD_LOCATION 1
#define NORMAL_LOCATION 2
#define MVP_LOCATION 3
#define MODEL_VIEW_LOCATION 7
#define NORMAL_MATRIX_LOCATION 11

创建实例vbos

MeshEntry::MeshEntry(aiMesh *mesh) {
    vbo[VERTEX_BUFFER] = NULL;
vbo[TEXCOORD_BUFFER] = NULL;
vbo[NORMAL_BUFFER] = NULL;
vbo[INDEX_BUFFER] = NULL;
vbo[MODELVIEW_MAT_VB] = NULL;
vbo[MVP_MAT_VB] = NULL;
vbo[NORMAL_MAT_VB] = NULL;

glGenVertexArrays(1, &vao);
glBindVertexArray(vao);

elementCount = mesh->mNumFaces * 3;

if (mesh->HasPositions()) {
    float *vertices = new float[mesh->mNumVertices * 3];
    for (int i = 0; i < mesh->mNumVertices; ++i) {
        vertices[i * 3] = mesh->mVertices[i].x;
        vertices[i * 3 + 1] = mesh->mVertices[i].y;
        vertices[i * 3 + 2] = mesh->mVertices[i].z;
    }

    glGenBuffers(1, &vbo[VERTEX_BUFFER]);
    glBindBuffer(GL_ARRAY_BUFFER, vbo[VERTEX_BUFFER]);
    glBufferData(GL_ARRAY_BUFFER, 3 * mesh->mNumVertices * sizeof(GLfloat), vertices, GL_STATIC_DRAW);

    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, NULL);
    glEnableVertexAttribArray(0);

    delete vertices;
}


if (mesh->HasTextureCoords(0)) {
    float *texCoords = new float[mesh->mNumVertices * 2];
    for (int i = 0; i < mesh->mNumVertices; ++i) {
        texCoords[i * 2] = mesh->mTextureCoords[0][i].x;
        texCoords[i * 2 + 1] = mesh->mTextureCoords[0][i].y;
    }

    glGenBuffers(1, &vbo[TEXCOORD_BUFFER]);
    glBindBuffer(GL_ARRAY_BUFFER, vbo[TEXCOORD_BUFFER]);
    glBufferData(GL_ARRAY_BUFFER, 2 * mesh->mNumVertices * sizeof(GLfloat), texCoords, GL_STATIC_DRAW);

    glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 0, NULL);
    glEnableVertexAttribArray(1);

    delete texCoords;
}


if (mesh->HasNormals()) {
    float *normals = new float[mesh->mNumVertices * 3];
    for (int i = 0; i < mesh->mNumVertices; ++i) {
        normals[i * 3] = mesh->mNormals[i].x;
        normals[i * 3 + 1] = mesh->mNormals[i].y;
        normals[i * 3 + 2] = mesh->mNormals[i].z;
    }

    glGenBuffers(1, &vbo[NORMAL_BUFFER]);
    glBindBuffer(GL_ARRAY_BUFFER, vbo[NORMAL_BUFFER]);
    glBufferData(GL_ARRAY_BUFFER, 3 * mesh->mNumVertices * sizeof(GLfloat), normals, GL_STATIC_DRAW);

    glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, 0, NULL);
    glEnableVertexAttribArray(2);

    delete normals;
}


if (mesh->HasFaces()) {
    unsigned int *indices = new unsigned int[mesh->mNumFaces * 3];
    for (int i = 0; i < mesh->mNumFaces; ++i) {
        indices[i * 3] = mesh->mFaces[i].mIndices[0];
        indices[i * 3 + 1] = mesh->mFaces[i].mIndices[1];
        indices[i * 3 + 2] = mesh->mFaces[i].mIndices[2];
    }

    glGenBuffers(1, &vbo[INDEX_BUFFER]);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vbo[INDEX_BUFFER]);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, 3 * mesh->mNumFaces * sizeof(GLuint), indices, GL_STATIC_DRAW);

    delete indices;
}


glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindVertexArray(0);

glGenBuffers(1, &vbo[MVP_LOCATION]);
glBindBuffer(GL_ARRAY_BUFFER, vbo[MVP_LOCATION]);
for (unsigned int i = 0; i < 4; i++) {
    glEnableVertexAttribArray(MVP_LOCATION + i);
    glVertexAttribPointer(MVP_LOCATION + i, 4, GL_FLOAT, GL_FALSE, sizeof(glm::mat4), (const GLvoid*)(sizeof(GLfloat) * i * 4));
    glVertexAttribDivisor(MVP_LOCATION + i, 1);
}

glGenBuffers(1, &vbo[MODELVIEW_MAT_VB]);
glBindBuffer(GL_ARRAY_BUFFER, vbo[MODEL_VIEW_LOCATION]);
for (unsigned int i = 0; i < 4; i++) {
    glEnableVertexAttribArray(MODEL_VIEW_LOCATION + i);
    glVertexAttribPointer(MODEL_VIEW_LOCATION + i, 4, GL_FLOAT, GL_FALSE, sizeof(glm::mat4), (const GLvoid*)(sizeof(GLfloat) * i * 4));
    glVertexAttribDivisor(MODEL_VIEW_LOCATION + i, 1);
}

glGenBuffers(1, &vbo[NORMAL_MAT_VB]);
glBindBuffer(GL_ARRAY_BUFFER, vbo[NORMAL_MATRIX_LOCATION]);
for (unsigned int i = 0; i < 4; i++) {
    glEnableVertexAttribArray(NORMAL_MATRIX_LOCATION + i);
    glVertexAttribPointer(NORMAL_MATRIX_LOCATION + i, 4, GL_FLOAT, GL_FALSE, sizeof(glm::mat4), (const GLvoid*)(sizeof(GLfloat) * i * 4));
    glVertexAttribDivisor(NORMAL_MATRIX_LOCATION + i, 1);
}

实例渲染

void MeshEntry::renderInstanced(std::vector<glm::mat4> mvps, 
std::vector<glm::mat4> modelViews, std::vector<glm::mat4> normalMats)
{
    glBindBuffer(GL_ARRAY_BUFFER, vbo[MVP_MAT_VB]);
    glBufferData(GL_ARRAY_BUFFER, sizeof(glm::mat4) * mvps.size(), &mvps[0]
    [0], GL_DYNAMIC_DRAW);

    glBindBuffer(GL_ARRAY_BUFFER, vbo[MODELVIEW_MAT_VB]);
    glBufferData(GL_ARRAY_BUFFER, sizeof(glm::mat4) * mvps.size(), 
    &modelViews[0][0], GL_DYNAMIC_DRAW);

    glBindBuffer(GL_ARRAY_BUFFER, vbo[NORMAL_MAT_VB]);
    glBufferData(GL_ARRAY_BUFFER, sizeof(glm::mat4) * mvps.size(), 
    &normalMats[0][0], GL_DYNAMIC_DRAW);

    glBindVertexArray(vao);

    glDrawElementsInstanced(GL_TRIANGLES, elementCount, GL_UNSIGNED_INT, 
    NULL, mvps.size());

    // Make sure the VAO is not changed from the outside    
    glBindVertexArray(0);
}

顶点着色器

#version 430 core

layout (location = 0) in vec3 VertexPosition;
layout (location = 1) in vec2 VertexTex;
layout (location = 2) in vec3 VertexNormal;

layout (location = 3) in mat4 MVP;                                                  

layout (location = 7) in mat4 ModelViewMatrix; 
layout (location = 11) in mat4 NormalMatrix;

out Data
{
    vec3 Position;
    vec3 Normal;
    vec2 TexCoord;
} data;


void main()
{
    data.Normal = normalize( NormalMatrix * vec4(VertexNormal, 0) ).xyz;
    data.Position = vec3( ModelViewMatrix * vec4( VertexPosition, 1 ) );
    data.TexCoord = VertexTex;

    gl_Position = MVP * vec4( VertexPosition, 1 );
    gl_Position = vec4( VertexPosition, 1 );
}

在我开始在VBO中使用矩阵之前,这段代码再次正常工作,因此保证输入正常。 我上周刚刚开始处理opengl,所以请原谅我发布我认为可能相关的所有代码,老实说我不确定会出现什么问题。

提前感谢您的帮助。

2 个答案:

答案 0 :(得分:0)

更改为:

layout(location =10)uniform  mat4 .. ;

(这是使用430着色器运行但不是说330.需要

#extension GL_ARB_explicit_uniform_location : enable

那些东西和大多数opengl 3.3卡都会拒绝它。)

答案 1 :(得分:0)

结果发现这是一个简单的错误,使用错误的变量作为“vbo”数组的索引

glGenBuffers(1, &vbo[MVP_LOCATION]);
glBindBuffer(GL_ARRAY_BUFFER, vbo[MVP_LOCATION]);
for (unsigned int i = 0; i < 4; i++) {
    glEnableVertexAttribArray(MVP_LOCATION + i);
    glVertexAttribPointer(MVP_LOCATION + i, 4, GL_FLOAT, GL_FALSE, 
sizeof(glm::mat4), (const GLvoid*)(sizeof(GLfloat) * i * 4));
    glVertexAttribDivisor(MVP_LOCATION + i, 1);
}

应该是

glGenBuffers(1, &vbo[MVP_MAT_VB]);
glBindBuffer(GL_ARRAY_BUFFER, vbo[MVP_MAT_VB]);
for (unsigned int i = 0; i < 4; i++) {
    glEnableVertexAttribArray(MVP_LOCATION + i);
    glVertexAttribPointer(MVP_LOCATION + i, 4, GL_FLOAT, GL_FALSE, 
sizeof(glm::mat4), (const GLvoid*)(sizeof(GLfloat) * i * 4));
    glVertexAttribDivisor(MVP_LOCATION + i, 1);
}

请注意每个代码段的第一行和第二行