OpenGL学习错误列表Error List

OpenGL学习错误列表Error List

这是一份学习OpenGL时遇到的错误记录,随着实践进行,此列表将不断更新。

1.undefined reference to `glBegin'

解决办法:编译时需要连接libGL.so , libGLU.so, libglut.so三个库,或者通过添加库路径到连接路径,或者通过-l参数添加链接。

使用命令行方式:

wangdq@wangdq:~/OpenGL$ gcc example.c -o example.out -lGL -lGLU -lglut
wangdq@wangdq:~/OpenGL$ ./example.out

或者使用eclipe c/c++ for linux在工程的属性下设置如下也可以编译成功:


OpenGL学习错误列表Error List_第1张图片

2.顶点着色器和片元着色器中传递颜色失败,导致无法渲染

如果着色器中变量输入输出错误,那么将会导致无法渲染。例如这里从《Learning Modern 3D Graphics Programming》例子中,从顶点着色器传递颜色给片元着色器,自己书写两个着色器代码为:

 vertex shader

#version 330

layout (location = 0) in vec4 pos;
layout (location = 1) in vec4 color;

smooth out vec4 outputColor;

void main()
{
    gl_Position = pos;
    outputColor = incolor;
}

Fragment shader

#version 330

smooth in vec4 incolor;

out vec4 outputColor;

void main()
{
    outputColor = incolor;
}

初看好像没有什么错误,运行时则无法渲染。

错误原因:OpenGL要求,前一阶段的输出变量和下一阶段的输入变量必须名称和类型相同,这里使用了smooth限定符,那么两者也必须相同。这里顶点着色器输出为outputColor,而片元着色器输入却是incolor,因此造成错误。解决办法即改成一致类型和名称。

3. 创建的windows窗口标题栏异常

使用了代码:

glutInitDisplayMode( GLUT_RGBA|GLUT_DOUBLE|GL_DEPTH);

或者:

glutInitDisplayMode(GLUT_RGBA|GLUT_DEPTH|GL_DOUBLE);造成窗口标题栏显示异常。

错误原因:  编译器并不会报错,但是glut使用的常量是GLUT_xxx,而不是GL_XX,因此造成窗口标题栏错误。

4.编译《Learning Modern 3D Graphics Programming》一书源代码时glloadD.lib版本不同造成的错误

在编译该书World Scene示例时,从网上下载的Unofficial OpenGL Software Development Kit与作者源代码中的glsdk版本不一致,导致编译后的lib文件版本不同,因此总是提示:

unresolved symbol glload::LoadFunctions错误。

错误原因: c++ static lib版本不一致造成的错误。

解决方法:windows下使用dumpbin工具查看lib导出函数,对比发现:

OpenGL学习错误列表Error List_第2张图片

两者包含的LoadFunctions函数根本不一样,因此使用新版本的lib,而是用旧版的头文件造成了不一致问题。

关于dumpbin /LINKERMEMBER 选项含义请参考:microsoft.

这里提醒我们,注意编译时lib与头文件版本问题。更应该在库中包含关于版本的信息,参考stackoverflow,更好的做法应该是:

方法一:   在头文件中声明lib版本如下:

#define MYLIB_MAJOR_VERSION 1
#define MYLIB_MINOR_VERSION 2
#define MYLIB_REVISION 3
#define MYLIB_VERSION "1.2.3"
#define MYLIB_VERSION_CHECK(maj, min) ((maj==MYLIB_MAJOR_VERSION) && (min<=MYLIB_MINOR_VERSION))

在使用的程序中进行检查:

if (! MYLIB_VERSION_CHECK(1, 2)) {
    fprintf(stderr, "ERROR: incompatible library version\n");
    exit(-1);
}

方法二:   可以在lib中包含版本信息如下:

struct {
    const char* string;
    const unsigned major;
    const unsigned minor;
    const unsigned revision;
} mylib_version = {
    MYLIB_VERSION, MYLIB_MAJOR_VERSION, MYLIB_MINOR_VERSION, MYLIB_REVISION
};

在lib中存储这个mylib_version结构体,在lib中提供验证函数,以便在应用程序中调用来进行版本验证。

这种方式更值得提倡。

5.glDrawElements 无法渲染

函数原型为:

void glDrawElements(    GLenum mode,
     GLsizei count,
     GLenum type,
     GLsizeiptr indices);

使用glDrawElements要注意:

1)同glVertexAttribPointer一样,当有缓存对象绑定到GL_ARRAY_BUFFER时,glVertexAttribPointer的最后一个参数解释为缓存中的偏移量;当有缓存对象绑定到GL_ELEMENT_ARRAY_BUFFER时glDrawElements的最后一个参数解释为缓存中的偏移量。因此,如果使用VBO/VAO方式来执行glDrawElements时,要注意最后一个参数是偏移量(byte-offset into the element array at which the index data begins),而不再是指向索引存贮位置的指针(Specifies a pointer to the location where the indices are stored.)。这段内容参考自:stackoverflowNo display from glDrawElements

2)注意count参数的意义,它表示将使用多少个索引进行渲染,这与渲染多少个几何图形例如三角形数目不同。

例如索引为:

const GLshort indices[] = {
	0,1,3,
	1,2,3,
	0,2,1,
	0,3,2
};

这个时候传入的count不能是4,而应该是4*3 = 12。如果传入4将只能绘制部分,例如一个三角形。

更好的方式是使用宏定义:

#define ARRAY_COUNT( array ) (sizeof( array ) / (sizeof( array[0] ) * (sizeof( array ) != sizeof(void*) || sizeof( array[0] ) <= sizeof(void*))))

然后这样书写:

glDrawElements(GL_TRIANGLES,ARRAY_COUNT(indices),GL_UNSIGNED_SHORT,0);


No.6 ubuntu error: GLSL 3.30 is not supported. Supported versions are: 1.00 ES, 1.10, 1.20, and 1.30

这是一个关于显卡驱动支持的错误.

解决办法:

ubuntu 可能使用的附加驱动如下图所示,默认一般使用X.org X Server驱动,它一般只能支持GLSL 1.50左右,

我的电脑上选择NVIDIA驱动331安装后重启,可以根据需要选择你的驱动程序.

OpenGL学习错误列表Error List_第3张图片

安装完驱动后重启,可以利用glxinfo(sudo apt-get install mesa-utils安装该工具)查看系统OpenGL信息如下:

 glxinfo | grep OpenGL
OpenGL vendor string: NVIDIA Corporation
OpenGL renderer string: GeForce G 105M/PCIe/SSE2
OpenGL core profile version string: 3.3.0 NVIDIA 331.104
OpenGL core profile shading language version string: 3.30 NVIDIA via Cg compiler
OpenGL core profile context flags: (none)
OpenGL core profile profile mask: core profile
OpenGL core profile extensions:
OpenGL version string: 3.3.0 NVIDIA 331.104
OpenGL shading language version string: 3.30 NVIDIA via Cg compiler
OpenGL context flags: (none)
OpenGL profile mask: (none)
OpenGL extensions:
可以看到现在支持GLSL 3.30的着色器语言啦.

No.7 Inconsistency detected by ld.so: dl-version.c: 224: _dl_check_map_versions: Assertion `needed != ((void *)0)' failed!

ubuntu下,安装完nvidia-331驱动后,新建的OpenGL工程,编译出现错误.

解决办法,为工程添加GL链接,例如:-L/usr/lib/nvidia-331/

我的codeblocks环境,添加如下:

OpenGL学习错误列表Error List_第4张图片


同时添加上相关其他库(glut/glew等)后即可,编译log显示的命令为:

g++ -Wall -std=c++11 -g  -c /home/xxx/OpenGLEx/KnochSnow/main.cpp -o obj/Debug/main.o
g++ -Wall -std=c++11 -g  -c /home/xxx/OpenGLEx/KnochSnow/shader.cpp -o obj/Debug/shader.o
g++  -o bin/Debug/KnochSnow obj/Debug/main.o obj/Debug/shader.o 
 -L/usr/lib/nvidia-331/  
-lGL -lX11 /usr/lib/i386-linux-gnu/libglut.so /usr/lib/i386-linux-gnu/libGLEW.so

这样编译通过,运行正常了.

你可能感兴趣的:(OpenGL学习错误列表Error List)