睿豐德科技 專注RFID識別技術和條碼識別技術與管理軟件的集成項目。質量追溯系統、MES系統、金蝶與條碼系統對接、用友與條碼系統對接
一、OpenGL簡介
眾所周知,OpenGL原先是Silicon Graphics Incorporated(SGI公司)在他們的圖形工作站上開發高質量圖像的接口。但最近幾年它成為一個非常優秀的開放式三維圖形接口。實際上它是圖形軟件和硬件的接口,它包括有120多個圖形函數,"GL"是"GRAPHIC LIBRARY"的縮寫,意思是“圖形庫”。OpenGL的出現使大多數的程序員能夠在PC機上用C語言開發復雜的三維圖形。微軟在Visual C++ 7中已提供了三個OpenGL的函數庫(OpenGL32.lib, glu32.lib, glaux.lib,glut32.lib),可以使我們方便地編程,簡單、快速地生成美觀、漂亮的圖形。例如,Windows NT中的屏幕保護程序中的花籃和迷宮等都給人們留下了深刻的印象。
二、生成OpenGL程序的基本步驟和條件
本文將給出一個例子,這個例子是一個用OpenGL顯示圖像的Windows程序,通過這個程序我們也可以知道用OpenGL編程的基本要求。我們知道,GDI是通過設備句柄(Device Context以下簡稱"DC")來繪圖,而OpenGL則需要繪制環境(Rendering Context,以下簡稱"RC")。每一個GDI命令需要傳給它一個DC,與GDI不同,OpenGL使用當前繪制環境(RC)。一旦在一個線程中指定了一個當前RC,所有在此線程中的OpenGL命令都使用相同的當前RC。雖然在單一窗口中可以使用多個RC,但在單一線程中只有一個當前RC。本例將首先產生一個OpenGL RC并使之成為當前RC,分為三個步驟:設置窗口像素格式;產生RC;設置為當前RC。
1、首先創建工程
用AppWizard產生一個EXE文件,選擇工程目錄,并在工程名字中輸入"OpenGL",保持其他的不變;
第一步、選單文檔(SDI);
第二步、不支持數據庫;
第三步、不支持OLE;
第四步、不選中浮動工具條、開始狀態條、打印和預覽支持、幫助支持的復選框,選中三維控制(3D Controls);
第五步、選中產生源文件注釋并使用MFC為共享動態庫;
第六步、保持缺省選擇。按Finish結束,工程創建完畢,如圖1所示。
VC2005和VC2008采用相同的設置。
2、將此工程所需的OpenGL文件 和庫加入到工程中
在工程菜單中,選擇"Build"下的"Settings"項。單擊"Link"標簽,選擇"General"目錄,在Object/Library Modules的編輯框中輸入"OpenGL32.lib glu32.lib glaux.lib"(注意,輸入雙引號中的內容,各個庫用空格分開;否則會出現鏈接錯誤),選擇"OK"結束。在VC2005和VC2008中的設置方式為:Project Option->Configuration Properties->Linker->Input設置選項卡的Additional Dependiencies中輸入同樣的內容即可。
然后打開文件"stdafx.h",將下列語句插入到文件中(劃下劃線的語句為所加語句):
[cpp] view plaincopy
3、改寫OnPreCreate函數并給視 類添加成員函數和成員變量
OpenGL需要窗口加上WS_CLIPCHILDREN(創建父窗口使用的Windows風格,用于重繪時裁剪子窗口所覆蓋的區域)和 WS_CLIPSIBLINGS(創建子窗口使用的Windows風格,用于重繪時剪裁其他子窗口所覆蓋的區域)風格。把OnPreCreate改寫成如下所示:
[c-sharp] view plaincopy
產生一個RC的第一步是定義窗口的像素格式。像素格式決定窗口著所顯示的圖形在內存中是如何表示的。由像素格式控制的參數包括:顏色深度、緩沖模式和所支持的繪畫接口。在下面將有對這些參數的設置。我們先在COpenGLView的類中添加一個保護型的成員函數BOOL SetWindowPixelFormat(HDC hDC),并編輯其中的代碼。
[cpp] view plaincopy
4、用ClassWizard添加WM_CREATE的消息處理函數OnCreate
添加OnCreate函數后如下所示。
[cpp] view plaincopy
至此,OpenGL工程的基本框架就建好了。但如果你現在運行此工程,則它與一般的MFC程序看起來沒有什么兩樣。
5、代碼解釋
現在我們可以看一看DescribePixelFormat提供有哪幾種像素格式,并對代碼進行一些解釋:
PIXELFORMATDESCRIPTOR包括了定義像素格式的全部信息。
DWFlags定義了與像素格式兼容的設備和接口。
通常的OpenGL發行版本并不包括所有的標志(flag)。wFlags能接收以下標志:
PFD_DRAW_TO_WINDOW 使之能在窗口或者其他設備窗口畫圖;
PFD_DRAW_TO_BITMAP 使之能在內存中的位圖畫圖;
PFD_SUPPORT_GDI 使之能調用GDI函數(注:如果指定了PFD_DOUBLEBUFFER,這個選項將無效);
PFD_SUPPORT_OpenGL 使之能調用OpenGL函數;
PFD_GENERIC_FORMAT 假如這種象素格式由Windows GDI函數庫或由第三方硬件設備驅動程序支持,則需指定這一項;
PFD_NEED_PALETTE 告訴緩沖區是否需要調色板,本程序假設顏色是使用24或 32位色,并且不會覆蓋調色板;
PFD_NEED_SYSTEM_PALETTE 這個標志指明緩沖區是否把系統調色板當作它自身調色板的一部分;
PFD_DOUBLEBUFFER 指明使用了雙緩沖區(注:GDI不能在使用了雙緩沖區的窗口中畫圖);
PFD_STEREO 指明左、右緩沖區是否按立體圖像來組織。
PixelType定義顯示顏色的方法。PFD_TYPE_RGBA意味著每一位(bit)組代表著紅、綠、藍各分量的值。PFD_TYPE_COLORINDEX 意味著每一位組代表著在彩色查找表中的索引值。本例都是采用了PFD_TYPE_RGBA方式。
● cColorBits定義了指定一個顏色的位數。對RGBA來說,位數是在顏色中紅、綠、藍各分量所占的位數。對顏色的索引值來說,指的是表中的顏色數。
● cRedBits、cGreenBits、cBlue-Bits、cAlphaBits用來表明各相應分量所使用的位數。
● cRedShift、cGreenShift、cBlue-Shift、cAlphaShift用來表明各分量從顏色開始的偏移量所占的位數。
一旦初始化完我們的結構,我們就想知道與要求最相近的系統象素格式。我們可以這樣做:
m_hGLPixelIndex = ChoosePixelFormat(hDC, &pixelDesc);
ChoosePixelFormat接受兩個參數:一個是hDc,另一個是一個指向PIXELFORMATDESCRIPTOR結構的指針&pixelDesc;該函數返回此像素格式的索引值。如果返回0則表示失敗。假如函數失敗,我們只是把索引值設為1并用DescribePixelFormat得到像素格式描述。假如你申請一個沒得到支持的像素格式,則Choose-PixelFormat將會返回與你要求的像素格式最接近的一個值。一旦我們得到一個像素格式的索引值和相應的描述,我們就可以調用SetPixelFormat設置像素格式,并且只需設置一次。
現在像素格式已經設定,我們下一步工作是產生繪制環境(RC)并使之成為當前繪制環境。在COpenGLView中加入一個保護型的成員函數BOOL CreateViewGLContext(HDC hDC),使之如下所示:
[cpp] view plaincopy