0

I have an array which contains coordinates. It looks like:

    glm::vec3* Vertices;

How can I pass its elements to glVertexAttribPointer. Is the only way just one dimensional array? For example; can I use something like that:

    float* Vertices[3];
Andon M. Coleman
  • 42,359
  • 2
  • 81
  • 106
user3117189
  • 69
  • 3
  • 9
  • That is an array of 3 `float*`'s... that will not work. What you want is an array large enough to hold 3 vertices (to draw 1 triangle), each 3 `float`s in length... So something like: `float Vertices [9];` But, to be honest, `glm::vec3` is probably usable as a contiguous block of memory, most of those sorts of classes are. So an array of `glm::vec3` by itself may be all that is necessary. – Andon M. Coleman Jan 07 '14 at 00:57

1 Answers1

2

Before reading my answer: Apparently my answer is only partially correct, and you can use glVertexAttribPointer without manually writing to the GRAM but instead using client memory, but it is still preferable to use VBOs instead of using this approach.

You don't pass something to glVertexAttribPointer. You will have to write it to the GRAM first by using glBufferData after binding a buffer with glBindBuffer. glVertexAttribPointer will only describe where in this bound buffer the data will be found. And here is the point that shows that you can pass almost any data you wish to the GRAM. If you have your array of vec3 (i assume vec3 only contains floats x, y and z) your memory for this array will look like x1, y1, z1, x2, y2, z2, x3, y3, z3 and so on. If that is written to your GRAM you will have to specify this data so your GPU knows what to do. Example:

glBindBuffer(GL_ARRAY_BUFFER, bufferID); 

bufferID must be allocated before (glGenBuffers).

glBufferData(GL_ARRAY_BUFFER, 36, vertices, GL_STATIC_DRAW); 

Write to the buffer bound in GL_ARRAY_BUFFER (with glBindBuffer). Write 36 bytes (float = 4bytes, 1 vertex with only position = 3 floats, 1 triangle = 3 vertices, sums up to 36 bytes for 1 triangle) GL_STATIC_DRAW indicates that we will write this once and then only draw it.

glVertexPointer(3, GL_FLOAT, 0, 0)
  • You have 3 coordinates per Vertex (size)
  • They are floats (GL_FLOAT, type)
  • You have 12 byte length for a whole data set in the buffer sizeof(float) * 3 and because you only use a single pointer here it can compute the stride for itself when you pass 0 (elements * typesize) (stride)
  • And they begin at the beginning of the buffer (0, offset)

I used glVertexPointer here for simplicity.

You can find a very good tutorial on VBOs in the LWJGL Wiki

http://www.lwjgl.org/wiki/index.php?title=Using_Vertex_Buffer_Objects_%28VBO%29

th3falc0n
  • 1,389
  • 1
  • 12
  • 33
  • 1
    That is not necessarily true, you definitely have to use VBOs in a core profile context, but in compatibility you can actually have `glVertexAttribPointer (...)` point to client memory. The major down-side to using client memory for vertex data is that GL either has to copy the entire array before doing a `glDrawArrays (...)` command or force pipeline synchronization so that the data cannot be changed while the command is in action. This is why VBOs give better performance and are the only choice in **modern** (core) GL. – Andon M. Coleman Jan 07 '14 at 01:13
  • That was something I actually didn't know. Adding a hint to your comment in the answer. – th3falc0n Jan 07 '14 at 01:16
  • Sorry, I did not mean to imply you had to change anything major in your answer. It was the statement that you have to use VBOs that was bugging me. This is all very good advice, and VBOs are the way to go, but they are not always a requirement. Also, `glm` is a C++ template library (though the question is not tagged as such, and I will fix that right now), so LWJGL might not be the best reference to use. – Andon M. Coleman Jan 07 '14 at 01:28
  • `stride` doesn't mean how "many elements between them" but how many bytes must be added to the pointer to get the next element, where `0` is a special value meaning `size*sizeof(type)` – ratchet freak Jan 07 '14 at 09:54
  • That was actually what I meant, just forgot to mention that 0 is a special case, but I edited that now. – th3falc0n Jan 07 '14 at 15:09