I am trying to stream data to a buffer which I have bound to a VAO vertex buffer binding point that I want to access through vertex attributes in the shader.

Usually I stream to buffers which I have bound as GL_UNIFORM_BUFFERs and I do it like this:

//create an immutable data storage 
glNamedBufferStorage(uboID, capacity, data, GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT | GL_MAP_COHERENT_BIT);

//map entire storage forever
mappedPtr = glMapNamedBufferRange(uboID, 0, capacity,  GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT | GL_MAP_COHERENT_BIT);

//bind buffer to target(GL_UNIFORM_BUFFER) binding point
glBindBufferBase(GL_UNIFORM_BUFFER, uboBinding, uboID);

//bind shader interface block to target binding point
glUniformBlockBinding(shaderProgramID, blockIndex, uboBinding);

Now the uniform block can be accessed in the shader program and i can stream to it like so:

//copy data to mapped pointer at stream offset
memcpy(mappedPtr + uploadOffset, &uploadData[0], uploadSize);

//This is the important part: tell the shader which range of the buffer to use
glBindBufferRange(GL_UNIFORM_BUFFER, uboBinding, uboID, uploadOffset, uploadSize);

//increment offset
uploadOffset += uploadSize;

If I bind a buffer to a VAO and access its data as vertex attributes in the shader, I don´t know how to give the shader the range in which the updated data can be found. I can give an offset when binding a buffer to a VAO when calling glVertexArrayVertexBuffer, but it has a few more parameters and does not seem like the right thing to call every frame. I have not gotten it to work with it, too.

Is there something like glBindBufferRange for vertex buffers bound to VAOs?


you can use separate attrib format so you can update the offset and stride of the vbo serpately from the format:

//during initialization

// set the details of a single attribute
glVertexArrayAttribFormat(vao, posAttrLoc, 3, GL_FLOAT, false, offsetof(Vertex, pos));
// which buffer binding point it is attached to
glVertexArrayAttribBinding(vao, posAttrLoc, vertexBindingPoint);
glEnableVertexArrayAttrib(vao, posAttrLoc);

then to set the vbo:

glVertexArrayVertexBuffer(vao, vertexBindingPoint, mesh.vbo, mesh.vboOffset, sizeof(Vertex));
  • \$\begingroup\$ This is the best way with a combination of DSA and vertex attrib binding. With the old API you'd need to adjust the pointers to offset to the start of the new range. \$\endgroup\$ Aug 21 '17 at 15:33
  • \$\begingroup\$ Yes, but isnt there some way to modify only the vboOffset parameter? I feel like glVertexArrayVertexBuffer is more like an initialization function and there must be something more designated I can use..(right?) \$\endgroup\$
    – stimulate
    Aug 21 '17 at 15:34
  • 1
    \$\begingroup\$ @stimulate it's the most designated you can get, it's really meant to be able to bind a new set of vbos to a vao without having to respecify the format. Which would help drivers avoid having to patch shaders. \$\endgroup\$ Aug 21 '17 at 15:37

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.