# OpenGL核心技术之几何着色器

3D引擎 同时被 3 个专栏收录
154 篇文章 16 订阅
97 篇文章 10 订阅
16 篇文章 86 订阅

CSDN视频网址：http://edu.csdn.net/lecturer/144

#version 330 core
layout (points) in;
layout (line_strip, max_vertices = 2) out;

void main() {
gl_Position = gl_in[0].gl_Position + vec4(-0.1, 0.0, 0.0, 0.0);
EmitVertex();

gl_Position = gl_in[0].gl_Position + vec4(0.1, 0.0, 0.0, 0.0);
EmitVertex();

EndPrimitive();
}

points绘制GL_POINTS基本图形的时候（1）
lines当绘制GL_LINES或GL_LINE_STRIP（2）时
trianglesGL_TRIANGLES, GL_TRIANGLE_STRIP或GL_TRIANGLE_FAN（3）

• points
• line_strip
• triangle_strip

in gl_Vertex
{
vec4 gl_Position;
float gl_PointSize;
float gl_ClipDistance[];
} gl_in[];


void main() {
gl_Position = gl_in[0].gl_Position + vec4(-0.1, 0.0, 0.0, 0.0);
EmitVertex();

gl_Position = gl_in[0].gl_Position + vec4(0.1, 0.0, 0.0, 0.0);
EmitVertex();

EndPrimitive();
}

glDrawArrays(GL_POINTS, 0, 4);

#version 330 core
layout (points) in;
layout (triangle_strip, max_vertices = 5) out;

void build_house(vec4 position)
{
gl_Position = position + vec4(-0.2f, -0.2f, 0.0f, 0.0f);// 1:左下角
EmitVertex();
gl_Position = position + vec4( 0.2f, -0.2f, 0.0f, 0.0f);// 2:右下角
EmitVertex();
gl_Position = position + vec4(-0.2f,  0.2f, 0.0f, 0.0f);// 3:左上
EmitVertex();
gl_Position = position + vec4( 0.2f,  0.2f, 0.0f, 0.0f);// 4:右上
EmitVertex();
gl_Position = position + vec4( 0.0f,  0.4f, 0.0f, 0.0f);// 5:屋顶
EmitVertex();
EndPrimitive();
}

void main()
{
build_house(gl_in[0].gl_Position);
}

GLfloat points[] = {
-0.5f,  0.5f, 1.0f, 0.0f, 0.0f, // 左上
0.5f,  0.5f, 0.0f, 1.0f, 0.0f, // 右上
0.5f, -0.5f, 0.0f, 0.0f, 1.0f, // 右下
-0.5f, -0.5f, 1.0f, 1.0f, 0.0f  // 左下
};

#version 330 core
layout (location = 0) in vec2 position;
layout (location = 1) in vec3 color;

out VS_OUT {
vec3 color;
} vs_out;

void main()
{
gl_Position = vec4(position.x, position.y, 0.0f, 1.0f);
vs_out.color = color;
}

in VS_OUT {    vec3 color;} gs_in[];

in vec3 vColor[];

out vec3 fColor;

fColor = gs_in[0].color; //只有一个输出颜色，所以直接设置为gs_in[0]
gl_Position = position + vec4(-0.2f, -0.2f, 0.0f, 0.0f);    // 1:左下
EmitVertex();
gl_Position = position + vec4( 0.2f, -0.2f, 0.0f, 0.0f);    // 2:右下
EmitVertex();
gl_Position = position + vec4(-0.2f,  0.2f, 0.0f, 0.0f);    // 3:左上
EmitVertex();
gl_Position = position + vec4( 0.2f,  0.2f, 0.0f, 0.0f);    // 4:右上
EmitVertex();
gl_Position = position + vec4( 0.0f,  0.4f, 0.0f, 0.0f);    // 5:屋顶
EmitVertex();
EndPrimitive();

fColor = gs_in[0].color;
gl_Position = position + vec4(-0.2f, -0.2f, 0.0f, 0.0f);
EmitVertex();
gl_Position = position + vec4( 0.2f, -0.2f, 0.0f, 0.0f);
EmitVertex();
gl_Position = position + vec4(-0.2f,  0.2f, 0.0f, 0.0f);
EmitVertex();
gl_Position = position + vec4( 0.2f,  0.2f, 0.0f, 0.0f);
EmitVertex();
gl_Position = position + vec4( 0.0f,  0.4f, 0.0f, 0.0f);
fColor = vec3(1.0f, 1.0f, 1.0f);
EmitVertex();
EndPrimitive();

