2014-01-07 4 views
0

У меня есть массив, содержащий координаты. Он выглядит так:Vertex Array для VBO -OpenGL

glm::vec3* Vertices; 

Как передать его элементы в glVertexAttribPointer. Единственный способ - только один размерный массив? Например; можно использовать что-то вроде этого:

float* Vertices[3]; 
+0

То есть массив 3 'флоат *' 's ... что не будет работать. То, что вы хотите, - это массив, достаточно большой, чтобы удерживать 3 вершины (чтобы нарисовать 1 треугольник), каждый 3 'float' в длину ... Так что-то вроде: 'float Vertices [9];' Но, если честно, 'glm :: vec3', вероятно, можно использовать в качестве непрерывного блока памяти, большинство из этих классов. Таким образом, массив 'glm :: vec3' сам по себе может быть всем, что необходимо. –

ответ

2

Прежде чем читать мой ответ: Очевидно, что мой ответ лишь отчасти, и вы можете использовать glVertexAttribPointer без ручного написания к грамположительной, но вместо того, чтобы использовать память клиента, но он по-прежнему предпочтительнее вместо использования этого подхода используйте VBOs.

Вы ничего не передаете glVertexAttribPointer. Сначала вам нужно записать его в GRAM, используя glBufferData после связывания буфера с glBindBuffer. glVertexAttribPointer будет описывать только, где в этом связанном буфере данные будут найдены. И вот пункт, который показывает, что вы можете передавать практически любые данные, которые вы хотите использовать в GRAM. Если у вас есть массив vec3 (я предполагаю, что vec3 содержит только float x, y и z), ваша память для этого массива будет выглядеть как x1, y1, z1, x2, y2, z2, x3, y3, z3 и так далее. Если это будет записано в ваш GRAM, вам нужно будет указать эти данные, чтобы ваш GPU знал, что делать. Пример:

glBindBuffer(GL_ARRAY_BUFFER, bufferID); 

bufferID должны быть выделены ранее (glGenBuffers).

glBufferData(GL_ARRAY_BUFFER, 36, vertices, GL_STATIC_DRAW); 

Запись в буфер, связанного в GL_ARRAY_BUFFER (с glBindBuffer). Напишите 36 байтов (float = 4 байта, 1 вершина с только позицией = 3 поплавка, 1 треугольник = 3 вершины, сумма до 36 байтов для 1 треугольника) GL_STATIC_DRAW указывает, что мы будем писать это один раз, а затем только рисовать.

glVertexPointer(3, GL_FLOAT, 0, 0) 
  • У вас есть 3 координаты каждой вершины (size)
  • Они поплавки (GL_FLOAT, type)
  • У вас есть 12 длина байта для целого набора данных в буфере SizeOf (флоат) * 3 и потому, что вы используете только один указатель здесь, он может вычислить шаг для себя, когда вы проходите 0 (элементы * typesize) (stride)
  • И они начинаются с начала буфера (0, offset)

Я использовал glVertexPointer здесь для простоты.

Вы можете найти очень хороший учебник по РВО в LWJGL Wiki

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

+1

Это не обязательно так, вы обязательно должны использовать VBOs в контексте основного профиля, но в совместимости вы можете фактически иметь 'glVertexAttribPointer (...)' пункт для клиентской памяти. Основная сторона использования клиентской памяти для данных вершин заключается в том, что GL либо должен скопировать весь массив, прежде чем делать «glDrawArrays» (...) 'команда или принудительная синхронизация трубопровода, чтобы данные не могли быть изменены во время действия команды. Вот почему VBOs дают лучшую производительность и являются единственным выбором в ** современной ** (основной) GL. –

+0

Это было то, чего я действительно не знал. Добавление подсказки к вашему комментарию в ответе. – th3falc0n

+0

Извините, я не хотел подразумевать, что вам пришлось изменить что-то важное в вашем ответе. Это было утверждение, что вы должны использовать VBOs, который меня подталкивал. Это очень хороший совет, и VBOs - это путь, но они не всегда являются обязательными. Кроме того, 'glm' является библиотекой шаблонов C++ (хотя вопрос не помечен как таковой, и я исправлю это прямо сейчас), поэтому LWJGL может не быть лучшей ссылкой на использование. –