设置OpenGL程序和着色器

设置OpenGL程序和着色器,opengl,shader,Opengl,Shader,在使用一个程序和一组顶点/片段着色器之后,我需要使用更多的程序,因此我的初始设置函数没有任何参数,不再足够 我将shader_程序和两个着色器源传递到我的设置函数。当我尝试在显示方法中使用该程序时,GLuint程序句柄为零。我目前不明白的是,当我为着色器使用固定源时,为什么这一切都起作用。它是C++程序,我把参数传递错了吗?我没有收到任何错误消息,但屏幕上没有显示任何内容 下面是我用来调用着色器设置函数和函数本身的代码: // Variables GLuint shader_program;

在使用一个程序和一组顶点/片段着色器之后,我需要使用更多的程序,因此我的初始设置函数没有任何参数,不再足够

我将shader_程序和两个着色器源传递到我的设置函数。当我尝试在显示方法中使用该程序时,GLuint程序句柄为零。我目前不明白的是,当我为着色器使用固定源时,为什么这一切都起作用。它是C++程序,我把参数传递错了吗?我没有收到任何错误消息,但屏幕上没有显示任何内容

下面是我用来调用着色器设置函数和函数本身的代码:

// Variables
GLuint shader_program;

const GLchar *vertex_shader =   
"#version 330\n"
""
"layout (location = 0) in vec3 in_position;"
...
"";

// In my main function, I call this to set up the shaders
installShaders(shader_program, vertex_shader, fragment_shader);

