GLUT教程
初始化设置
建立一个main函数,完成必须的初始化和开启事件处理循环。
所有的GLUT函数都有glut前缀并且那些完成一些初始化的函数有glutInit前缀。你首先要做的是调用函数glutInit()。
----------------------------------------
Void glutInit(int*argc,char**argv);
参数:
Argc:一个指针,指向从main()函数传递过来的没更改的argc变量。
Argv:一个指针,指向从main()函数传递过来的没更改的argv变量。
在初始化GLUT后,我们开始定义我们的窗口。首先确定窗口位置(它默认的是屏幕左上角),我们使用函数glutInitWindowPosition()。
-----------------------------------------------
Void glutInitWindowPositon(int x,int y);
参数:
X: 距离屏幕左边的像素数。-1是默认值,意思就是由窗口管理程序决定窗口出现在哪里。如果不使用默认值,那你就自己设置一个值。
Y:距离屏幕上边的像素数。和X一样。
---------------------------------------------------
设置窗口大小,使用函数glutInitWindowSize()。
Void glutInitWindowSize(int width,int height);
参数:
Width:窗口的宽度。
Height:窗口的高度。
同样width,height也只是一个参考数字。避免使用负数。
-------------------------------------------------------------
接下来。你应该使用函数glutInitDisplayMode()定义显示方式。
Void glutInitDisplayMode(unsighed int mode)
参数:
Mode――可以指定下列显示模式
Mode参数是一个GLUT库里预定义的可能的布尔组合。你使用mode去指定颜色模式,数量和缓冲区类型。
指定颜色模式的预定义常量有:
1:GLUT_RGBA或者GLUT_RGB。指定一个RGBA窗口,这是一个默认的颜色模式。
2:GLUT_INDEX。指定颜色索引模式。
这个显示模式还允许你选择单缓冲区或双缓冲区窗口。
1:GLUT_SINGLE.单缓冲区窗口。
2:GLUT_BUFFER.双缓冲区窗口,这是产生流畅动画必须选的。
还可以指定更多,如果你想指定一组特殊的缓冲的话,用下面的变量:
1:GLUT_ACCUM.累积缓冲区。
2:GLUT_STENCIL.模板缓冲区。
3:GLUT_DEPTH.深度缓冲区。
假定你想要一个有单缓冲区,深度缓冲区的RGB窗口,你用“或“(|)操作符来建立你想要的显示模式。
…………….
glutInitDisplayMode(GLUT_RGB|GLUT_SINGLE|GLUT_DEPTH);
---------------------------------------------------------------------
经过上面的这些步骤后,就可以调用函数glutCreateWindow()来创建窗口了。
Int glutCreateWindow(char* title);
参数:
Title:设置窗口的标题。
glutCreateWindow()的返回值是一个窗口标识符。
---------------------------------------------------------------
现在就有一些代码来完成所有的初始化操作。
#include<gl/glut.h>
void main(int argc,char**argv)
{
glutInit(&argc,argv);
glutInitDisplayMode(GLUT_DEPTH|GLUT_SINGLE|GLUT_RGBA);
glutInitWindowPosition(100,100);
glutInitWindowSize(320,320);
glutCreateWindow(“GLUT Tutorial”);
}
如果你运行上述代码,你将会得到一个空的黑的控制台窗口,而没有OpenGL窗口。并且控制台窗口将很快消失。
在我们渲染一些东西前,还有两件事需要处理。第一告诉GLUT哪个函数负责渲染。我们创建一个简单的渲染的函数。下面的这个函数将会清除颜色缓冲区并画一个三角形。
...
void renderScene(void) {
}
上面的函数的名字你可以自己取一个。现在你必须告诉GLUT使用我们上面的函数来进行渲染。这个叫寄存回调
-----------------------------------------------------------
void glutDisplayFunc(void (*func)(void));
参数:
func: 当窗口需要被重绘是调用的函数的名称。注意使用NULL作为实参是错误的。
最后一件事是告诉GLUT我们准备进入应用程序事件处理循环。GLUT提供了一个函数让程序进入一个永不结束的循环。一直等待处理下一个事件。函数是glutMainLoop()。
void glutMainLoop(void)
到目前为止所有的代码都列在下面。如果你运行代码,将会得到一个控制台窗口,和一个画着一个白色三角形的OpenGL窗口,出现在你设置的位置,并有着你设置的尺寸。
#include <GL/glut.h>
}
void main(int argc, char **argv) {
}
=======================================================================================
******************************************************************************************
你将看到两个窗口:一个控制台窗口,一个OpenGL窗口。
现在改变窗口大小使高度与宽度不再相等,这时三角形发生变形。这是因为你没有正确设置投影矩阵。默认的是透视投影矩阵且高宽比为1.因此高宽比改变了,投影就会变形。因此只要高宽比改变了,投影就应该重新计算。
GLUT定义了当窗口大小改变时哪一个函数应该被调用。此外,这个函数还会在窗口初次被创建时调用,保证初始化窗口不是正方形的时候渲染也不会变形出错。
这个函数是glutReshapeFunc()。
void glutReshapeFunc(void(*func) (int width,int height));参数:
func: 指负责设置正确投影的函数的名称。
因此我们必须做的第一件事是回到main()函数。在上一章的代码里加入对glutReshapeFunc()的调用,让我们把负责窗口尺寸的函数叫做changeSize。现在的代码如下。
void main(int argc, char **argv) {
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DEPTH | GLUT_SINGLE | GLUT_RGBA);
glutInitWindowPosition(100,100);
glutInitWindowSize(320,320);
glutCreateWindow("3D Tech- GLUT Tutorial");
glutDisplayFunc(renderScene);
// Here is our new entry in the main function
glutReshapeFunc(changeSize);
glutMainLoop();
}
下面我们需要做的就是定义函数changeSize()。从glutReshapeFunc()函数的声明可以看到,changSize()函数有两个形参。。这两个参数代表新的窗口高度和宽度。
void changeSize(int w, int h) {
//
防止除数即高度为0,
(
你可以设置窗口宽度为0).
if(h == 0)
h = 1;
float ratio = 1.0* w / h;
//
单位化投影矩阵。
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
//
设置视口大小为增个窗口大小
glViewport(0, 0, w, h);
//
设置正确的投影矩阵
gluPerspective(45,ratio,1,1000);
//
下面是设置模型视图矩阵
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt(0.0,0.0,5.0, 0.0,0.0,-1.0,
0.0f,1.0f,0.0f);
}
第一步是计算高宽比(wight/height)。注意为了计算正确,我们必须保证高度不为0。
接着,设置当前矩阵为投影矩阵,这个矩阵定义了一个可视空间(viewing volume)。
调用一个单位矩阵来初始化投影矩阵。然后用函数glViewport把视口设置为整个窗口。也可以设置不同的值。函数中(0,0)指定了视口的左下角,(w,h)指定了视口矩形的大小。这个坐标是和客户区域有关的,而不是屏幕坐标。。
gluPerspective函数是其他OpenGL库(GLU库)里的一个函数。
最后就是设置模型观测矩阵。调用GL_MODELVIEW把当前矩阵设为模型观测矩阵。gluLookAt()也是GLU库里的一个函数。