01
一個(gè)簡(jiǎn)單的OpenGL程序(內(nèi)部一些常見(jiàn)的參數(shù))
#include <GL/glut.h>
void mydisplay(){
glClear(GL_COLOR_BUFFER_BIT);
//glColor3f(1.0f, 0.0f, 0.0f);
glBegin(GL_POLYGON);
glVertex2f(-0.5, -0.5);
glVertex2f(-0.5, 0.5);
glVertex2f(0.5, 0.5);
glVertex2f(0.5, -0.5);
glEnd();
glFlush();
}
int main(int argc, char** argv){
glutInit(&argc,argv);
glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB);
glutInitWindowSize(500,500);
glutInitWindowPosition(0,0);
glutCreateWindow("simple");
glutDisplayFunc(mydisplay);
init();
glutMainLoop();
}
02
glutMainLoop()是一個(gè)在我們所有圖形語(yǔ)言中驅(qū)動(dòng)主要操作的函數(shù). 這個(gè)函數(shù)被無(wú)限期迭代. 在每次迭代中, 它檢查事件隊(duì)列是否為空.
03
04
marching cube算法是一種用來(lái)計(jì)算等值線isocurve(或等值面isosurface)的常用算法,其基本思想是線性插值逼近等值線(或等值面)浩峡,下面以二維為例介紹其計(jì)算過(guò)程可岂。
1、在平面上構(gòu)建m*n的網(wǎng)格翰灾,利用已知的函數(shù)v=f(x,y)求出網(wǎng)格節(jié)點(diǎn)的值缕粹;
2、根據(jù)所要求的值(iso-value)在相鄰節(jié)點(diǎn)之間插值標(biāo)出相應(yīng)點(diǎn)纸淮;
3平斩、根據(jù)第二步所得到的點(diǎn),在同一網(wǎng)格內(nèi)連接成線咽块,即求得相應(yīng)的等值線绘面。
注意:使用marching cube算法一定要有快速計(jì)算網(wǎng)格節(jié)點(diǎn)值的方法,要么用函數(shù)v=f(x,y)侈沪,要么直接硬件測(cè)量得到
05
繪制滑動(dòng)五彩小正方形
#include <GL/gl.h>
#include <GL/glut.h>
/* globals */
GLsizei wh = 500, ww = 500; /* initial window size */
GLfloat size = 3.0; /* half side length of square */
void drawSquare(int x, int y)
{
y = wh-y;
glColor3f( (char) random()%256, (char) random()%256,
(char) random()%256);
glBegin(GL_POLYGON);
glVertex2f(x+size, y+size);
glVertex2f(x-size, y+size);
glVertex2f(x-size, y-size);
glVertex2f(x+size, y-size);
glEnd();
glFlush();
}
void myReshape(GLsizei w, GLsizei h)
{
/* adjust clipping box */
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0.0, (GLdouble)w, 0.0, (GLdouble)h, -1.0, 1.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
/* adjust viewport and clear */
glViewport(0,0,w,h);
glClearColor (0.0, 0.0, 0.0, 0.0);
glClear(GL_COLOR_BUFFER_BIT);
glFlush();
/* set global size for use by drawing routine */
ww = w;
wh = h;
}
void myinit(void)
{
glViewport(0,0,ww,wh);
/* Pick 2D clipping window to match size of screen window
This choice avoids having to scale object coordinates
each time window is resized */
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0.0, (GLdouble) ww , 0.0, (GLdouble) wh , -1.0, 1.0);
/* set clear color to black and clear window */
glClearColor (0.0, 0.0, 0.0, 0.0);
glClear(GL_COLOR_BUFFER_BIT);
glFlush();
}
void mouse(int btn, int state, int x, int y)
{
if(btn==GLUT_RIGHT_BUTTON&state==GLUT_DOWN) exit();
}
int main(int argc, char** argv)
{
glutInit(&argc,argv);
glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB);
glutCreateWindow("square");
myinit ();
glutReshapeFunc (myReshape);
glutMouseFunc (mouse);
glutMotionFunc(drawSquare);
glutMainLoop();
}
06
橡皮筋技術(shù)
基于異或操作的橡皮筋技術(shù)利用了異或邏輯操作的重要性質(zhì):值A(chǔ)與值B兩次異或揭璃,其值仍然為A;異或邏輯運(yùn)算如下圖所示:也就是:
A | B | A異或B | A異或B異或B |
---|---|---|---|
1 | 1 | 0 | 1 |
1 | 0 | 1 | 1 |
0 | 1 | 1 | 0 |
0 | 0 | 0 | 0 |
將這個(gè)性質(zhì)應(yīng)用到像素的顏色上亭罪,則可以利用兩次異或操作恢復(fù)本來(lái)的像素顏色瘦馍。即:將圖形顯示方式設(shè)置為異或模式(如Visual C++中的函數(shù)SetROP2),畫出圖形(此時(shí)圖形是可見(jiàn)的),在異或模式下应役,將相同的圖形再畫一遍情组,這個(gè)圖形將會(huì)從屏幕上消失,而原來(lái)被它覆蓋的部分將恢復(fù)如初扛吞。
07
OpenGL繪制流水線及各個(gè)模塊的功能
- 頂點(diǎn)處理
該模塊的兩個(gè)主要功能是執(zhí)行坐標(biāo)變化和計(jì)算每一個(gè)頂點(diǎn)的顏色值 - 裁剪和圖元組裝
由于成像系統(tǒng)不可能一次對(duì)整個(gè)場(chǎng)景成像呻惕,我們必須進(jìn)行裁剪荆责;圖元組裝是把頂點(diǎn)組裝成像線段和多邊形這樣的圖元 - 光柵化
光柵化模塊必須確定在幀緩存中那些像素位于圖元的內(nèi)部滥比,該模塊對(duì)于每個(gè)圖元輸出一組片元 - 片元處理
片元可以看做是攜帶相關(guān)信息的潛在像素,該模塊利用光柵化模塊生成的片元來(lái)更新幀緩存中的像素
08
雙緩存原理及調(diào)用設(shè)置參數(shù)
圖形硬件具有兩個(gè)幀緩存做院,其中一個(gè)幀緩存用于顯示圖像盲泛,我們稱之為前端緩存,另一個(gè)稱之為后端緩存键耕,用于存儲(chǔ)用戶需要顯示的內(nèi)容寺滚。一段完成了場(chǎng)景的繪制,就可以交換前端緩存和后端緩存的內(nèi)容屈雄,然后清除后端緩存并寫入新的數(shù)據(jù)
glSwapBuffer();
gluInitDisplayModel(GLUT_RGB | GLUT_DOUBLE | GLUT_DEPTH);
09
OpenGL的坐標(biāo)系:
- 對(duì)象坐標(biāo)系
- 世界坐標(biāo)系
- 照相機(jī)坐標(biāo)系
- 裁剪坐標(biāo)系
- 規(guī)范化的設(shè)備坐標(biāo)系
- 屏幕坐標(biāo)系
10
正交投影規(guī)范化
使用平移和旋轉(zhuǎn)變換將照相機(jī)坐標(biāo)系下的頂點(diǎn)變換到默認(rèn)的視見(jiàn)體內(nèi)部成為投影規(guī)范化村视,使得變形后的對(duì)象的正交投影與原來(lái)想得到的對(duì)象的投影圖相同
投影變換矩陣:
10
phong模型以及改進(jìn)的phong模型
(1)phong反射模型有4個(gè)向量:n,v,l,r。對(duì)于表面上任意一點(diǎn)p酒奶,向量n是p點(diǎn)處的法向量蚁孔,向量v是從p指向觀察者的向量奶赔。向量l是從點(diǎn)p指向點(diǎn)光源的向量。向量r的方向是從沿著向量l方向入射的光線按照反射定律的出射方向杠氢。phong反射模型考慮了光線和材質(zhì)之間的相互作用:環(huán)境光反射站刑,漫反射,鏡面反射
(2)改進(jìn)的phong模型
引入一個(gè)新的向量——半角向量鼻百,半角向量位于觀察向量v和光源向量l這兩者正中間绞旅,在改進(jìn)的phong模型中(又稱blinn-phong模型),利用半角向量計(jì)算鏡面反射分量r
11
phong著色和gouraud著色的特點(diǎn)
(1)gouraud著色:在這種明暗繪制方法中温艇,我們對(duì)公用一個(gè)頂點(diǎn)的多邊形的法向量取平均值因悲,把歸一化后的平均值定義為該頂點(diǎn)的法向量,這種方法可以獲得更平滑的插值效果勺爱,降低March帶的效果
(2)phong著色:在多邊形內(nèi)部對(duì)方向量進(jìn)行插值(gouraud是對(duì)頂點(diǎn)的明暗值進(jìn)行插值)囤捻,為了求出某個(gè)頂點(diǎn)的法向量,我們對(duì)公用該頂點(diǎn)的多邊形的法向量進(jìn)行插值邻寿。
12
梁友棟算法(liang-barsky算法)
13
bresenham算法