着色器类

  1. 头文件 .h

    #pragma once
    
    #include <glad/glad.h> //包含glad来获取所有必须的 OpenGL头文件
    
    #include <string>
    #include <fstream>
    #include <sstream>
    #include <iostream>
    
    class Shader
    {
    public:
     unsigned int ID;
    
    public:
     Shader(const GLchar* vertexPath, const GLchar* fragmentPath);
    
     void use();//激活Shader
    
     //uniform工具函数
     void setBool(const std::string& name, bool value) const;
     void setInt(const std::string& name, int value) const;
     void setFloat(const std::string& name, float value) const;
    };
    
    
    
  2. 源文件 .cpp

    #include "Shader.h"
    
    using namespace std;
    
    Shader::Shader(const GLchar* vertexPath, const GLchar* fragmentPath)
    {
     //从文件中读取Shader代码,即GLSL代码
     string vertexCode;
     string fragmentCode;
     ifstream vShaderFile;
     ifstream fShaderFile;
    
     //保证ifstream对象可以抛出异常
     vShaderFile.exceptions(ifstream::failbit | ifstream::badbit);
     fShaderFile.exceptions(ifstream::failbit | ifstream::badbit);
     try
     {
         //打开文件流
         vShaderFile.open(vertexPath);
         fShaderFile.open(fragmentPath);
    
         //将文件缓冲内容读取到流中
         stringstream vShaderStream, fShaderStream;
         vShaderStream << vShaderFile.rdbuf();
         fShaderStream << fShaderFile.rdbuf();
    
         //关闭文件流
         vShaderFile.close();
         fShaderFile.close();
    
         //将流中的数据转换到string变量中
         vertexCode = vShaderStream.str();
         fragmentCode = fShaderStream.str();
     }
     catch(ifstream::failure e)
     {
         cout << "ERROR::SHADER::FILE_NOT_SUCCESSFULLY_READ" << endl;
     }
     const char* vShaderCode = vertexCode.c_str();
     const char* fShaderCode = fragmentCode.c_str();
    
     //编译Shader
     unsigned int vertex, fragment;
     int success;
     char infoLog[512];
    
     //vertex shader
     vertex = glCreateShader(GL_VERTEX_SHADER);
     glShaderSource(vertex, 1, &vShaderCode, NULL);
     glCompileShader(vertex);
     glGetShaderiv(vertex, GL_COMPILE_STATUS, &success);
     if (!success)
     {
         glGetShaderInfoLog(vertex, 512, NULL, infoLog);
         cout << "ERROR::SHADER::VERTEX::COMPILATION_FAILED\n" << infoLog << endl;
     }
    
     //fragment shader
     fragment = glCreateShader(GL_FRAGMENT_SHADER);
     glShaderSource(fragment, 1, &fShaderCode, NULL);
     glCompileShader(fragment);
     glGetShaderiv(fragment, GL_COMPILE_STATUS, &success);
     if (!success)
     {
         glGetShaderInfoLog(fragment, 512, NULL, infoLog);
         cout << "ERROR::SHADER::FRAGMENT::COMPILATION_FAILED\n" << infoLog << endl;
     }
    
     //shader program
     ID = glCreateProgram();
     glAttachShader(ID, vertex);
     glAttachShader(ID, fragment);
     glLinkProgram(ID);
     glGetProgramiv(ID, GL_LINK_STATUS, &success);
     if (!success)
     {
         glGetProgramInfoLog(ID, 512, NULL, infoLog);
         cout << "ERROR::SHADER::PROGRAM::LINKING_FAILED\n" << infoLog << endl;
     }
    
     //free(delete) shader
     glDeleteShader(vertex);
     glDeleteShader(fragment);
    }
    
    void Shader::use()
    {
     glUseProgram(ID);
    }
    
    //设定Shader中传入的uniform变量
    void Shader::setBool(const std::string& name, bool value) const
    {
     glUniform1i(glGetUniformLocation(ID, name.c_str()), (int)value);
    }
    
    void Shader::setInt(const std::string& name, int value) const
    {
     glUniform1i(glGetUniformLocation(ID, name.c_str()), value);
    }
    
    void Shader::setFloat(const std::string& name, float value) const
    {
     glUniform1f(glGetUniformLocation(ID, name.c_str()), value);
    }
    
    
  3. 简要解释

    • glCreateShader:创建OpenGL可用的shader对象,参数用于指定shader的类型
    • glShaderSource:将shader的代码(字符数组)传入shader对象中,第一个参数是shader对象,第二个参数是传递的源码字符数组的数量,第三个参数是shader源码字符数组,第四个参数设为NULL,暂且不做追究
    • glCompileShader:对shader对象进行编译
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容