国产激情自拍_国产9色视频_丁香花在线电影小说观看 _久久久久国产精品嫩草影院

首頁 > 編程 > Delphi > 正文

NeHe的opengl教程delphi版(8)----簡單的透明

2019-11-18 18:30:21
字體:
來源:轉載
供稿:網友
 

{

呵呵,這兩課早就翻譯好了,一直沒貼,大家久等了(有人再等嗎?)

簡單的透明
OpenGL中的絕大多數特效都與某些類型的(色彩)混合有關。
混色的定義為,將某個象素的顏色和已繪制在屏幕上與其對應的象素顏色相互結合。
至于如何結合這兩個顏色則依賴于顏色的alpha通道的分量值,以及/或者所使用的混色函數。
Alpha通常是位于顏色值末尾的第4個顏色組成分量。
前面這些課我們都是用GL_RGB來指定顏色的三個分量。
相應的GL_RGBA可以指定alpha分量的值。
更進一步,我們可以使用glColor4f()來代替glColor3f()。

絕大多數人都認為Alpha分量代表材料的透明度。
這就是說,alpha值為0.0時所代表的材料是完全透明的。
alpha值為1.0時所代表的材料則是完全不透明的。

混色的公式
若您對數學不感冒,而只想看看如何實現透明,請跳過這一節。
若您想深入理解(色彩)混合的工作原理,這一節應該適合您吧。
『CKER的補充:其實并不難^-^。原文中的公式如下,CKER再嘮叨一下吧。
其實混合的基本原理是就將要分色的圖像各象素的顏色以及背景顏色均按照RGB規則各自分離之后,
根據-圖像的RGB顏色分量*alpha值+背景的RGB顏色分量*(1-alpha值)
-這樣一個簡單公式來混合之后,最后將混合得到的RGB分量重新合并。』

公式如下:
(Rs Sr + Rd Dr, Gs Sg + Gd Dg, Bs Sb + Bd Db, As Sa + Ad Da)
OpenGL按照上面的公式計算這兩個象素的混色結果。
小寫的s和r分別代表源象素和目標象素。大寫的S和D則是相應的混色因子。
這些決定了您如何對這些象素混色。
絕大多數情況下,各顏色通道的alpha混色值大小相同,
這樣對源象素就有 (As, As, As, As),
目標象素則有1, 1, 1, 1) - (As, As, As, As)。
上面的公式就成了下面的模樣:
(Rs As + Rd (1 - As), Gs As + Gd (1 - As), Bs As + Bs (1 - As), As As + Ad (1 - As))
這個公式會生成透明/半透明的效果。

OpenGL中的混色
在OpenGL中實現混色的步驟類似于我們以前提到的OpenGL過程。
接著設置公式,并在繪制透明對象時關閉寫深度緩存。
因為我們想在半透明的圖形背后繪制 對象。
這不是正確的混色方法,但絕大多數時候這種做法在簡單的項目中都工作的很好。

Rui Martins 的補充: 正確的混色過程應該是先繪制全部的場景之后再繪制透明的圖形。
并且要按照與深度緩存相反的次序來繪制(先畫最遠的物體)。
考慮對兩個多邊形(1和2)進行alpha混合,不同的繪制次序會得到不同的結果。
(這里假定多邊形1離觀察者最近,那么正確的過程應該先畫多邊形2,再畫多邊形1。
正如您再現實中所見到的那樣,
從這兩個<透明的>多邊形背后照射來的光線總是先穿過多邊形2,
再穿過多邊形1,最后才到達觀察者的眼睛。)
在深度緩存啟用時,您應該將透明圖形按照深度進行排序,
并在全部場景繪制完畢之后再繪制這些透明物體。否則您將得到不正確的結果。
我知道某些時候這樣做是很令人痛苦的,但這是正確的方法。

