Zoeken…


Invoering

Deze voorbeelden tonen verschillende manieren om shaders te laden en te compileren. Alle voorbeelden moeten foutafhandelingscode bevatten .

Opmerkingen

Shader-objecten, zoals gemaakt op basis van glCreateShader doen niet veel. Ze bevatten de gecompileerde code voor een enkele fase, maar ze hoeven niet eens de volledige gecompileerde code voor die fase te bevatten. In veel opzichten werken ze als C- en C ++ -obestanden.

Programma-objecten bevatten het laatste gekoppelde programma. Maar ze hebben ook de status voor de uniforme waarden van het programma, evenals een aantal andere statusgegevens. Ze hebben API's voor het introspecteren van de interfacegegevens van de arcering (hoewel deze alleen uitgebreid werd in GL 4.3). Programma-objecten definiëren de arceringcode die u gebruikt bij het renderen.

Shader-objecten, eenmaal gebruikt om een programma te koppelen, zijn niet langer nodig, tenzij u van plan bent ze te gebruiken om andere programma's te koppelen.

Scheidbare arcering laden in C ++

4.1

Deze code laadt, compileert en koppelt een enkel bestand dat een afzonderlijk shader-programma maakt voor een enkele fase . Als er fouten zijn, wordt het info-logboek voor die fouten opgehaald.

De code gebruikt een aantal algemeen beschikbare C ++ 11-functionaliteit.

#include <string>
#include <fstream>

//In C++17, we could take a `std::filesystem::path` instead of a std::string
//for the filename.
GLuint CreateSeparateProgram(GLenum stage, const std::string &filename)
{
    std::ifstream input(filename.c_str(), std::ios::in | std::ios::binary | std::ios::ate);
    
    //Figure out how big the file is.
    auto fileSize = input.tellg();
    input.seekg(0, ios::beg);
    
    //Read the whole file.
    std::string fileData(fileSize);
    input.read(&fileData[0], fileSize);
    input.close();
    
    //Compile&link the file
    auto fileCstr = (const GLchar *)fileData.c_str();
    auto program = glCreateShaderProgramv(stage, 1, &fileCstr);

    //Check for errors
    GLint isLinked = 0;
    glGetProgramiv(program, GL_LINK_STATUS, &isLinked);
    if(isLinked == GL_FALSE)
    {
        //Note: maxLength includes the NUL terminator.
        GLint maxLength = 0;
        glGetProgramiv(program, GL_INFO_LOG_LENGTH, &maxLength);        

        //C++11 does not permit you to overwrite the NUL terminator,
        //even if you are overwriting it with the NUL terminator.
        //C++17 does, so you could subtract 1 from the length and skip the `pop_back`.
        std::basic_string<GLchar> infoLog(maxLength);
        glGetProgramInfoLog(program, maxLength, &maxLength, &infoLog[0]);
        infoLog.pop_back();

        //The program is useless now. So delete it.
        glDeleteProgram(program);

        //Use the infoLog in whatever manner you deem best.

        //Exit with failure.
        return 0;
    }
    
    return program;
}

Individuele Shader-objectcompilatie in C ++

Het traditionele GLSL-compilatiemodel omvat het compileren van code voor een arceringstrap in een arceringobject en vervolgens het koppelen van meerdere arceringobjecten (die alle fasen omvat die u wilt gebruiken) in een enkel programmaobject.

Sinds 4.2 kunnen programma-objecten worden gemaakt die slechts één arceringstrap hebben. Deze methode koppelt alle shader-fasen in één programma.

Shader-objectcompilatie

#include <string>
#include <fstream>

//In C++17, we could take a `std::filesystem::path` instead of a std::string
//for the filename.
GLuint CreateShaderObject(GLenum stage, const std::string &filename)
{
    std::ifstream input(filename.c_str(), std::ios::in | std::ios::binary | std::ios::ate);
    
    //Figure out how big the file is.
    auto fileSize = input.tellg();
    input.seekg(0, ios::beg);
    
    //Read the whole file.
    std::string fileData(fileSize);
    input.read(&fileData[0], fileSize);
    input.close();
    
    //Create a shader name
    auto shader = glCreateShader(stage);

    //Send the shader source code to GL
    auto fileCstr = (const GLchar *)fileData.c_str();
    glShaderSource(shader, 1, &fileCstr, nullptr);

    //Compile the shader
    glCompileShader(shader);

    GLint isCompiled = 0;
    glGetShaderiv(shader, GL_COMPILE_STATUS, &isCompiled);
    if(isCompiled == GL_FALSE)
    {
        GLint maxLength = 0;
        glGetShaderiv(shader, GL_INFO_LOG_LENGTH, &maxLength);

        //C++11 does not permit you to overwrite the NUL terminator,
        //even if you are overwriting it with the NUL terminator.
        //C++17 does, so you could subtract 1 from the length and skip the `pop_back`.
        std::basic_string<GLchar> infoLog(maxLength);
        glGetShaderInfoLog(shader, maxLength, &maxLength, &infoLog[0]);
        infoLog.pop_back();

        //We don't need the shader anymore.
        glDeleteShader(shader);

        //Use the infoLog as you see fit.
        
        //Exit with failure.
        return 0;
    }

    return shader;
}

Programma-object koppelen

#include <string>

GLuint LinkProgramObject(vector<GLuint> shaders)
{
    //Get a program object.
    auto program = glCreateProgram();

    //Attach our shaders to our program
    for(auto shader : shaders)
        glAttachShader(program, shader);

    //Link our program
    glLinkProgram(program);

    //Note the different functions here: glGetProgram* instead of glGetShader*.
    GLint isLinked = 0;
    glGetProgramiv(program, GL_LINK_STATUS, (int *)&isLinked);
    if(isLinked == GL_FALSE)
    {
        GLint maxLength = 0;
        glGetProgramiv(program, GL_INFO_LOG_LENGTH, &maxLength);

        //C++11 does not permit you to overwrite the NUL terminator,
        //even if you are overwriting it with the NUL terminator.
        //C++17 does, so you could subtract 1 from the length and skip the `pop_back`.
        std::basic_string<GLchar> infoLog(maxLength);
        glGetProgramInfoLog(program, maxLength, &maxLength, &infoLog[0]);
        infoLog.pop_back();
        
        //We don't need the program anymore.
        glDeleteProgram(program);

        //Use the infoLog as you see fit.
        
        //Exit with failure
        return 0;
    }

    //Always detach shaders after a successful link.
    for(auto shader : shaders)
        gldetachShader(program, shader);
        
    return program;
}


Modified text is an extract of the original Stack Overflow Documentation
Licentie onder CC BY-SA 3.0
Niet aangesloten bij Stack Overflow