本章目標:
- 大致瞭解OpenGL的功能
- 瞭解不同程度的渲染複雜性
- 理解OpenGL程序的基本結構
- 瞭解OpenGL函數的語法
- 瞭解OpenGL渲染管線的操作序列
- 大致瞭解如何在OpenGL程序中實現動畫
本書對OpenGL進行了簡單的介紹,主要包含下面幾節:
- 什麼是OpenGL:介紹OpenGL是什麼,它能夠做什麼,不能夠做什麼,以及它的工作原理.
- 一段簡單的OpenGL代碼:展示一個小型的OpenGL程序,並對它進行了簡單的討論,並定義了一些基本的計算機圖形術語
- OpenGL函數的語法:解釋OpenGL函數所使用的一些約定和記法
- OpenGL是一個狀態機:描述OpenGL狀態變量的用法,並介紹一些查詢,啓用和禁用OpenGL狀態的函數
- OpenGL渲染管線:展示一個用於處理幾何和圖像數據的典型操作序列
- 與OpenGL相關的函數庫:介紹一些與使用OpenGL相關的函數,包括對GLUT(Graphice歲LibraryUtilityToolkit,一種可移植的工具庫)的詳細介紹
- 動畫:簡單介紹如何創建能夠在屏幕移動的圖片
OpenGL及其廢棄機制:介紹在OpenGL的最新版本中哪些廢棄修改,這些修改如何影響到應用程序,以及根據這些修改,OpenGL未來會如何發展
1.1 什麼是OpenGL
OpenGL是圖形處理硬件的一種軟件接口.這個接口包含的函數超過700個(納入OpenGL3.0的函數大約670個,另外50個函數位於OpenGL工具庫中),這些函數可以用於指定物體和操作,創建交互式的三維應用程序.
OpenGL的設計目標就是作爲一種流水線型的,獨立於硬件的接口,在許多不同的硬件平臺上實現.爲了實現這個目標,
OpenGL並未包含用於執行窗口任務或者獲取用戶輸入之類的函數.反之,必須通過具體的窗口系統來控制OpenGL應用程序所使用的特定硬件.類似的,OpenGL並沒有提供用於描述三維物體模型的高級函數,這類函數可能允許特定系那個對較爲複雜的形狀,例如騎車,身體的某個補位,飛機或分子等.在OpenGL中,程序員必須根據一些爲數不多的基本幾何圖元(如點,直線和多邊形)來創建所需要的模型.
當然,程序員可以在OpenGL的基礎上,創建提供這些特性的高級函數庫.OpenGL工具庫(GLU)提供了許多建模功能,例如二次曲面以及NURBS曲面和表面.GLU是所有OpenGL實現的第一個標準組成部分.
1.2 一段簡單的OpenGL代碼
由於OpenGL圖形系統的功能非常強大,因此OpenGL程序可能相當複雜,但是,許多使用的OpenGL程序的基本結構可能非常簡單,它的任務就是初始化一些狀態(這些狀態用於控制OpenGL的渲染方式),並指定需要進行渲染的物體
在查看OpenGL代碼之前,首先介紹幾個術語,渲染(rendering)是計算機根據模型創建圖像的過程,我們已經在前面看到過這個術語,模型(model)是根據幾何圖元創建的,也成爲無題(object),幾何圖元包括點,直線和多邊形,它們是通過頂點(vertex)指定的.
最終完成了渲染的圖像是由屏幕上繪製的像素組成的,像素是最小可視元素,
位平面是一塊內存取悅,保存了屏幕上的每個像素的一個位的信息,
glClearColor()函數確定了窗口將清除成什麼顏色,而glClear()函數實際完成清除窗口的任務.在設置了清楚顏色之後,以後每次調用glClear()時,窗口就會清除這種顏色.當然,可以再次調用glClearColor()函數,更改當前的清除顏色,
glColor3f()函數確定了繪製物體時所使用的顏色,此後,所有繪製的物體都將使用這種顏色,出來再次調用這個函數更改繪圖顏色.
glOrtho()函數指定了OpenGL在繪製最終圖像時所使用的座標系統(cooridinate system),決定了圖像將如何映射到屏幕上,接下來的幾個函數位於一對glBegin()和glEnd()調用之間,它們定義了要繪製的物體.
glFlush()函數保證了繪圖命令將實際執行,而不是存儲在緩衝區中等待其他的OpenGl命令
1.3 OpenGL函數的語法
glColor3f()函數名的3表示這個函數接受三個參數,f表示這些函數都是浮點數,
表1-1 函數後綴和參數數據類型
後綴 | 典型的對應C語言類型 | OpenGL類型定義 |
---|---|---|
b | signed char | GLbyte |
s | short | GLshort |
i | int or long | GLShort |
f | float | GLint,GLsizei |
d | double | GLdouble,GLclampd |
ub | unsigned char | GLubyte,GLboolean |
us | unsigned short | GLushort |
ui | unsigned int unsigned long | GLuint,GLenum,GLbitfield |
注意:不同的OpenGL實現在選擇哪些C數據類型表示OpenGL數據類型方面存在一些差異,如果堅持在自己的應用程序中使用OpenGL定義的數據類型,那麼在不同的OpenGL實現之間一直代碼時,就可以避免類型不匹配的問題.
有些OpenGL函數名的最後還有一個v,它表示這個函數所接受的參數是一個指向值向量(或數組)指針,而不是一系列的單獨參數,許多函數既有向量版本也有非向量版本,也有一些函數只接受單獨的參數,另外還有一些函數要求至少有一個參數被指定爲向量,下面這幾行代碼顯示了既可以使用向量版本也可以使用非向量版本的函數來設置當前繪製顏色.
glColor3f(1.0,0.0,0.0);
GLfloat color_array[] = {1.0,1.0,1.0};
glColor3fv(color_array);
最後,OpenGL還定義了GLvoid類型,這種類型最長用於那些接受指向值數組的指針爲參數的OpenGL函數.
在本書的剩餘部分,將只用基本名稱來表示OpenGL函數,並且加表示它還有多個不同版本,glColor()表示用於設置當前顏色的函數所有版本,如果想強調所使用的是一個函數的某個特定版本,可以加上必要的後綴來表示這個版本.glVertex*v()表示用於指定頂點的函數的所有版本.
1.4 OpenGL是一個狀態機
OpenGL是一個狀態機,尤其是如果你使用固定功能的管線,可以設置它的各種狀態(或模式),然後讓這些狀態一直生效,直到再次修改它們,正如所看到的那樣,當前顏色就是一個狀態變量,可以把當前顏色設置成白色,紅色,或其他顏色,當前顏色只是OpenGL所維護的許多狀態變量之一.其他的狀態還有很多,並且有着各自的用途,例如控制當前視圖和投影變換,直線和多邊形點畫模式,多邊形繪圖模式,像素包裝約定,光照的位置和特徵已經被繪製的物體的材料屬性,許多表示模式的狀態變量可以用glEnable()和glDisable()函數進行啓用和禁用.
如果使用shader,根據所用的OpenGL版本的不同,shader所識別狀態的數量也不同.
每個狀態都有一個默認值,任何時候都可以向系統查詢每個狀態變量的當前值,
1.5 OpenGL渲染管線
1.5.1 顯示列表(display list)
任何數據,不論它描述的是幾何圖元還是像素,都可以保存在display list中,供當前或以後使用,當然,也可以不用保存,而是立即處理(immediate mode)
1.5.2 求值器
所有的幾何圖元最終都要通過頂點來描述.
1.5.3 基於頂點的操作
頂點變圖元,
1.5.4 圖元裝配
圖元裝配的一個主要內容就是裁剪,
透視除法(perspective division)使遠處的物體看起來比近處的物體更小一些,接下來所進行的是視口(viewport)和深度(z座標)操作.如果啓用了剔除功能(sulling)並且該圖元是一個多邊形,那麼它就有可能被剔除測試所拒絕.根據多變模式,多邊形可能化成點的形式或者直線的形式.
1.5.5 像素操作
在OpenGL的渲染管線中,和單路徑的幾何數據相比,像素數據所經歷的流程有所不同,首先,來自系統內存的一個數組中像素進行解包,從某種格式(像素的原始格式可能有多種)解包爲適當數量的數據成分,接着,這些數據被縮放,偏移,處理結果先進行截取,然後寫入紋理內存,或者發送到光柵化階段
1.5.6 紋理裝配
OpenGL應用程序可以在幾何物體上應用紋理圖像,使它們看上去更爲逼真.如果需要使用多幅紋理圖像,把它們放在紋理對象中是一種明智的做法.這樣就可以很方便的在他們之間進行切換.
1.5.7 光柵化
光柵化就是把幾何數據和像素數據轉換爲片斷(fragment)的過程,每個片段方塊對應於幀緩衝區的一個像素,把頂點連接起來形成直線或者計算填充多邊形的內部像素時,需要考慮直線和多邊形的點畫模式,直線的寬度,點的大小,着色模型以及用於支持抗鋸齒處理的覆蓋計算.每個片段方塊都將具有各自的顏色和深度值.
1.5.8 片斷操作
在數據實際存儲到幀緩衝區之前,要執行一系列的操作,這些操作可能會修改甚至丟棄這些片段.
1.6 與OpenGL相關的函數庫
OpenGL提供了一組功能強大但又非常基本的渲染函數,所有的高級繪圖操作都是在這些函數的基礎上完成的.另外,OpenGL程序還必須使用窗口系統的底層機制,有一些函數庫可以幫助程序員簡化編程任務,他們是:
- OpenGL工具函數庫(GLU)包含了一些函數,它們利用底層的OpenGL函數來執行一些特定的任務,例如設置特定的矩陣(歷史用於視圖方向和投影的矩陣),多邊形分格化以及表面渲染等.所有的OpenGL實現都把GLU作爲它們的一部分,<>描述了GLU的部分函數,分佈
- 所有的窗口系統都提供了一個函數庫,對該窗口系統的功能進行擴展,以支持OpenGL渲染,對於使用X窗口系統的計算而言,它所使用的OpenGL擴展(GLX)是作爲OpenGL的一個附件提供的.所有的GLX函數都使用前綴glX,win7而言,WGL函數庫提供了Windows和OpenGL之間的接口
- OpenGL實用工具庫,它的目的是隱藏不同窗口