我們將使用第七課的代碼。
一開始先在代碼開始處增加兩個新的變量。出于清晰起見,我重寫了整段代碼。

}
Var
   h_RC             : HGLRC;            // Rendering Context(著色描述表)。
   h_DC             : HDC;              // Device Context(設備描述表)
   h_Wnd            : HWND;             // 窗口句柄
   h_Instance       : HINST;            // 程序Instance(實例)。
   keys             : Array[0..255] Of Boolean; // 用于鍵盤例程的數組

   light            : Boolean;          // 光源的開/關

   blend            : Boolean;          // Blending OFF/ON? ( 新增 )

   lp               : Boolean;          // L鍵按下了么?
   fp               : Boolean;          // F鍵按下了么?

   bp               : Boolean;          // B 鍵按下了么? ( 新增 )

   xrot             : GLfloat;          // X 旋轉
   yrot             : GLfloat;          // Y 旋轉
   xspeed           : GLfloat;          // X 旋轉速度
   yspeed           : GLfloat;          // Y 旋轉速度

   z                : GLfloat = -5.0 f; // 深入屏幕的距離
   LightAmbient     : Array[0..3] Of GLfloat = (0.5, 0.5, 0.5, 1.0);  //環境光參數 ( 新增 )
   LightDiffuse     : Array[0..3] Of GLfloat = (1.0, 1.0, 1.0, 1.0);  // 漫射光參數 ( 新增 )
   LightPosition    : Array[0..3] Of GLfloat = (0.0, 0.0, 2.0, 1.0);  // 光源位置 ( 新增 )
   filter           : GLuint;           // 濾波類型
   texture          : Array[0..2] Of GLuint; // 3種紋理的儲存空間

PRocedure glGenTextures(n: GLsizei; Var textures: GLuint); stdcall; external
   opengl32;

Procedure glBindTexture(target: GLenum; texture: GLuint); stdcall; external
   opengl32;

Function gluBuild2DMipmaps(target: GLenum; components, width, height: GLint;
   format, atype: GLenum; data: Pointer): Integer; stdcall; external glu32 name
   'gluBuild2DMipmaps';

{
然后往下移動到 LoadGLTextures() 這里。
找到 if (TextureImage[0]=LoadBMP('Data/Crate.bmp'))
這一行。我們現在使用有色玻璃紋理來代替上一課中的木箱紋理。
if (TextureImage[0]=LoadBMP("Data/glass.bmp")); // 載入玻璃位圖 ( 已修改 )
}

Function LoadTexture: boolean;          // 載入位圖并轉換成紋理
Var
   Status           : boolean;          // Status 指示器
   TextureImage     : Array[0..1] Of PTAUX_RGBImageRec; // 創建紋理的存儲空間
Begin
   Status := false;
   ZeroMemory(@TextureImage, sizeof(TextureImage)); // 將指針設為 NULL
   TextureImage[0] := LoadBMP('Walls.bmp');
   If TextureImage[0] <> Nil Then
      Begin
         Status := TRUE;                // 將 Status 設為 TRUE
         glGenTextures(1, texture[0]);  // 創建紋理
         // 創建 Nearest 濾波貼圖
         glBindTexture(GL_TEXTURE_2D, texture[0]);
         // 生成紋理
         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);  // ( 新增 )
         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);  // ( 新增 )

         glTexImage2D(GL_TEXTURE_2D, 0, 3, TextureImage[0].sizeX,
            TextureImage[0].sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE,
            TextureImage[0].data);
         glBindTexture(GL_TEXTURE_2D, texture[1]);  // 使用來自位圖數據生成 的典型紋理
         // 生成紋理
         glTexImage2D(GL_TEXTURE_2D, 0, 3, TextureImage[0].sizeX,
            TextureImage[0].sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE,
            TextureImage[0].data);
         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);  // 線形濾波
         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);  // 線形濾波
         // 創建 MipMapped 紋理
         glBindTexture(GL_TEXTURE_2D, texture[2]);
         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
            GL_LINEAR_MIPMAP_NEAREST);  // ( 新增 )
         gluBuild2DMipmaps(GL_TEXTURE_2D, 3, TextureImage[0].sizeX,
            TextureImage[0].sizey, GL_RGB, GL_UNSIGNED_BYTE,
            TextureImage[0].data);      //(新增)  }
      End;
   If assigned(TextureImage[0]) Then    // 紋理是否存在
      If assigned(TextureImage[0].data) Then // 紋理圖像是否存在
         TextureImage[0].data := Nil;   // 釋放紋理圖像占用的內存
   TextureImage[0] := Nil;              // 釋放圖像結構
   result := Status;                    // 返回 Status
