如何在自己的opengl程序中使用GLSL

GLSL,即GL Shading Language,用自己写的程序取代opengl的固定渲染管线的一种语言。

 

之前看了下RenderMonkey,虽然功能不算弱,但使用RenderMonkey却不知道在里面怎么用自己的shader去渲染自己的opengl程序,所以就去找下了关于把shader链接到自己的程序里的方法。

 

因为Microsoft仅支持到opengl1.1,所以使用了glew扩展。

 

测试用的vertex shader和fragment shader非常简单,即把物体显示为红色,代码如下:

//filename:temp.vert void main(void) { gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; } //filename:temp.frag void main(void) { gl_FragColor = vec4(1.0,0.0,0.0,1.0); }

 

shader的类的定义:

class Shader { public: Shader(); ~Shader(); bool ReadVertextShader(char *_fn); bool ReadFragmentShader(char *_fn); void SetShader(); void UseShader(); private: bool TextFileRead(char *_fn,GLchar *&_shader); GLchar *m_VertexShader; GLchar *m_FragmentShader; GLhandleARB m_Program; GLhandleARB m_Vert,m_Frag; };

 

其中m_VertexShader和m_FragmentShader存放shader的字符串,m_Vert、m_Frag和m_Program分别为顶点着色器对象、片段着色器对象和着色器程序对象的句柄。

在用ReadVertextShader()和ReadFragmentShader()方法来读取shader源代码之后,我们就使用SetShader()来编译着色器代码,然后当我们需要使用shader的时候就调用UseShader()即可。

 

SetShader()代码如下:

void Shader::SetShader() { //创建shader对象 m_Vert = glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB); m_Frag = glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB); const GLcharARB *vv = m_VertexShader; const GLcharARB *ff = m_FragmentShader; //添加shader glShaderSourceARB(m_Vert,1,&vv,NULL); glShaderSourceARB(m_Frag,1,&ff,NULL); //编译shader glCompileShaderARB(m_Vert); glCompileShaderARB(m_Frag); //创建程序对象 m_Program = glCreateProgramObjectARB(); //绑定shader到程序对象 glAttachObjectARB(m_Program,m_Vert); glAttachObjectARB(m_Program,m_Frag); //链接程序 glLinkProgramARB(m_Program); }

 

UseShader()代码如下:

void Shader::UseShader() { //使用程序 glUseProgramObjectARB(m_Program); }

 

不过我并没有使用函数来获取编译和链接的日志,这个有待进一步改进。

 

当我们不需要再使用shader时,要先取消shader对象与程序对象的绑定关系,然后再删除这些对象,我把这些步骤放在了析构函数里执行:

Shader::~Shader() { if(NULL != m_VertexShader) delete[] m_VertexShader; if(NULL != m_FragmentShader) delete[] m_FragmentShader; //解除shader与program的绑定关系 glDetachShader(m_Program,m_Vert); glDetachShader(m_Program,m_Frag); //删除shader和program glDeleteObjectARB(m_Vert); glDeleteObjectARB(m_Frag); glDeleteObjectARB(m_Program); }

 

 

 

当我们写好类的实现方法后,就可以在程序里调用这些方法来使用shader了。

我是在WM_CREATE消息里执行这些的,可以根据需要来自行调用。

同时在WM_CREATE消息里使用了glewInit()来初始化glew,不初始化glew的话无法正常使用glew扩展的函数,并且glew的初始化要放在opengl资源创建之后……这个问题弄了我好久才把其解决……

 

程序运行图:

如何在自己的opengl程序中使用GLSL_第1张图片

 

源代码下载:

http://download.csdn.net/source/2422990

你可能感兴趣的:(opengl学习笔记)