這裏有三個書上的代碼,芃都給標了註釋了,方便大家理解。
- 繪製矩形
最基礎的代碼,需學會glut的基本操作。
#include <gl/glut.h>
void Initial(void) //初始化操作
{
glClearColor(1.0f, 1.0f, 1.0f, 1.0f); //設置窗口背景顏色爲白色(清空當前顏色緩衝)
glMatrixMode(GL_PROJECTION); //設置投影參數;GL_PROJECTION 投影, GL_MODELVIEW 模型視圖, GL_TEXTURE 紋理
gluOrtho2D(0.0,200.0,0.0,150.0); //更改模型座標範圍
}
void Display(void)
{
glClear(GL_COLOR_BUFFER_BIT); //用當前背景色填充窗口
glColor3f(1.0f, 0.0f, 0.0f); //設置當前的繪圖顏色爲紅色
glRectf(50.0f, 100.0f, 150.0f, 50.0f); //繪製一個矩形
glFlush(); //處理所有的OpenGL程序,保證所有繪圖命令的執行
}
int main(int argc, char* argv[])
{
glutInit(&argc, argv); //初始化glut庫
glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB); //初始化窗口的顯示模式
glutInitWindowSize(400,300); //設置窗口的尺寸
glutInitWindowPosition(100,120); //設置窗口的位置
glutCreateWindow("矩陣"); //創建一個名爲矩形的窗口
glutDisplayFunc(Display); //設置當前窗口的顯示回調函數,用於完成繪製
Initial(); //完成窗口初始化
glutMainLoop(); //啓動主GLUT事件處理無限循環
return 0;
}
- 橡皮筋技術
書上的代碼,需瞭解鼠標事件和雙緩衝區的用法。理解這個程序是咋實現的可能需要花點功夫,如果不想看了,直接看鼠標事件那個函數,瞭解它的參數設置和鼠標事件類型。
#include <gl/glut.h>
int iPointNum = 0; //已確定點的數目
int x1=0,x2=0,y1=0,y2=0; //確定的點座標
int winWidth = 400, winHeight = 300; //窗口的寬度和高度
void Initial(void)
{
glClearColor(1.0f, 1.0f, 1.0f, 1.0f);//設置窗口背景顏色爲白色(清空當前顏色緩衝)
}
void ChangeSize(int w, int h)
{
winWidth = w; winHeight = h; //更改窗口的長和寬
glViewport(0, 0, w, h); //指定窗口顯示區域
glMatrixMode(GL_PROJECTION); //設置投影參數
glLoadIdentity(); //重置當前指定的矩陣爲單位矩陣
gluOrtho2D(0.0,winWidth,0.0,winHeight); //更改模型座標範圍
}
void Display(void)
{
glClear(GL_COLOR_BUFFER_BIT); //用當前背景色填充窗口
glColor3f(1.0f, 0.0f, 0.0f); //設置當前的繪圖顏色爲紅色
if(iPointNum >= 1) {
glBegin(GL_LINES); //繪製直線段
glVertex2i(x1,y1); //畫點函數,第一個點
glVertex2i(x2,y2); //第二個點
glEnd(); //繪製結束
}
glutSwapBuffers(); //交換緩衝區
}
void MousePlot(GLint button, GLint action, GLint xMouse, GLint yMouse) //typedef int GLint
{
if(button == GLUT_LEFT_BUTTON && action == GLUT_DOWN) { //鼠標按左鍵控制操作,設置點的位置
if(iPointNum == 0 || iPointNum == 2){ //當點數爲空或者爲滿時
iPointNum = 1; //設置點爲1
x1 = xMouse; y1 = winHeight - yMouse; //將鼠標左鍵輸入的位置的橫座標和縱座標分別輸入到x1和y1裏
}
else {
iPointNum = 2; //點數設置爲2
x2 = xMouse; y2 = winHeight - yMouse; //將鼠標左鍵輸入的位置的橫座標和縱座標分別輸入到x1和y1裏
glutPostRedisplay(); //指定窗口重新繪製
}
}
if(button == GLUT_RIGHT_BUTTON && action == GLUT_DOWN){ //如果是鼠標右鍵操作
iPointNum = 0; //將點數設爲空
glutPostRedisplay(); //取消界面,並且重新繪製
}
}
void PassiveMouseMove (GLint xMouse, GLint yMouse) //鼠標移動響應函數
{
if(iPointNum == 1) { //一個點的時候
x2 = xMouse; //設置橫縱座標的位置
y2 = winHeight - yMouse;
glutPostRedisplay(); //指定窗口重新繪製
}
}
int main(int argc, char* argv[])
{
glutInit(&argc, argv); //初始化庫函數
glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB); //使用雙緩存及RGB模型
glutInitWindowSize(400,300); //設置窗口大小
glutInitWindowPosition(100,100); //設置窗口位置
glutCreateWindow("橡皮筋技術"); //設置窗口姓名
glutDisplayFunc(Display); //執行繪圖函數
glutReshapeFunc(ChangeSize); //指定窗口在整形回調函數
glutMouseFunc(MousePlot); //指定鼠標響應函數
glutPassiveMotionFunc(PassiveMouseMove); //指定鼠標移動響應函數
Initial(); //重置圖形背景
glutMainLoop(); //無限循環
return 0;
}
- 反走樣處理
書上的代碼。
涉及到顯示列表繪圖的方法,簡單的解釋就是,它就像一個函數一樣,在glNewList()和glEndList()內的語句,可以通過glCallList()函數反覆調用。
反走樣處理在void Displayw(void)中,主要了解這一塊,這裏註釋只是說了每個函數是幹嘛的,具體原理想要了解的話,自己查資料叭。
#include <gl/glut.h>
GLuint lineList; //指定顯示列表ID
void Initial()
{
glClearColor(1.0f, 1.0f, 1.0f, 0.0f);//設置窗口背景顏色(清空當前顏色緩衝)
glLineWidth(12.0f); //設置線的寬度
glColor4f (0.0, 0.6, 1.0, 1.0); //設置爲顏色
lineList = glGenLists(1); //創建顯示列表ID
glNewList(lineList, GL_COMPILE); //定義顯示列表
glBegin(GL_LINE_LOOP); //繪製線段
glVertex2f(1.0f, 1.0f); //第一個點
glVertex2f(4.0f, 2.0f); //第二個點
glVertex2f(2.0f, 5.0f); //第三個點
glEnd(); //繪製結束
glEndList(); //顯示列表結束
}
void ChangeSize(GLsizei w, GLsizei h) //typedef int GLsizei
{
if(h == 0) h = 1;
glViewport(0, 0, w, h); //指定窗口位置
glMatrixMode(GL_PROJECTION); //接下來進行投影操作
glLoadIdentity(); //重置當前指定的矩陣爲單位矩陣.
if(w<=h)
gluOrtho2D(0.0, 5.0, 0.0, 6.0*(GLfloat)h/(GLfloat)w);//更改模型座標範圍
else
gluOrtho2D(0.0, 5.0*(GLfloat)w/(GLfloat)h, 0.0, 6.0);//更改模型座標範圍
glMatrixMode(GL_MODELVIEW); //模型視景的操作
glLoadIdentity(); //重置當前指定的矩陣爲單位矩陣
}
void Displayt(void)
{
glClear(GL_COLOR_BUFFER_BIT);//用當前背景色填充窗口
glCallList(lineList); //函數執行顯示列表
glFlush(); //強制刷新緩衝,保證繪圖命令將被執行
}
void Displayw(void)
{
glClear(GL_COLOR_BUFFER_BIT); //用當前背景色填充窗口
glEnable(GL_LINE_SMOOTH); //使用反走樣
glEnable (GL_BLEND); //啓用混合函數
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); //指定混合函數
glCallList(lineList); //函數執行顯示列表
glFlush(); //強制刷新緩衝,保證繪圖命令將被執行
}
void main(void)
{
glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB); //使用雙緩存及RGB模型
glutInitWindowSize(300, 300); //窗口大小
glutCreateWindow("原始圖形"); //窗口名稱
glutDisplayFunc(Displayt); //執行函數
glutReshapeFunc(ChangeSize);
Initial();
glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB); //使用雙緩存及RGB模型
glutInitWindowPosition(300, 300);
glutInitWindowSize(300, 300);
glutCreateWindow("反走樣圖形");
glutDisplayFunc(Displayw);
glutReshapeFunc(ChangeSize);
Initial();
glutMainLoop();
}