2014-05-10 104 views
2

我想將霧添加到場景中。但是,我不想根據與相機的距離給片段顏色添加霧,而是希望採用更現實的方法。我想計算距離,從眼睛到碎片的矢量「穿過」一層霧。 enter image description here計算GLSL中的矢量交點(OpenGL)

霧層我的意思是霧的下限(在這種情況下是z座標)和上限。我想計算從眼睛到片段的矢量,並獲取它在霧中的部分。該部分在圖形中標記爲紅色。

這個計算其實很簡單。但是,我必須用簡單的方法做一些測試(如果是的話)。

calculate line from vector and camera position; 
get line intersection with lower limit; 
get line intersection with higher limit; 

do some logic stuff to figure out how to handle the intersections; 
calculate deltaZ, based on intersections;   
scale the vector (vector = deltaZ/vector.z) 
fogFactor = length(vector); 

這應該很容易。然而,造成麻煩的是我必須添加一些邏輯來確定相機和碎片如何與霧相關。另外,我必須確定矢量實際上與極限相交。 (當矢量z值爲0時會產生問題) 問題是,變化不是着色器中最好的朋友,至少這是互聯網告訴我的。 ;)

我的第一個問題:有沒有更好的方法來解決這個問題? (我真的想留在我的模型霧,因爲這是關於解決問題。)

第二個問題:我認爲計算應該從片段着色器,而不是頂點着色器,因爲這是沒有什麼可以被插入。我對嗎?

下面是該場景的第二個圖形。 second graphic

+0

我的座標系已經搞亂了。我用z作爲向上的矢量,x是屏幕上的矢量,y是平行的。我知道,我應該使用正常的座標系,其中x和y是水平/垂直的在屏幕上... –

回答

1

問題解決了。 :)

我沒有定義具有下限和上限的霧,而是用中心高度和半徑來定義它。因此,下限等於中心減半徑,上限是中心加半徑。

有了這個,我想出了這個計算:(對不起,壞的變量名)

// Position_worldspace is the fragment position in world space 
// delta 1 and 2 are differences in the z-axis from the fragment/eye to 
// the center height 

float delta1 = clamp(position_worldspace.z - fog_centerZ, 
        -fog_height, fog_height) 
float delta2 = clamp(fog_centerZ - cameraPosition_worldspace.z, 
        -fog_height, fog_height); 

float fogFactor z = delta1 + delta2; 

vec3 viewVector = position_worldspace - cameraPosition_worldspace; 
float fogFactor = length(viewVector * (fogFactorZ/(viewVector).z)); 

我想這是不計算該最快的方法,但它的伎倆。

不過! 這個效應並不是真正的規律,因爲霧的更高和更低的極限是銳利的。我忘了這一點,因爲當眼睛不在這些邊界附近時,它看起來並不壞。但我認爲這個問題有一個簡單的解決方案。 :)

感謝您的幫助!