// SET-UP-METHOD
void installShaders(GLuint program_handle, const GLchar *vertex_shader_source, const GLchar *fragment_shader_source)
{
// Handles for the shader objects
GLuint   vertex_shader_name;
GLuint fragment_shader_name;

// Status values 
GLint   vertex_shader_compiled;
GLint fragment_shader_compiled;
GLint      successfully_linked;

// Generate shader names
vertex_shader_name   = glCreateShader(GL_VERTEX_SHADER);
fragment_shader_name = glCreateShader(GL_FRAGMENT_SHADER);

// Specify the sources for the shaders
glShaderSource(  vertex_shader_name, 1, (const GLchar**)&vertex_shader_source  , NULL);
glShaderSource(fragment_shader_name, 1, (const GLchar**)&fragment_shader_source, NULL);

// Compile Vertex shader and check for errors
glCompileShader(vertex_shader_name);
glGetShaderiv(vertex_shader_name, GL_COMPILE_STATUS, &vertex_shader_compiled);
printShaderInfoLog(vertex_shader_name);

// Compile Fragment shader and check for errors
glCompileShader(fragment_shader_name);
glGetShaderiv(fragment_shader_name, GL_COMPILE_STATUS, &fragment_shader_compiled);
printShaderInfoLog(fragment_shader_name);

// Exit if the shaders couldn't be compiled correctly
if(!vertex_shader_compiled || !fragment_shader_compiled)
{
    printf("Shaders were not compiled correctly!\n");
    exit(EXIT_FAILURE);
}

// Generate program name
program_handle = glCreateProgram();

// Attach shaders to the program
glAttachShader(program_handle, vertex_shader_name);
glAttachShader(program_handle, fragment_shader_name);

// Link program and check for errors
glLinkProgram(program_handle);
glGetProgramiv(program_handle, GL_LINK_STATUS, &successfully_linked);
printProgramInfoLog(program_handle);

// Exit if the program couldn't be linked correctly
if(!successfully_linked)
{
    printf("Program was not linked correctly!\n");
    exit(EXIT_FAILURE);
}

// Set up initial values of uniform variables
glUseProgram(program_handle);

location_projectionMatrix = glGetUniformLocation(program_handle, "myProjectionMatrix");
printf("Location of the uniform -->myProjectionMatrix<--- : %i\n", location_projectionMatrix);
projectionMatrix = glm::mat4(1.0f);
glUniformMatrix4fv(location_projectionMatrix, 1, GL_FALSE, glm::value_ptr(projectionMatrix));

location_modelViewMatrix = glGetUniformLocation(program_handle, "myModelViewMatrix");
printf("Location of the uniform -->myModelViewMatrix<--- : %i\n", location_modelViewMatrix);
modelViewMatrix = glm::mat4(1.0f);
glUniformMatrix4fv(location_modelViewMatrix, 1, GL_FALSE, glm::value_ptr(modelViewMatrix));

glUseProgram(0);

// Everything worked
printf("Shaders were set up correctly!\n");
}
//变量
GLuint shader_程序;
常量GLchar*顶点着色器=
“#版本330\n”
""
“vec3中的布局(位置=0)处于_位置;”
...
"";
//在我的主函数中,我调用它来设置着色器
安装着色器(着色器程序、顶点着色器、片段着色器);
//安装方法
void安装着色器(GLuint程序\u句柄、常量GLchar*顶点\u着色器\u源、常量GLchar*片段\u着色器\u源)
{
//着色器对象的句柄
GLuint顶点\着色器\名称;
GLuint片段\u着色器\u名称;
//状态值
闪烁顶点着色器编译;
闪烁片段\u着色器\u已编译;
闪烁成功链接;
//生成着色器名称
顶点着色器名称=glCreateShader(GL顶点着色器);
fragment\u shader\u name=glCreateShader(GL\u fragment\u shader);
//指定着色器的源
glShaderSource(顶点着色器名称,1,(常量GLchar**)和顶点着色器源,NULL);
glShaderSource(片段着色器名称,1,(常量GLchar**)和片段着色器源,NULL);
//编译顶点着色器并检查错误
glCompileShader(顶点着色器名称);
glGetShaderiv(顶点着色器名称、顶点着色器编译状态和顶点着色器编译状态);
printShaderInfoLog(顶点着色器名称);
//编译片段着色器并检查错误
glCompileShader(片段着色器名称);
glGetShaderiv(片段着色器名称、GL编译状态和片段着色器编译状态);
printShaderInfoLog(片段\着色器\名称);
//如果无法正确编译着色器,请退出
如果(!顶点着色器已编译| |!片段着色器已编译)
{
printf(“着色器未正确编译!\n”);
退出(退出失败);
}
//生成程序名
program_handle=glCreateProgram();
//将着色器附加到程序
glAttachShader(程序句柄、顶点着色器名称);
glAttachShader(程序句柄、片段着色器名称);
//链接程序并检查错误
glLinkProgram(程序句柄);
glGetProgramiv(程序句柄、GL链接状态和成功链接);
printProgramInfoLog(程序句柄);
//如果无法正确链接程序,请退出
如果(!已成功链接)
{
printf(“程序链接不正确!\n”);
退出(退出失败);
}
//设置统一变量的初始值
glUseProgram(程序句柄);
location_projectionMatrix=glGetUniformLocation(程序句柄,“myProjectionMatrix”);

printf(“统一-->myProjectionMatrixmyModelViewMatrix的位置问题在于,将GLSL着色器程序名(从
glCreateShader
返回的值)存储到的变量按值传递到例程中。因此,当函数返回时,其值丢失。通过引用传递值(当作为指针或C++引用),当函数退出时,值将被保留,并且你可以在应用程序的其他部分引用着色器。

尝试使你的<代码>程序句柄< /Cord>指针或引用(如果你使用C++)当函数返回时,从<代码> GCREATEATEP> <代码>返回的值丢失,因为您把“代码>程序”句柄作为值进入您的函数。欢迎您。猜我应该做一个回答。是的,也许还有一个问题……因为我对OpenGL和C++也是相当新的……我是通过着色器源“最佳”吗?“方式?是的。
glShaderSource
以多种方式处理源代码。如果您将着色器指定为一个以NULL结尾的字符串,那么您执行该操作的方式就是有效的。当然,您可以始终从文件加载它们。我会构建一个类来封装着色器操作,这样只需一次调用即可创建程序。