End;

{
在glInit()代碼段加入以下兩行。
第一行以全亮度繪制此物體,并對其進行50%的alpha混合(半透明)。
當混合選項打開時,此物體將會產生50%的透明效果。
第二行設置所采用的混合類型。

Rui Martins 的補充:
alpha通道的值為 0.0意味著物體材質是完全透明的。
1.0 則意味著完全不透明。
}

Procedure glInit();                     // 此處開始對OpenGL進行所有設置
Begin
   If (Not LoadTexture) Then            // 調用紋理載入子例程
      exit;                             // 如果未能載入,退出

   glEnable(GL_TEXTURE_2D);             // 啟用紋理映射
   glShadeModel(GL_SMOOTH);             // 啟用陰影平滑
   glClearColor(0.0, 0.0, 0.0, 0.0);    // 黑色背景
   glClearDepth(1.0);                   // 設置深度緩存
   glEnable(GL_DEPTH_TEST);             // 啟用深度測試
   glDepthFunc(GL_LESS);                // 所作深度測試的類型
   glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); //高度優化的透視投影計算
   glLightfv(GL_LIGHT1, GL_AMBIENT, @LightAmbient[0]); // 設置環境光
   glLightfv(GL_LIGHT1, GL_DIFFUSE, @LightDiffuse[0]); // 設置漫射光
   glLightfv(GL_LIGHT1, GL_POSITION, @LightPosition); // 光源位置
   glEnable(GL_LIGHT1);                 // 啟用一號光源

   glColor4f(1.0, 1.0, 1.0, 0.5);       // 全亮度, 50% Alpha 混合( 新增 )
   glBlendFunc(GL_SRC_ALPHA, GL_ONE); // 基于源象素alpha通道值的半透明混合函數 ( 新增 )

