OpenGL +无法使用buffersubdata

时间:2016-01-29 04:22:25

标签: c++ opengl

我试图使用glNamedBufferSubData或glBufferSubData覆盖缓冲区中的顶点值,但它似乎没有做任何事情。

我有函数updateGeometry我想从renderGeometry函数调用我修改SpringMass对象的一个​​变量。我希望数据完全覆盖,因此使用 - 因为偏移是预期的。

const int NUM_VERTICES_PER_LINE = 2;
const int NUMFLOATSPERVERTICES = 6;
const int VERTEX_BYTE_SIZE = NUMFLOATSPERVERTICES * sizeof(float);

GLint numSpringIndices, numMassIndices;
#define NUM_ARRAY_ELEMENTS(a) sizeof(a) / sizeof(*a);
Spring::Spring() : anchorPosition{ 0.0f, 1.0f, 0.0f }, mPosition{ 0.0f, 0.0f, 0.0f }, displacement{ 0.0f, -0.3f, 0.0f } {
    USING_ATLAS_GL_NS; //Short for atlas GL namespace
    USING_ATLAS_MATH_NS;
    glGenVertexArrays(1, &mVertexArrayObject);
    glBindVertexArray(mVertexArrayObject);

    //mSpringMass = ObjectGenerator::makeSpring(anchorPosition, stretch, d);
    //mMass = ObjectGenerator::makeMass(calculateConnectionPoint(anchorPosition), massWidth, massHeight);
    mSpringMass = ObjectGenerator::makeSpringMass(anchorPosition, stretch, d, massWidth, massHeight);
    numSpringIndices = mSpringMass.numIndices;

    glGenBuffers(1, &mVertexBufferObject);
    glBindBuffer(GL_ARRAY_BUFFER, mVertexBufferObject);
    glBufferData(GL_ARRAY_BUFFER, mSpringMass.vertexBufferSize(), mSpringMass.vertices, GL_STATIC_DRAW);
    glEnableVertexAttribArray(0);
    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, VERTEX_BYTE_SIZE, 0);
    glEnableVertexAttribArray(1);
    glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, VERTEX_BYTE_SIZE, (char*)(sizeof(float) * 3));

    glGenBuffers(1, &springIndexBufferID);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, springIndexBufferID);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, mSpringMass.indexBufferSize(), mSpringMass.indices, GL_STATIC_DRAW);
    // Get the path where our shaders are stored.
    std::string shaderDir = generated::ShaderPaths::getShaderDirectory();

    // Now set up the information for our shaders.
    std::vector<ShaderInfo> shaders
    {
        ShaderInfo{ GL_VERTEX_SHADER, shaderDir + "Spring.vs.glsl" },
        ShaderInfo{ GL_FRAGMENT_SHADER, shaderDir + "Spring.fs.glsl" }
    };
    // Create a new shader and add it to our list.
    mShaders.push_back(ShaderPointer(new Shader));
    mShaders[0]->compileShaders(shaders);
    mShaders[0]->linkShaders();
    mShaders[0]->disableShaders();
}

Spring::~Spring()
{
    glDeleteVertexArrays(1, &mVertexArrayObject);
    glDeleteBuffers(1, &mSpringBuffer);
}

void Spring::renderGeometry(atlas::math::Matrix4 projection, atlas::math::Matrix4 view) {
    // To avoid warnings from unused variables, you can use the 
    //UNUSED macro.
    UNUSED(projection);
    UNUSED(view);
    mShaders[0]->enableShaders();
    updateGeometry();
    GLint dispLocation = mShaders[0]->getUniformVariable("displacement");
    GLint anchorLocation = mShaders[0]->getUniformVariable("anchorPosition");
    glUniform3fv(anchorLocation, 1, &anchorPosition[0]);
    glUniform3fv(dispLocation, 1, &displacement[0]);
    glBindVertexArray(mVertexArrayObject);

    glDrawElements(GL_LINES, numSpringIndices, GL_UNSIGNED_SHORT, 0);

    mShaders[0]->disableShaders();
}

