I am working on a Project to create Geometry by using a Geometry Shader and Transform Feedback.
I am currently trying to have the Geometry Shader return its input (1 triangle) without changing/adding anything, but its not working.
I would appreciate any help/advice I can get. Here are parts of my code:
The creation of the Program for Transform Feedback:
//==========================================
// Create the Transform Program
//==========================================
int check = LoadShader("Shaders//transformVS.glsl", GL_VERTEX_SHADER, transformVS);
//TODO: check for fail
check = LoadShader("Shaders//transformGS.glsl", GL_GEOMETRY_SHADER, transformGS);
//TODO: check for fail
transformProgram = glCreateProgram();
glAttachShader(transformProgram, transformVS);
glAttachShader(transformProgram, transformGS);
glBindAttribLocation(transformProgram, 0, "position_in");
glBindAttribLocation(transformProgram, 1, "normal_in");
glBindAttribLocation(transformProgram, 2, "length_in");
static const char* varyings[] = { "position_out", "normal_out", "length_out" };
glTransformFeedbackVaryings(transformProgram, 3, varyings, GL_INTERLEAVED_ATTRIBS);
glLinkProgram(transformProgram);
if (CheckProgram(transformProgram) == -1){
glDetachShader(transformProgram, transformVS);
glDetachShader(transformProgram, transformGS);
glDeleteShader(transformVS);
transformVS = 0;
glDeleteShader(transformGS);
transformGS = 0;
glDeleteProgram(transformProgram);
transformProgram = 0;
return -1;
}
error = glGetError();
The Creation of the VBOs, VAOs and TFOs:
//=====================================
// Create VBOs
//=====================================
glGenBuffers(2, VBOID);
glBindBuffer(GL_ARRAY_BUFFER, VBOID[0]);
glBufferData(GL_ARRAY_BUFFER, 3 * sizeof(TVertex_VNL), vertices, GL_DYNAMIC_COPY);
glBindBuffer(GL_ARRAY_BUFFER, 0);
error = glGetError();
glBindBuffer(GL_ARRAY_BUFFER, VBOID[1]);
glBufferData(GL_ARRAY_BUFFER, 3 * sizeof(TVertex_VNL), NULL, GL_DYNAMIC_COPY);
glBindBuffer(GL_ARRAY_BUFFER, 0);
error = glGetError();
//=====================================
// Create VAOs
//=====================================
glGenVertexArrays(2, VAOID);
glBindVertexArray(VAOID[0]);
glBindBuffer(GL_ARRAY_BUFFER, VBOID[0]);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(TVertex_VNL), BUFFER_OFFSET(0)); //position
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(TVertex_VNL), BUFFER_OFFSET(sizeof(float) * 3)); //normal
glVertexAttribPointer(2, 1, GL_FLOAT, GL_FALSE, sizeof(TVertex_VNL), BUFFER_OFFSET(sizeof(float) * 6)); //length
glBindBuffer(GL_ARRAY_BUFFER, 0);
glEnableVertexAttribArray(0);
glEnableVertexAttribArray(1);
glEnableVertexAttribArray(2);
glBindVertexArray(0);
error = glGetError();
glBindVertexArray(VAOID[1]);
glBindBuffer(GL_ARRAY_BUFFER, VBOID[1]);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(TVertex_VNL), BUFFER_OFFSET(0)); //position
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(TVertex_VNL), BUFFER_OFFSET(sizeof(float) * 3)); //normal
glVertexAttribPointer(2, 1, GL_FLOAT, GL_FALSE, sizeof(TVertex_VNL), BUFFER_OFFSET(sizeof(float) * 6)); //length
glBindBuffer(GL_ARRAY_BUFFER, 0);
glEnableVertexAttribArray(0);
glEnableVertexAttribArray(1);
glEnableVertexAttribArray(2);
glBindVertexArray(0);
error = glGetError();
//=====================================
// Create TFOs
//=====================================
glGenTransformFeedbacks(2, TFOID);
glBindTransformFeedback(GL_TRANSFORM_FEEDBACK, TFOID[0]);
glBindBufferBase(GL_TRANSFORM_FEEDBACK_BUFFER, 0, VBOID[0]);
glBindTransformFeedback(GL_TRANSFORM_FEEDBACK, 0);
error = glGetError();
glBindTransformFeedback(GL_TRANSFORM_FEEDBACK, TFOID[1]);
glBindBufferBase(GL_TRANSFORM_FEEDBACK_BUFFER, 0, VBOID[1]);
glBindTransformFeedback(GL_TRANSFORM_FEEDBACK, 0);
error = glGetError();
The render Method:
//=========================================
// Clear Screen
//=========================================
//Clear all the buffers
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
//========================================
// Transform Feedback
//========================================
glEnable(GL_RASTERIZER_DISCARD);
glUseProgram(transformProgram);
glBindVertexArray(VAOID[0]);
glBindTransformFeedback(GL_TRANSFORM_FEEDBACK, TFOID[1]);
glBeginTransformFeedback(GL_TRIANGLES);
glDrawArrays(GL_TRIANGLES, 0, 3);
glEndTransformFeedback();
glBindTransformFeedback(GL_TRANSFORM_FEEDBACK, 0);
glDisable(GL_RASTERIZER_DISCARD);
//========================================
// Draw Triangle
//========================================
//Bind the shader that we want to use
glUseProgram(renderProgram);
//Setup all uniforms for your shader
glUniformMatrix4fv(renderMVP, 1, FALSE, &MVP[0][0]);
//Bind the VAO
glBindVertexArray(VAOID[1]);
glDrawArrays(GL_TRIANGLES, 0, 3);
//glDrawTransformFeedback(GL_TRIANGLES, TFOID[1]);
//========================================
// Swap Buffers
//========================================
glutSwapBuffers();
The Vertex Shader:
#version 330
in vec3 position_in;
in vec3 normal_in;
in float length_in;
out vec3 vs_position;
out vec3 vs_normal;
out float vs_length;
void main()
{
vs_position = position_in;
vs_normal = normal_in;
vs_length = length_in;
}
The Geometry Shader:
#version 330
layout(triangles) in;
layout(triangle_strip, max_vertices = 3) out;
in vec3 vs_position[];
in vec3 vs_normal[];
in float vs_length[];
out vec3 position_out;
out vec3 normal_out;
out float length_out;
void main()
{
for(int i = 0; i < 3; i++){
position_out = vs_position[i];
normal_out = vs_normal[i];
length_out = vs_length[i];
EmitVertex();
}
EndPrimitive();
}
RASTERIZER_DISACRD
, it probably shouldn't be necessary, but I haven't looked that up in the spec. I think it can't hurt to add some error checks to the render method, though. – derhass