End;

 {在接近第七課結尾處的地方找到下面的代碼段。
                  If keys[VK_LEFT] Then    //Left方向鍵按下了么?
                  yspeed := yspeed - 0.01; //若是, 減少yspeed
                接著上面的代碼,我們增加如下的代碼。
                這幾行監視B鍵是否按下。
                如果是的話,計算機檢查混合選項是否已經打開。
                然后將其置為相反的狀態。
                }
               If (keys[ord('B')] And Not bp) Then //B 健按下且bp為 FALSE么?
                  Begin
                     bp := TRUE;        // 若是, bp 設為 TRUE
                     blend := Not blend; // 切換混合選項的 TRUE / FALSE
                     If (blend) Then    // 混合打開了么?
                        Begin
                           glEnable(GL_BLEND); // 打開混合
                           glDisable(GL_DEPTH_TEST); // 關閉深度測試
                        End
                     Else               // 否則
                        Begin
                           glDisable(GL_BLEND); // 關閉混合
                           glEnable(GL_DEPTH_TEST); // 打開深度測試
                        End;
                  End;
               If (Not keys[ord('B')]) Then //  B 鍵松開了么?
                  Begin
                     bp := FALSE;       // 若是, bp設為 FALSE
                  End;
               {
               但是怎樣才能在使用紋理貼圖的時候指定混合時的顏色呢?很簡單,
               在調整貼圖模式時,文理貼圖的每個象素點的顏色都是由alpha通道參數
               與當前地象素顏色相乘所得到的。
               比如,繪制的顏色是 (0.5, 0.6, 0.4),
               我們會把顏色相乘得到(0.5, 0.6, 0.4, 0.2)
                (alpha參數在沒有指定時,缺省為零)。
               就是如此!OpenGL實現Alpha混合的確很簡單!
               }
               {
                原文注 (11/13/99)
                我(NeHe)混色代碼進行了修改,以使顯示的物體看起來更逼真。
                同時對源象素和目的象素使用alpha參數來混合,會導致物體的人造痕跡看起來很明顯。
                會使得物體的背面沿著側面的地方顯得更暗。
                基本上物體會看起來很怪異。
                我所用的混色方法也許不是最好的,但的確能夠工作。
                啟用光源之后,物體看起來很逼真。
                感謝Tom提供的原始代碼,他采用的混色方法是正確的,
                但物體看起來并不象所期望的那樣吸引人:)
                代碼所作的再次修改是因為在某些顯卡上glDepthMask()函數存在尋址問題。
                這條命令在某些卡上啟用或關閉深度緩沖測試時似乎不是很有效,
                所以我已經將啟用或關閉深度緩沖測試的代碼轉成老式的glEnable和glDisable。

                紋理貼圖的Alpha混合
                用于紋理貼圖的alpha參數可以象顏色一樣從問題貼圖中讀取。
                方法如下,您需要在載入所需的材質同時取得其的alpha參數。
                然后在調用glTexImage2D()時使用GL_RGBA的顏色格式。
               }


上一篇:NeHe的opengl教程delphi版(9)----星星

下一篇:Delphi代碼創建形式規范

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
學習交流
熱門圖片

新聞熱點

疑難解答

圖片精選

網友關注