void Spring::updateGeometry() {
    //glBindBuffer(GL_ARRAY_BUFFER, mVertexBufferObject);
    GLfloat newD = d * 0;
    mSpringMass = ObjectGenerator::makeSpringMass(anchorPosition, stretch, newD, massWidth, massHeight);
    //glBufferSubData(GL_ARRAY_BUFFER, 0, sizeof(mSpringMass.vertices), mSpringMass.vertices);
    glNamedBufferSubData(mVertexBufferObject, 0, sizeof(mSpringMass.vertices), mSpringMass.vertices);
}

修改

这里要说明的是ObjectGenerator代码。

#include "ObjectGenerator.h"
#define NUM_ARRAY_ELEMENTS(a) sizeof(a) / sizeof(*a);
ShapeData ObjectGenerator::makeSpringMass(glm::vec3 anchorPosition, GLfloat stretch, GLfloat d, GLfloat width, GLfloat height) {
    ShapeData ret;
    glm::vec3 springColor{ 1.0f, 0.0f, 0.0f }, massColor{ 0.0f, 1.0f, 0.0f }, connectionPoint{ anchorPosition.x, anchorPosition.y - (18 * d), 0.0f };
    static const Vertex vertices[] = {
        glm::vec3(anchorPosition.x, anchorPosition.y, 0.0f), // 0
        springColor,
        glm::vec3(anchorPosition.x, anchorPosition.y - d,0.0f), // 1
        springColor,
        glm::vec3(anchorPosition.x + stretch, anchorPosition.y - (2 * d), 0.0f), // 2
        springColor,
        glm::vec3(anchorPosition.x - stretch, anchorPosition.y - (4 * d), 0.0f), // 3
        springColor,
        glm::vec3(anchorPosition.x + stretch, anchorPosition.y - (6 * d), 0.0f), // 4
        springColor,
        glm::vec3(anchorPosition.x - stretch, anchorPosition.y - (8 * d), 0.0f), // 5
        springColor,
        glm::vec3(anchorPosition.x + stretch, anchorPosition.y - (10 * d), 0.0f), // 6
        springColor,
        glm::vec3(anchorPosition.x - stretch, anchorPosition.y - (12 * d), 0.0f), // 7
        springColor,
        glm::vec3(anchorPosition.x + stretch, anchorPosition.y - (14 * d), 0.0f), // 8
        springColor,
        glm::vec3(anchorPosition.x - stretch, anchorPosition.y - (16 * d), 0.0f), // 9
        springColor,
        glm::vec3(anchorPosition.x, anchorPosition.y - (17 * d), 0.0f), // 10
        springColor,
        connectionPoint, // 11
        springColor,
        //=================Mass==============//
        glm::vec3(connectionPoint.x - width, connectionPoint.y, 0.0f), //top Left 12
        massColor,
        glm::vec3(connectionPoint.x + width, connectionPoint.y, 0.0f), //top Right 13
        massColor,
        glm::vec3(connectionPoint.x + width, connectionPoint.y - height, 0.0f), // bottom right 14
        massColor,
        glm::vec3(connectionPoint.x - width, connectionPoint.y - height, 0.0f), // bottom left 15
        massColor,
    };
    ret.numVertices = NUM_ARRAY_ELEMENTS(vertices);
    ret.vertices = new Vertex[ret.numVertices];
    memcpy(ret.vertices, vertices, sizeof(vertices)); //memcpy(dest, source, size);

    GLushort indices[] = { 0,1 ,1,2, 2,3, 3,4, 4,5, 5,6, 6,7, 7,8, 8,9, 9,10, 10,11, 11,12, 12,13, 13,14, 14,15, 15,12};
    //GLushort indices[] = { 0,1 ,1,2, 2,3, 3,4, 4,5, 5,6, 6,7, 7,8, 8,9, 9,10, 10,11 };
    ret.numIndices = NUM_ARRAY_ELEMENTS(indices);
    ret.indices = new GLushort[ret.numIndices];
    memcpy(ret.indices, indices, sizeof(indices));

    return ret;
} 

1 个答案:

答案 0 :(得分:0)

我已经弄清楚了。

在我的对象生成器类中,顶点数据永远不会更新,因为我离开了static const限定符。 glBuffersubData工作得很好,但它只是覆盖完全相同的数据......