Приветствую вас, любители OpenGL!
А теперь приступим.
public class Loader {
public void createVAO(int[] indices) {
int vaoID = glGenVertexArrays();
glBindVertexArray(vaoID);
createIndicesVBO(indices);
glEnableVertexAttribArray(0);
}
public void createVBO(float[] vertices) {
int vboID = glGenBuffers();
glBindBuffer(GL_ARRAY_BUFFER, vboID);
FloatBuffer buffer = makeByteBufferFromArrayOfFloats(vertices);
glBufferData(GL_ARRAY_BUFFER, buffer, GL_STATIC_DRAW);
glVertexAttribPointer(0, 3, GL_FLOAT, false, 0,0);
}
public void createIndicesVBO(int[] indices) {
int vboID = glGenBuffers();
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vboID);
IntBuffer buffer = makeByteBufferFromArrayOfInts(indices);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, buffer, GL_STATIC_DRAW);
}
public void pleaseDraw(float[] vertices, int[] indices) {
glClearColor(0, 0, 1, 1);
glClear(GL_COLOR_BUFFER_BIT);
glDrawElements(GL_TRIANGLES, indices.length, GL_UNSIGNED_INT,0);
}
public void cleanUp() {
glDeleteBuffers(0);
glDeleteVertexArrays(0);
}
public FloatBuffer makeByteBufferFromArrayOfFloats(float[] vertices) {
FloatBuffer FloatByteBuffer = BufferUtils.createFloatBuffer(vertices.length);
FloatByteBuffer.put(vertices);
FloatByteBuffer.flip();
return FloatByteBuffer;
}
public IntBuffer makeByteBufferFromArrayOfInts(int[] array) {
IntBuffer IntByteBuffer = BufferUtils.createIntBuffer(array.length);
IntByteBuffer.put(array);
IntByteBuffer.flip();
return IntByteBuffer;
}
}
Примечание - этот код работает и выводит синее окно с черным квадратом посередине. Вопросов:
glBindBuffer(GL_ARRAY_BUFFER, vboID); Я не совсем понимаю, что вообще означает GL_Array Buffer. Насколько я могу понять, это просто показывает текущее состояние OpenGL, что этот VBO в какой-то момент будет хранить данные массива. Но из приведенной ниже функции я могу догадаться, что это не просто тип данных, а что-то вроде
контейнер для данных, и это только то, что может быть активный для текущего состояния. Я правильно понимаю? Или я что-то упускаю?glBufferData(GL_ARRAY_BUFFER, buffer, GL_STATIC_DRAW); Опять это GL_Array_Thing. И кажется, эта функция помещает данные в графический процессор или помещает текущий VBO в VAO? Я не уверен.glVertexAttribPointer(0, 3, GL_FLOAT, false, 0,0); Итак, VAO состоит из атрибутов, и здесь мы показываем OpenGL, как читать наш атрибут 0. Поправьте меня если я ошибаюсь.glEnableVertexAttribArray(0); и glVertexAttribPointer(0, 3, GL_FLOAT, false, 0,0); на glEnableVertexAttribArray(1); и glVertexAttribPointer(1, 3, GL_FLOAT, false, 0,0);. В финальном рендере ничего не должно измениться, но на самом деле черный квадратик не появляется. Не могу понять почему.glDrawElements(GL_TRIANGLES, indices.length, GL_UNSIGNED_INT,0);Есть много дополнительных вопросов, но они либо появляются из-за моего непонимания вопросов, которые я описал выше. Пожалуйста, помогите мне разобраться в этой неразберихе в моей голове об основах OpenGL. Для тех, кто смог прочитать или хотя бы ответить на этот пост - Большое спасибо!
Эти вопросы нацелены на некоторые фундаментальные принципы OpenGL. Они слишком широки, чтобы на них можно было ответить в сообщении stackoverflow. По этим темам уже существует обширная документация и руководства. См., Например, вики OpenGL на буферные объекты и Спецификация вершин. Есть также обширные учебники, такие как open.gl или Изучение программирования современной 3D-графики.




glBindBuffer(GL_ARRAY_BUFFER, vboID);
Значит: у меня есть несколько VBO. Выберите (для следующего использования) тот, который идентифицирован vboID. Режим GL_ARRAY_BUFFER предназначен для данных сырой (байтов).
glBufferData(GL_ARRAY_BUFFER, size, buffer, GL_STATIC_DRAW); //Notice I added "size" for C++. LWJGL doesn't need it.
Средство: заполнить связанный в данный момент array_buffer (с помощью "glBindBuffer") байтами size; взять их с buffer (адрес в RAM CPU). Мое намерение (GL_STATIC_DRAW) состоит в том, чтобы графический процессор многократно считывал данные, а не модифицировал их.
glVertexAttribPointer(0, 3, GL_FLOAT, false, stride, 0,0); // "stride" added
Графический процессор читает из одного или нескольких VBO. Например, VBO может состоять из координат x, y, z (3 числа с плавающей запятой), за которыми следуют компоненты цвета R, G, B, A (4 байта) и повторять последовательность для других вершин.
glVertexAttribPointer устанавливает связь между VBO и необходимыми атрибутами. В примере: первый атрибут (0) требует значений 3 типа GL_FLOAT, которые не (false) нормализованы (не в диапазоне [0,0, 1,0]). Следующая последовательность для этого атрибута - это stride байта (использование 0 означает, что атрибуты плотно упакованы). Последний 0.0 - это смещение в VBO для первого атрибута.
Цвет может быть прочитан как другой атрибут из того же VBO или нет. «Имя» для этого атрибута может быть 1, потому что 0 уже используется для координат. Поэтому ему нужен собственный вызов glVertexAttribPointer.
Идентификаторы атрибутов были выбраны графическим процессором. Поскольку OpenGL> = 3.3 (который я настоятельно рекомендую использовать), вам лучше выбирать их (по "location = 0" в шейдерах)
VAO содержит привязки буферов и привязки атрибутов. Каждый раз, когда вам нужно рендерить данные из некоторых VBO, вам не нужно снова использовать требуемые glBindBuffer и glVertexAttribPointer. Просто используйте вместо него glBindVertexArray.
«Индексирующий рендеринг» означает, что вы используете два VBO: один для координат, а другой для индексов. (Другие VBO также могут использоваться для других атрибутов). VBO с индексами сообщает графическому процессору порядок «последовательностей» от первого VBO (и других VBO). Это позволяет читать одну и ту же вершину несколько раз, не повторяя ее атрибуты. Обратите внимание, что триангуляция имеет одну и ту же вершину среди нескольких треугольников. Вы можете избежать отправки в GPU повторяющихся данных.
Этот сайт лучше всего подходит для короткие и конкретные вопросы, по одному вопросу на сообщение. Это не форум. Предлагаю разбить это на несколько постов. Кроме того, пробовали ли вы его поискать (в вики OpenGL и / или на страницах руководства)? Если вы предоставите подробную информацию о том, что вы обнаружили и как это не ответит на ваш вопрос, люди могут с большей готовностью помочь вам.