vec3 GetNormal()
{
vec3 a = vec3(gl_in[0].gl_Position) - vec3(gl_in[1].gl_Position);
vec3 b = vec3(gl_in[2].gl_Position) - vec3(gl_in[1].gl_Position);
return normalize(cross(a, b));
}

vec4 explode(vec4 position, vec3 normal)
{
float magnitude = 2.0f;
vec3 direction = normal * ((sin(time) + 1.0f) / 2.0f) * magnitude;
return position + vec4(direction, 0.0f);
}

#version 330 core
layout (triangles) in;
layout (triangle_strip, max_vertices = 3) out;

in VS_OUT {
vec2 texCoords;
} gs_in[];

out vec2 TexCoords;

uniform float time;

vec4 explode(vec4 position, vec3 normal) { ... }

vec3 GetNormal() { ... }

void main() {
vec3 normal = GetNormal();

gl_Position = explode(gl_in[0].gl_Position, normal);
TexCoords = gs_in[0].texCoords;
EmitVertex();
gl_Position = explode(gl_in[1].gl_Position, normal);
TexCoords = gs_in[1].texCoords;
EmitVertex();
gl_Position = explode(gl_in[2].gl_Position, normal);
TexCoords = gs_in[2].texCoords;
EmitVertex();
EndPrimitive();
}

glUniform1f(glGetUniformLocation(shader.Program, "time"), glfwGetTime());


# 显示法向量

c++
DrawScene();
DrawScene();

#version 330 core
layout (location = 0) in vec3 position;
layout (location = 1) in vec3 normal;

out VS_OUT {
vec3 normal;
} vs_out;

uniform mat4 projection;
uniform mat4 view;
uniform mat4 model;

void main()
{
gl_Position = projection * view * model * vec4(position, 1.0f);
mat3 normalMatrix = mat3(transpose(inverse(view * model)));
vs_out.normal = normalize(vec3(projection * vec4(normalMatrix * normal, 1.0)));
}

#version 330 core
layout (triangles) in;
layout (line_strip, max_vertices = 6) out;

in VS_OUT {
vec3 normal;
} gs_in[];

const float MAGNITUDE = 0.4f;

void GenerateLine(int index)
{
gl_Position = gl_in[index].gl_Position;
EmitVertex();
gl_Position = gl_in[index].gl_Position + vec4(gs_in[index].normal, 0.0f) * MAGNITUDE;
EmitVertex();
EndPrimitive();
}

void main()
{
GenerateLine(0); // First vertex normal
GenerateLine(1); // Second vertex normal
GenerateLine(2); // Third vertex normal
}

#version 330 core
out vec4 color;

void main()
{
color = vec4(1.0f, 1.0f, 0.0f, 1.0f);
}

// ================
// ================
#version 330 core
layout (location = 0) in vec3 position;
layout (location = 1) in vec3 normal;

out VS_OUT {
vec3 normal;
} vs_out;

uniform mat4 projection;
uniform mat4 view;
uniform mat4 model;

void main()
{
gl_Position = projection * view * model * vec4(position, 1.0f);
mat3 normalMatrix = mat3(transpose(inverse(view * model)));
vs_out.normal = vec3(projection * vec4(normalMatrix * normal, 1.0));
}

// ================
// ================
#version 330 core
out vec4 color;

void main()
{
color = vec4(1.0f, 1.0f, 0.0f, 1.0f);
}

// ================
// ================
#version 330 core
layout (triangles) in;
layout (line_strip, max_vertices = 6) out;

in VS_OUT {
vec3 normal;
} gs_in[];

const float MAGNITUDE = 0.2f;

void GenerateLine(int index)
{
gl_Position = gl_in[index].gl_Position;
EmitVertex();
gl_Position = gl_in[index].gl_Position + vec4(gs_in[index].normal, 0.0f) * MAGNITUDE;
EmitVertex();
EndPrimitive();
}

void main()
{
GenerateLine(0); // First vertex normal
GenerateLine(1); // Second vertex normal
GenerateLine(2); // Third vertex normal
}

C++ 核心代码如下所示：

 	// Clear buffers
glClearColor(0.1f, 0.1f, 0.1f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

glm::mat4 model;

// Draw model

// Now set transformation matrices for drawing normals
model = glm::mat4();

// And draw model again, this time only drawing normal vectors using the geometry shaders (on top of previous model)

// Swap the buffers
glfwSwapBuffers(window);

• 7
点赞
• 0
评论
• 4
收藏
• 一键三连
• 扫一扫，分享海报

12-29 2102
05-18 6634
04-25 431
12-27 653
05-01 415
12-24 456
02-03 566
04-11 278
10-07 170