OpenGL VBO с одной плавающей точкой на задачу о вершине - PullRequest
1 голос
/ 26 апреля 2020

Я застрял вчера весь день с этой проблемой и не могу понять. Код приведен ниже, но, как правило, я пытаюсь дать мне sh Атрибуты вершины для 1.Postions 2.Indices 3.Normals и 4.All float. Все значения хранятся в разных VBO и после привязки каждого VBO я объявляю vertexAttribPointer. Я не могу заставить работать как нормали, так и значения с плавающей запятой. То, что я вижу, похоже на то, что положение значения с плавающей запятой - это либо xy, либо z часть нормалей vec3 в предыдущем vbo.

GL4 gl = GLContext.getCurrentGL().getGL4();

int[] vaoids = new int[1];
gl.glGenVertexArrays(1,vaoids,0);

int[] vboids = new int[4];
gl.glGenBuffers(4,vboids,0);

gl.glBindVertexArray(vaoids[0]);

FloatBuffer verticesBuffer = FloatBuffer.allocate(mesh.vertices.length);
verticesBuffer.put(mesh.vertices);
verticesBuffer.flip();

gl.glBindBuffer(gl.GL_ARRAY_BUFFER, vboids[0]);
gl.glBufferData(gl.GL_ARRAY_BUFFER, mesh.vertices.length * 4 ,verticesBuffer,gl.GL_STATIC_DRAW);
gl.glEnableVertexAttribArray(0);
gl.glVertexAttribPointer(0, 3, gl.GL_FLOAT, false, 0, 0);
verticesBuffer.clear();
verticesBuffer = null;

//normal buffer
FloatBuffer normalBuffer = FloatBuffer.allocate(mesh.normals.length);
normalBuffer.put(mesh.normals);
normalBuffer.flip();

gl.glBindBuffer(gl.GL_ARRAY_BUFFER, vboids[2]);
gl.glBufferData(gl.GL_ARRAY_BUFFER, mesh.normals.length * 4 ,normalBuffer,gl.GL_STATIC_DRAW);
gl.glEnableVertexAttribArray(2);
gl.glVertexAttribPointer(2, 3, gl.GL_FLOAT, false, 0, 0);
normalBuffer.clear();
normalBuffer = null;


//color buffer
float[] colors = new float[mesh.vertices.length/3];
Arrays.fill(colors,255.0f);
FloatBuffer colorBuffer = FloatBuffer.allocate(colors.length);
colorBuffer.put(colors);
colorBuffer.flip();

gl.glBindBuffer(gl.GL_ARRAY_BUFFER, vboids[3]);
gl.glBufferData(gl.GL_ARRAY_BUFFER, colors.length * 4 ,colorBuffer,gl.GL_STATIC_DRAW);
gl.glEnableVertexAttribArray(3);
gl.glVertexAttribPointer(3, 1, gl.GL_FLOAT,false, 0, 0);
colorBuffer.clear();
colorBuffer = null;

IntBuffer indicesBuffer = IntBuffer.allocate(mesh.indices.length);
indicesBuffer.put(mesh.indices);
indicesBuffer.flip();

gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, vboids[1]);
gl.glBufferData(gl.GL_ELEMENT_ARRAY_BUFFER, mesh.indices.length * 4 ,indicesBuffer,gl.GL_STATIC_DRAW);
gl.glEnableVertexAttribArray(1);
gl.glVertexAttribPointer(1, mesh.type.equals(MeshType.TRIANGLE) ? 3 : mesh.type.equals(MeshType.LINE) ? 2 : mesh.type.equals(MeshType.POINT) ? 1:0, gl.GL_UNSIGNED_INT, false, 0, 0);
indicesBuffer.clear();
indicesBuffer = null;

//gl.glBindBuffer(gl.GL_ARRAY_BUFFER,0);
gl.glBindVertexArray(0);

Это код, который объявляет vao и vbos. Я рендеринг с glDrawElements и включаю необходимые индексы VertexAttributeArray до этого. В моем шейдере я получаю доступ к значению, как показано ниже:

layout (location=0) in vec3 position;
layout (location=2) in vec3 normal;
layout (location=3) in float color;

out vec3 normals;
out vec4 positionWorldSpace;
out flat float vertexColor;

И фрагментный шейдер

in flat float color;

Я могу заставить их работать раздельно, но если я объявлю, что оба значения с плавающей точкой не исправить больше. Нормы, кажется, правы однако. Как я уже сказал, значения в float кажутся значениями от нормалей. Может ли быть какое-то переполнение от обычного vbo до float vbo? После нескольких часов просмотра кода я просто не могу определить ошибку.

1 Ответ

2 голосов
/ 26 апреля 2020

Индексы не являются атрибутами. [Index buffer] (индексные буферы) (GL_ELEMENT_ARRAY_BUFFER) указывается непосредственно в VAO. См. Спецификация вершины .
Когда вы используете glDrawArrays, тогда порядок вершинных координат координат вершин в массиве определяет примитивы . Если вы хотите использовать другой порядок или вы хотите использовать вершины для разных примитивов, тогда вы должны использовать glDrawElements. Когда вы используете glDrawElements, то примитивы определяются индексами вершин в буфере GL_ELEMENT_ARRAY_BUFFER:

gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, vboids[1]);
gl.glBufferData(gl.GL_ELEMENT_ARRAY_BUFFER, mesh.indices.length * 4 ,indicesBuffer,gl.GL_STATIC_DRAW);

// DELETE
//gl.glEnableVertexAttribArray(1);
//gl.glVertexAttribPointer(1, mesh.type.equals(MeshType.TRIANGLE) ? 3 : mesh.type.equals(MeshType.LINE) ? 2 : mesh.type.equals(MeshType.POINT) ? 1:0, gl.GL_UNSIGNED_INT, false, 0, 0);

indicesBuffer.clear();
indicesBuffer = null;

gl.glBindVertexArray(0);
gl.glDrawElements(gl.GL_TRIANGLES, mesh.indices.length, gl.GL_UNSIGNED_INT, null);
...