1

Let's say I want to upload unsigned integer and float data to the graphics card, in a single draw call. I use standard VBOs (not VAO, I'm using OpenGL 2.0), with the various vertex attribute arrays combined into the single GL_ARRAY_BUFFER, and pointed to individually using glVertexAttribPointer(...), so:

    glBindBuffer(GL_ARRAY_BUFFER, vertexBufferId);
    glEnableVertexAttribArray(positionAttributeId);
    glEnableVertexAttribArray(myIntAttributeId);
    glVertexAttribPointer(positionAttributeId, 4, GL_FLOAT, false, 0, 0);
    glVertexAttribPointer(colorAttributeId, 4, GL_UNSIGNED_INT, false, 0, 128);

    glClear(...);
    glDraw*(...);

The problem I have here is that my buffer (ref'ed by vertexBufferId), has to be created as a FloatBuffer in LWJGL, so that it can support the attribute of type GL_FLOAT, and this would seem to preclude the use of GL_INT here (or else, the other way around - it's either one or the other since the buffer cannot be of two types).

Any ideas? How would this be handled in native C code?

genpfault
  • 51,148
  • 11
  • 85
  • 139
Engineer
  • 8,529
  • 7
  • 65
  • 105
  • Are you using OpenGL or OpenGL ES 2.0? Because they're not the same thing. – Nicol Bolas Jul 23 '12 at 17:28
  • @NicolBolas I am using the OpenGL ES 2.0 subset of OpenGL 2.0 -- as far as I am thus far aware. – Engineer Jul 23 '12 at 17:28
  • OpenGL ES 2.0 is *not* a subset of OpenGL 2.0. So which are you using: desktop GL or GL ES? – Nicol Bolas Jul 23 '12 at 17:31
  • @NicolBolas Once again, there is a shared subset ("interesection") of programmable pipeline functionality between OpenGL 2.0/2.1 and OpenGL ES 2.0, correct? Since the OpenGL ES 2.0 spec was derived from the OpenGL 2.1 spec. This is common knowledge, as far as I am aware. FTR, I am currently developing in a desktop enviroment. – Engineer Jul 23 '12 at 17:34
  • And yet... you're using `GL_UNSIGNED_INT`, which is *not allowed* in ES 2.0 (ES only allows `BYTE` and `SHORT`). So even if there were an intersection, you're not using it. As for "common knowledge", it's a common *misconception*. – Nicol Bolas Jul 23 '12 at 17:37
  • @NicolBolas Funny, since every reference I see on OpenGL ES 2.0 suggests that in fact, it does support both GL_UNSIGNED_INT and GL_INT. Perhaps you can post a reference to back up your comments? – Engineer Jul 23 '12 at 17:46
  • See page 20 of the [OpenGL ES 2.0 specification PDF](http://www.khronos.org/registry/gles/specs/2.0/es_full_spec_2.0.25.pdf). Or check the [quick-reference card](http://www.khronos.org/opengles/sdk/docs/reference_cards/OpenGL-ES-2_0-Reference-card.pdf). It lists byte, ubyte, short, ushort, float, and fixed. Notably absent are int and uint. That's why it's important to code on the *actual* platform rather than any "shared subset"; because otherwise, you have no way of knowing whether you're coding outside of the subset. – Nicol Bolas Jul 23 '12 at 17:53
  • @NicolBolas Of course it lists those -- those are the types as referenced in GLSL, not in client code. Their counterparts in client code are GL_*. And in the quick ref card (which I checked before replying to you previously), it lists an unsigned integer type, no? Further, these exist as GL_* types in the LWJGL API docs. Genuinely, is there something I am missing here? – Engineer Jul 23 '12 at 17:57
  • let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/14300/discussion-between-nicol-bolas-and-nick-wiggill) – Nicol Bolas Jul 23 '12 at 17:58

1 Answers1

2

This would be handled in C (in a safe way) by doing this:

GLfloat *positions = malloc(sizeof(GLfloat) * 4 * numVertices);
GLuint *colors = malloc(sizeof(GLuint) * 4 * numVertices);

//Fill in data here.

//Allocate buffer memory
glBufferData(..., (sizeof(GLfloat) + sizeof(GLuint)) * 4 * numVertices, NULL, ...);
//Upload arrays
glBufferSubData(..., 0, sizeof(GLfloat) * 4 * numVertices, positions);
glBufferSubData(..., sizeof(GLfloat) * 4 * numVertices, sizeof(GLuint) * 4 * numVertices, colors);

free(positions);
free(colors);

There are other ways of doing this in as well, which involve a lot of casting and so forth. But this code emulates what you'll have to do in LWJGL.

Nicol Bolas
  • 449,505
  • 63
  • 781
  • 982
  • Useful enough; I assumed C would use clever casting since it's so flexible with regards to memory access, but this helps me not at all with the LWJGL-specific part of the problem. – Engineer Jul 23 '12 at 17:47
  • How doesn't it help you in LWJGL? Can you not create an int buffer and use `glBufferSubData` to upload it to part of the buffer? The reason I *didn't* use C-style casting tricks was to emulate how you would need to do it in Java. – Nicol Bolas Jul 23 '12 at 17:55
  • I think I see. I shall try this. – Engineer Jul 23 '12 at 18:17