我正在研究图形管道,我对镶嵌阶段有一些疑问。我的基本阅读材料是《OpenGL SuperBible第六版:综合教程和参考》。
问题 #1:在 SuperBible 中,我读到顶点着色器每个补丁顶点(或曲面细分上下文中的控制点)运行一次,一次“馈送”细分控制着色器一个顶点。反过来,TCS 在顶点组上运行。虽然在这个链接中
http://web.engr.oregonstate.edu/~mjb/cs519/Handouts/tessellation.1pp.pdf
它说 TCS 每个“输出顶点”运行一次(我假设是 VS 输出的顶点)。两者哪一个是真的?我弄错了整个事情还是其中一个错了?
问题 #2:这个是关于 GLSL 的。以下着色器来自 SuperBible 示例。
顶点着色器
#version 410 core
void main(void)
{
const vec4 vertices[] = vec4[](vec4( 0.25, -0.25, 0.5, 1.0),
vec4(-0.25, -0.25, 0.5, 1.0),
vec4( 0.25, 0.25, 0.5, 1.0));
gl_Position = vertices[gl_VertexID];
}
镶嵌控制着色器
#version 410 core
layout (vertices = 3) out;
void main(void)
{
if (gl_InvocationID == 0)
{
gl_TessLevelInner[0] = 5.0;
gl_TessLevelOuter[0] = 5.0;
gl_TessLevelOuter[1] = 5.0;
gl_TessLevelOuter[2] = 5.0;
}
gl_out[gl_InvocationID].gl_Position = gl_in[gl_InvocationID].gl_Position;
}
a) 标记 gl_VertexID(在顶点着色器上)和 gl_InvocationID(在 TCS 上)是什么意思?它们让我感到困惑,因为它们没有在程序的任何地方明确声明。
b) 我知道在 TCS 中 gl_Position 变量从顶点着色器获取其数据,但在顶点着色器中没有任何地方明确声明 gl_Position 应该是输出(例如,在主程序之前使用 out 关键字)。我认为要通过各种着色器和管道阶段传递数据,必须明确声明具有相同名称的输入和输出,那么在这种情况下发生了什么?