6
\$\begingroup\$

I'm kind of stuck with this question for some time now, maybe because I don't know exactly what to search for, it might be a term I have not heard of yet as most tutorials ends after drawing one object to the screen using a VBO.

Being a newbie to OpenGL as well as GLSL I do know at least a few things, one being that you always want to send as little information as you can from CPU -> GPU and by as few times as possible (better to send all data at once, instead of many small packages per frame). Knowing this tells me that there must be a better way to draw many of the same object, say a teapot, than looping over transformations then "glDrawArrays" and then repeating that step over and over.

It should be possible to send some kind of array containing the number of teapots you want to draw and all the positions/transformation-matrix you want for them.

I know I could possibly put multiple teapots into the same VBO with all the vertex data offset, but that would double the vertex-data and make it less flexible, seems like a bad solution to me.

So what is the right solution to drawing many of the same VBO at different transformations with a single or as few draw calls as possible?

\$\endgroup\$
10
\$\begingroup\$

What you're looking for is instancing. You simply call glDrawArraysInstanced​ or glDrawElementsInstanced​, passing the number of instances that you want. There are two ways to then determine per-instance data:

  1. The gl_InstanceID vertex shader input tells you which instance is currently being processed. Your vertex shader can have an internal mechanism for getting the correct data corresponding to the current gl_InstanceID. For example, it could use it to index a table.

  2. You can use instanced arrays, which causes a generic vertex attribute array to be indexed by instance, rather than by element index. For example, glVertexAttribDivisor​(attrib​, 1​) tells OpenGL to increment the index to the vertex attribute attrib with every instance. glVertexAttribDivisor​(attrib​, 2​) would increment the index with every second instance.

\$\endgroup\$
  • \$\begingroup\$ This is exactly what I'm looking for! I just knew that there had to be something like this available. I will take a long read on instancing, thanks. \$\endgroup\$ – Jacob Kofoed Aug 18 '13 at 13:58

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.