国产激情自拍_国产9色视频_丁香花在线电影小说观看 _久久久久国产精品嫩草影院
国产精品视频一区二区三区麻豆| 四虎国产精品永久| 国产经典自拍视频在线观看| 精品亚洲成a人片在线观看| 国产亚洲精品午夜高清影院| 二区中文字幕| 国产高清av| 亚洲尤物在线视频| 日本动漫理论片在线观看网站| 精品一区二区三区在线观看l| 四虎成年永久免费网站| 欧美xxxx黑人又粗又长| 亚洲欧美日韩一区成人| 国产精品美女视频免费观看软件| 中文在线视频观看| 精品偷拍激情视频在线观看| 超碰91在线| 国产免费av高清在线| 日本视频在线| 最近中文av字幕在线中文| 免费精品国产自产拍观看| 免费看黄视频网站| 国产素人视频在线观看| 欧美激情福利视频在线观看免费| 成人欧美日韩| 国产porn在线| 天天操天天艹| 92国产在线视频| 国产麻豆综合视频在线观看| 日本一本久久| 精品电影在线| 精品伦理一区二区| 国产高清视频在线| 91看片在线观看| 国产精品jvid在线观看| 午夜在线小视频| 午夜亚洲成人| www.av在线视频| 91中文在线| 91亚洲欧美| 国产福利片在线| 国产一级在线观看| 国产有码在线| 99视频在线观看地址| 国产精品一品| 天天操天天操天天色天天要| 九九99九九精彩| 久热中文字幕精品视频在线| eeuss影院在线| av在线不卡免费| eeuss影院在线观看第一页| 国产视频xxxx| 国产黄色在线看| av片在线观看| 欧美日韩性视频一区二区三区| v天堂福利视频在线观看| 亚洲第一成年免费网站| 免费黄网站在线观看| 最近高清中文在线字幕在线观看| 99色在线视频| 91资源在线观看| 欧美精品久久久久久久小说| 99色在线视频| 91精品专区| 欧美日韩久久中文字幕| 国产有码在线| 国产成人久久精品77777| 99热99re6国产在线播放| 国产在线黄色片| 国产高清在线视频| sm国产在线调教视频| 国产在线视精品麻豆| 国产精品国产三级国产试看| 亚洲欧美小说国产图片| 天天操天天操一操| 色综合久久五月天| 国产对白在线| 国产农村一级特黄α**毛片| 亚洲一本大道| 国产区av在线| 黄色片免费在线| 9999在线视频| 国产一级在线观看www色| 青青草免费在线观看| 精品国产一区二区三区久久久狼牙 | 四虎影视成人永久免费观看视频| 激情丁香婷婷| 精品精品导航| 国产私人尤物无码不卡| 九色在线网站| 青青草中文字幕| 亚洲欧美精选| 精品剧情v国产在线观看| 国精一区二区三区| 欧美aaa一级片| av天天在线| 亚洲欧美一区二区三区在线播放| 国产深夜福利| 国产成人天天5g影院| 最近中文av字幕在线中文| 久久精品国产亚洲a∨麻豆| 日韩欧美中文字幕不卡| 在线免费国产视频| 国产youjizz在线| 国产不卡视频| 亚洲人在线播放| 亚洲精品视频在线免费| 亚洲精品国自产拍在线观看| 国产视频你懂的| 国产福利三区| 在线观看免费高清完整| 性网站在线看| 成年黄网站在线观看免费| 国产资源在线看| 天天爱天天做色综合| 国产精品久久一区二区三区不卡| 国产超碰在线| jizz性欧美| 91caoporn在线| 91午夜在线| 日p在线观看| 最新亚洲精品国自产在线观看| 国产精品视频h| 国产精品视频一区二区免费不卡 | 国产福利免费观看| 伊人中文字幕在线| 欧美精品久久久久久久小说| 天堂在线看视频| 91黄色在线| 久久综合精品视频| 国产视频福利| 国产在线第一页| av男人的天堂网| 丁香花在线电影| 精品欧美不卡一区二区在线观看| eeuss影院www在线播放| 国产精品久久久久白浆| 牛牛精品视频在线| 亚洲欧美精选| 国产成人精品自线拍| 麻豆精品不卡国产免费看| 国产不卡视频| 国产一区二区三区不卡在线| www.xxx黄| 四虎久久影院| 国产福利视频在线| 天堂资源在线中文| 欧洲一区av| 波多野结衣久久高清免费| 国产精品入口麻豆免费| 国产在线你懂得| 免费国产视频| 免费中文字幕| 九九热视频在线观看| 日本国产在线| 日本免费视频www| 伊人av免费在线观看| 国产导航在线| 91中文字幕网| 夜夜操天天干| 四虎成年永久免费网站| av在线中文| 欧美性猛交xxxx免费看蜜桃| 午夜影院在线免费观看| 国产日产一区二区| 国产亚洲依依| 国产一二区视频| 国产高清在线视频| 精品国语对白精品自拍视| 国产精品伦理一区二区三区| 国产天堂在线播放视频| 国产一卡二卡3卡4卡四卡在线| 91av资源在线| 中文字幕高清av| 国产色在线 com| 国产变态拳头交视频一区二区 | 国产一级片在线| 91xxx在线观看| 国产精品合集一区二区| 69久久精品| 不卡av免费观看| 日本中文字幕在线视频| 国产精品区一区二| 尤物在线精品视频| 亚洲第一成年免费网站| 麻豆国产在线视频| 国产日韩网站| 欧美一级久久久久久久久大| 午夜视频在线观看网站午夜视频在线 | 天天操天天操一操| 丁香视频免费观看| 国产高清在线| 欧美亚洲另类在线观看| 99视频在线观看地址| 国产激情自拍视频| 九九热视频在线观看| 伊人春色在线| 中文字幕在线影视资源| 日本国产在线| 精品国产免费观看一区|