向場景中加入光照
向場景中加入光照的4個步驟:
1)為每一個物體的每一個頂點計算法向量,法線確定了物體相對於光源的指向
法線的計算:設向量a(x1,y1,z1)。向量b(x2,y2,z2)
則a×b=(x2·y3-x3·y2,x3·y1-x1·y3,x1·y2-x2·y1)
2)創建、選擇並定位全部的光源
光源的創建:
glLight*()函數能夠定義光的一些屬性——顏色、位置、方向
定義光時。此族函數最長用的一種形式是:
void glLightfv(Glenum light,Glenum pname,TYPE* param)
此函數中三個參數:所要為其指定屬性的光、所要指定的屬性、此屬性的值
參數light的值能夠是GL_LIGHT0~GL_LIGHT7。指定了要對那個光進行設置
參數所定義的屬性或特性例如以下表所看到的:
param是一個浮點型數組,比如:
float ambientLight[]={ 1.0f, 1.0f, 1.0f, 1.0f };
glLightfv(GL_LIGHT0,GL_AMBIENT,ambientLight);
註意:在指定一個環境光屬性時。同一時候也指定了此光在此場景中所加入的環境光RGBA的強度,
默認條件下是沒有環境光的。其默認值為(0.0f,0.0f,0.0f,1.0f);
光源的定位:
光源的位置是以GL_POSITION和一個四個值的矢量(x,y,z,w)來定義的。
假設w的值為0.0,那麽(x,y,z)的值就定義了一個矢量。其指定了光線照過來的方向,
且全部的光線都是平行的,就好像光源處於無窮遠處。
假設w的值為非零。所定義的就是一個定點光源
比如:float lightPosition[]={0.0f,0.0f.0.0f,1.0f};
glLghtfv(GL_LIGHT0,GL_POSITION,lightPosition);
定義了一個位於世界坐標原點的定點光源。
而對於光的衰減、光柱的張角、聚光燈的焦點的設置。我們經常使用glLightf()函數
glLightf(GL_LIGHT0,GL_CONSTANT_ATTENUATION,4.0)//光的衰減
glLightf(GL_LIGHT0,GL_SPOT_CUTOFF,15.0f);//30°光柱張角
glLightf(GL_LIGHT0,GL_SPOT_EXPONENT,10.0F);//指定聚光燈的焦點
3)創建並選擇一種光照模型。
光照模型定義了環境光,並設置用於光照計算的視點的位置
OpenGL的光照模型同意設置四個影響場景的因素
- 場景的環境光強度
- 視點是否處於無窮遠(影響鏡面發射光反射角的計算)
- 單面光照還是雙面光照
- 鏡面反射的顏色是否與環境光顏色和反射光顏色分離
能夠使用glLightModel*()函數來定義光照模型
void glLightModel[if](GLenum pname,TYPE param);
void glLightModel[if]v(GLenum pname,TYPE param);
比如:將全局環境光設置為中等亮度的白光
float ambienLighttModel[]={0.5f,0.5f,0.5f,1.0f};
glLightModelfv(GL_LIGHT_MODEL_AMBIENT,ambientLightModel);
4)為場景中的物體定義材質屬性
實質上與創建光源相似,僅僅是使用的函數不同
void glMaterialf(GLenum face,GLenum pname,TYPE param);
void glMaterialfv(GLenum face,GLenum pname,TYPE* param);
face 的值能夠是GL_FRONT,GL_BACK,GL_FRONT_AND_BACK
pname通知OPENGL要設置材質的哪一屬性,下表列出了可能值
比如:給多邊形正、背面材質的環境光顏色設置為紅色
float red[]={1.0f,0.0f,0.0f,1.0f};
glMaterialfv(GL_FRONT_AND_BACK,GL_AMBIENT,red);
分享一下旋轉燈光的小程序: 下載
程序執行環境:vs2013+OpenGL
在結束之前。送大家一句話(和大家共勉):
——表面繁榮未必是好事,拋開表象看實質才是人生真諦
向場景中加入光照