OpenGL ES 線性插值演算法黑邊問題探源

2021-08-31 20:58:11 字數 2358 閱讀 3701

分享一下我老師大神的人工智慧教程!零基礎,通俗易懂!

write by 九天雁翎(jtianling) -- blog.csdn.net/vagrxie

-- 討論新聞組

-- **庫

-- 豆瓣

第二次使用別人的引擎碰到用opengl線性過濾演算法放大出現黑邊的問題了,而引擎的製作者竟然不知道怎麼解決,兩次碰到此問題時都是試圖教導我使用最近點過濾方式繞行,我很無奈,幫助其解決一下,順麵將問題簡單的記錄於此。

opengl在放大時有兩種方法,一種是最近點(nearest),一種是線性(linear),雖然在opengl裡面,設定紋理引數的時候都稱為過濾(filter),都通過gltexparameteri函式設定。比如二維時,設定線性過濾:

gltexparameteri( gl_texture_2d, gl_texture_mag_filter, gl_linear );

放大時實際演算法為插值(

interpolation)。

具體的最近點過濾演算法參考

,線性過濾演算法參考

。 簡單的講,最近點過濾演算法就是用最靠近畫素中心的那個紋理單元進行放大和縮小,效率更高,效果不好,鋸齒嚴重。

線性過濾演算法是對靠近畫素中心的2*2紋理單元(二維時,三維為2*2*2),取加權平均值,用於放大和縮小。效果更好,效率稍低。(參看《opengl程式設計指南》第六版)

一般來說,我們常用linear方式,但是linear方式有個問題,那就是碰到邊緣時怎麼處理的問題,一種是取邊緣外元素作為普通點進行加權計算,一種是不取。

為了方便演示,我使用一張android sdk中附帶的,並放大2.0f倍,多次緊密排列繪製,以觀察效果,主要繪製源**如下:

void drawimage(float x, float y, float scale)

void drawimages(float x, float y)

當然,這裡我主要關心linear方式,所以:

gltexparameteri( gl_texture_2d, gl_texture_min_filter,

gl_linear );

gltexparameteri( gl_texture_2d, gl_texture_mag_filter,

gl_linear );

在預設時,opengl

是預設設定gl_repeat的

,此時,加權的紋理單元是從原紋理單元的相反一側去取。效果的好壞依賴與的內容。

但是僅繪製上面兩張時,效果明顯有問題,可以看到下面有明顯的白邊(加權計算來自於上面白色的狀態列)

在opengl中,還有幾種情況

1.gl_clamp,線性演算法會取邊框外的畫素點進行計算,導致黑邊,這也就是常見的黑邊效果。

2.gl_clamp_to_edge,忽略邊框,為簡單設定時想要的正確效果。

3.gl_clamp_to_border,新增邊框顏色值,在紋理座標超出邊框時,按設定的顏色值進行計算,在沒有為邊框設定值時,效果類似gl_clamp。(可以將此時的邊框值看做為黑色)

比如,我用如下方法,設定乙個紅色邊框值,  

gltexparameteri( gl_texture_2d, gl_texture_wrap_s, gl_clamp_to_border);

gltexparameteri( gl_texture_2d, gl_texture_wrap_t, gl_clamp_to_border);

float color[4] = ;

gltexparameterfv( gl_texture_2d, gl_texture_border_color, color);

效果就會如下,明顯多出乙個紅色邊框:

加入還覺得不夠明顯的話,修改draw函式,

void drawimage(float x, float y, float scale)

這下意思明顯了吧:

以上是opengl的情況,opengl es的情況又需要單獨講一下:

opengl es 1.1中,只有兩種情況,repeat(預設),和

gl_clamp_to_edge。

參考這裡

。 android的情況,在我手機(nexus s)中,預設的repeat方式,會看到黑邊。(這個有點奇怪,與opengl中的現象不一樣)設定為

gl_clamp_to_edge後,問題解決。

iphone上的情況,望知情人通知,目前沒有時間測試。

write by 九天雁翎(jtianling) -- blog.csdn.net/vagrxie

給我老師的人工智慧教程打call!

線性插值和雙線性插值

線性插值 如果你只處理分離的資料 想知道分離點之間的某些值,需要用到某種型別的插值。這種情況如圖5 17座標所示。對某些分離的 整數 x值,你知道y值。當x 2,你知道y 10,x 3時y 30。但你不知道x 2.7時的y值。使用線性插值,你通過連線兩點的線段找到x 2.7對應的y值,如圖1所示。使...

mysql實現線性插值法 線性插值法

線性插值法 linear interpolation 什麼是線性插值法 線性插值法是指使用連線兩個已知量的直線來確定在這兩個已知量之間的乙個未知量的值的方法。如何進行線性插值 假設我們已知座標 x0,y0 與 x1,y1 要得到 x0,x1 區間內某一位置x在直線上的值。根據圖中所示,我們得到兩點式...

線性插值法

線性插值法是指使用連線兩個已知量的直線來確定在這兩個已知量之間的乙個未知量的值的方法。進行線性插值 假設我們已知座標 x 0,y0 與 x 1,y1 要得到 x 0,x1 區間內某一位置x在直線上的值。根據圖中所示,我們得到兩點式直線方程 假設方程兩邊的值為 那麼這個值就是插值係數 從x 0到x的距...