OpenGL:反走樣
由於計算機以離散點生成圖形,生成圖形必然與真實景物存在差距,這種差距表現為:直線或光滑曲面的鋸齒、花紋失去原有色彩形狀、細小物體在畫面的消失等。統統叫做走樣(aliasing)。反走樣可以減少這種情況。粗略設想一下,就是把原來邊界的地方鋸齒部分用低飽和度的點補上,這樣既不影響整體輪廓,又獲得較好的平滑效果。
用於減少和消除各種走樣現象的方法就是反走樣。通常反走樣的方法有提高解析度法、非加權區域取樣法、加權區域取樣法等,但是在OpenGL中實現反走樣就簡單的多。
反走樣前提供“提示”採用函式:
void glHint(GLenum target,GLenum hint);
其中hint可以是:
GL_FASTEST 給出最有效的選擇
GL_NICEST 給出最高質量的選擇
GL_DONT_CARE 沒有選擇
target 意義
GL_POINT_SMOOTH_HINT 指定點、
GL_LINE_SMOOTH_HINT 線、
GL_POLYGON_SMOOTH_HINT 多邊形的取樣質量
GL_FOG_HINT 指出霧化計算是按每個象素進行(GL_NICEST),還是按每個頂點進行(GL_FASTEST)
GL_PERSPECTIVE_CORRECTION_HINT 指定顏色紋理插值的質量
其中GL_PERSPECTIVE_CORRECTION_HINT用以糾正單純線性插值帶來的觀察錯誤。
OpenGL實現反走樣需要滿足兩個條件,一是啟用混合,二是啟用針對幾何圖元的反走樣處理。
前面已經講過,glEnable(GL_BLEND)啟動混合,而glEnable(mode)則啟用幾何圖元的反走樣,其中mode取值為GL_POINT_SMOOTH、GL_LINE_SMOOTH或GL_POLYGON_SMOOTH。
接下來我們實現一個網格狀球體的反走樣處理。為了便於觀察,我們不使用包括霧、光照、紋理等效果。
int glInit()
{
//啟用陰影平滑(Smooth Shading)。
glShadeModel(GL_SMOOTH);
glClearColor(1.0f, 1.0f, 1.0f, 1.0f);
//設定深度緩衝
glClearDepth(1.0f);
//啟動深度測試
glEnable(GL_DEPTH_TEST);
//深度測試的型別
glDepthFunc(GL_LEQUAL);
//進行透視修正
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
return TRUE;
}
void glMain()
{
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLoadIdentity(); //載入單位矩陣
glTranslatef(-1.5f, 0.0f, -5.0f);
//球體的顏色為黑色
glColor3f(0.0f, 0.0f, 0.0f);
//未使用反走樣處理
glDisable(GL_BLEND);
glDisable(GL_LINE_SMOOTH);
glDisable(GL_POLYGON_SMOOTH);
auxWireSphere(1.0);
//啟用反走樣處理
glEnable(GL_BLEND);
glEnable(GL_LINE_SMOOTH);
glEnable(GL_POLYGON_SMOOTH);
glTranslatef(3.0f, 0.0f, 0.0f);
auxWireSphere(1.0);
SwapBuffers(g_hDC);//交換前後緩衝區
}
程式執行效果如圖9-7所示,可以看到兩個球體的明顯不同。