爆破效果
原理:
将每一个片元沿三角形法向量方向移动一段距离
核心代码 + 避坑点:
.vert
#version 450 core
layout (location = 0) in vec3 aPos;
layout (location = 1) in vec3 aNormal;
layout (location = 2) in vec2 aTexCoords;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
//out vec3 FragPos;//尝试直接使数据跨过几何着色器?????不可
注意1:若该着色器有几何着色器,则该out输出块只能传给几何着色器,不能直接通过out传递给片元着色器。
例如:在顶点着色器中有 out vec3 FragPos,在片元着色器中有in vec3 FragPos,在几何着色器中 没有 in vec3 FragPos接收,
则虽然程序编译不会报错,但是却无法使用。
不知为何,如果当前着色器无法使用,GLSL会默认使用上一个着色器!!!
(亲测避坑)
out VS_OUT{
vec2 texCoords;//必须同名,!!!!!
vec3 normal;
vec3 fragPos;
}vs_out;
注意2:若out VS_OUT{ … } 中参数名称,与in VS_OUT{…}中参数名称不同,也无法正常运行!!!
例如:在顶点着色器中有out VS_OUT{ vec2 texCoords; },而在几何着色器中有in VS_OUT{ vec2 TexCoords; },即使是一个字母的大小写不匹配也会无法正常运行!!!
(亲测)
void main()
{
vs_out.normal = aNormal;
vs_out.texCoords = aTexCoords;
vs_out.fragPos = vec3(model * vec4(aPos, 1.0));
gl_Position = projection * view * vec4(vs_out.fragPos, 1.0);
}
.geom
#version 450 core
layout (triangles) in;
layout (triangle_strip, max_vertices = 3) out;
in VS_OUT{
vec2 texCoords;
vec3 normal;
vec3 fragPos;
} gs_in[];
out vec2 TexCoords;
out vec3 Normal;
out vec3 FragPos;
uniform float time;//新增全局变量需要在主程序中添加数据
vec4 explode(vec4 position, vec3 normal) {
float magnitude = 2.0;//爆破程度
vec3 direction = normal * ((sin(time) + 1.0) / 2.0) * magnitude;
return position + vec4(direction, 0.0);
}
void main() {
vec3 normal = gs_in[0].normal;
//gs_in[0、1、2]都是同一个值(在初始赋值时便是如此),若是使用EBO则需通过三角形绘制方向计算
gl_Position = explode(gl_in[0].gl_Position, normal);
TexCoords = gs_in[0].texCoords;
Normal = gs_in[0].normal;
FragPos = gs_in[0].fragPos;
EmitVertex();
gl_Position = explode(gl_in[1].gl_Position, normal);
TexCoords = gs_in[1].texCoords;
Normal = gs_in[1].normal;
FragPos = gs_in[1].fragPos;
EmitVertex();
gl_Position = explode(gl_in[2].gl_Position, normal);
TexCoords = gs_in[2].texCoords;
Normal = gs_in[2].normal;
FragPos = gs_in[2].fragPos;
EmitVertex();
EndPrimitive();
}
.frag
无变化
最终效果:
当然这种爆破的效果很差,但也算是使用几何着色器对顶点位置改变的一种应用方式。
© 版权声明
文章版权归作者所有,未经允许请勿转载。
THE END
暂无评论内容