如何使用glCreateShaderProgram?

How to use glCreateShaderProgram?

http://docs.gl/gl4/glCreateShaderProgram

伪代码:

const GLuint shader = glCreateShader(type);
if (shader) {
    glShaderSource(shader, count, strings, NULL);
    glCompileShader(shader);
    const GLuint program = glCreateProgram();
    if (program) {
        GLint compiled = GL_FALSE;
        glGetShaderiv(shader, GL_COMPILE_STATUS, &compiled);
        glProgramParameteri(program, GL_PROGRAM_SEPARABLE, GL_TRUE);
        if (compiled) {
            glAttachShader(program, shader);
            glLinkProgram(program);
            glDetachShader(program, shader);
        }
        /* append-shader-info-log-to-program-info-log */
    }
    glDeleteShader(shader);
    return program;
}
else {
    return 0;
}

我不知道可以一次编译多个着色器。我遇到的问题是文档没有告诉我如何调用它。

如果要编译顶点+片段着色器,应该指定什么类型?最初我尝试 glCreateShader(GL_VERTEX_SHADER | GL_FRAGMENT_SHADER); 但后来它抱怨有两个 main 函数。 OpenGL 可能将两个着色器解释为一个着色器。

我认为不可能一次创建多个着色器。 glCreateShaderProgram 只做为您创建着色器所需的一切(创建、编译、link)。

如果您查看 opengl.org 上的文档,您会发现一次只能创建一个着色器。您只能指定以下 GLenum 之一:GL_COMPUTE_SHADERGL_VERTEX_SHADERGL_TESS_CONTROL_SHADERGL_TESS_EVALUATION_SHADERGL_GEOMETRY_SHADERGL_FRAGMENT_SHADER.

我认为你的想法是对的。 OpenGL 可能将两个着色器解释为一个,这是不可能的。

你可以这样做:

glCreateShader(GL_VERTEX_SHADER);
glCreateShader(GL_FRAGMENT_SHADER);

查看我提供的来源的描述字段。它将解释如何进一步处理着色器对象。

我不确定为什么可以传递字符串数组。如果您在不同的源代码文件中有多个小的着色器代码片段。

来源:https://www.opengl.org/sdk/docs/man/html/glCreateShader.xhtml

来自 linked 文档:

glCreateShaderProgram creates a program object containing compiled and linked shaders for a single stage specified by type.

[强调我的]

这意味着您不能将它与针对渲​​染管线不同部分的着色器列表一起使用。


但是,您或许可以修改示例实现以满足您的需求。它需要通过将第一个参数替换为 GLenumcount 元素的数组来更改函数签名,然后将实现变成每对 shader[i], strings[i] 上的循环以将它们添加到生成的程序,其中 shader 是分别与每个源字符串关联的着色器 ID 数组。

一旦编译了每个着色器,代码就会 link 整体进入一个程序,释放所有着色器 ID,并 return 程序 ID(实际实现留作练习) .

glCreateShaderProgram() 只编译和 link 一个着色器。最后一个参数是一个字符串数组,就像 glShaderSource() 的相应参数一样,它也用于指定 one 着色器的来源。能够传递多个字符串只是为这两个调用提供了便利。例如,如果您将着色器代码作为字符串数组(比如每行一个),则可以直接将它们传入,而无需先连接它们。

glCreateShaderProgram() 旨在与程序管道对象结合使用。此机制允许您组合来自多个程序的着色器,而无需 link 它们。典型的调用序列如下所示:

GLuint vertProgId = glCreateShaderProgram(GL_VERTEX_SHADER, 1, &vertSrc);
GLuint fragProgId = glCreateShaderProgram(GL_FRAGMENT_SHADER, 1, &fragSrc);

GLuint pipelineId = 0;
glGenProgramPipelines(1, &pipelineId);

glUseProgramStages(pipelineId, GL_VERTEX_SHADER_BIT, vertProgId);
glUseProgramStages(pipelineId, GL_FRAGMENT_SHADER_BIT, fragProgId);

glBindProgramPipeline(pipelineId);