close

normal為什麼必須要乘上world matrix的inverse和transpose之後的矩陣,而不是直接乘上world matrix。其實我以前也搞不懂,為什麼有些Shader上是將World Matrix定義為invtransposeWorldMatrix(大致上是這樣定義)而有些卻是直接定義為WorldMatrix(大致上是這樣定義)。在看了Real-Time Rendering之後了解到真正的用意是什麼,將說明如下

NormalTransform2.jpg 

這張圖的左邊是一個三角形物體,在這個斜邊上的Normal垂直於斜邊。但是在經過non-uniform scale之後就會像右圖一樣因為縮放的關係像上延伸,因此斜邊上的Normal已經沒有跟斜編成垂直的。怎麼樣,很可怕是吧,如果這時候利用這個normal來做各種計算,所得到的結果都將是錯誤的。

那要怎麼避免呢,首先我們來了解一下什麼是non-uniform scale。照字面上的意思就是非相等的縮放,也就是在3D空間中(或是2D),每個軸向的縮放值是不一樣的。相對的uniform scale就是個軸向縮放值相等。所以我們知道,只有在non-uniform的狀況下會有這樣的情形發生,所以通常在很多引擎的設計上,會捨棄non-uniform scale,來統一shader的normal計算方式,或是針對各種不同狀況來決定是要執行的shader。

了解了是什麼造成這樣的局面但是卻還是不了解為何要將World Matrix做invese與transpose。接下來就為大家來個數學證明。

首先要對變數做定義,假設在還沒做transform前的斜邊線段為T,那麼可以得到N。T = 0。相對的,T'與N'表示transform之後的T與 N。T' = MT, N' = GN (M和G各表示為某個Matrix可轉換為T'或N')。
由於 N' 。 T' =0 也是要成立的,因此可以展開為 N'。T' = (GN)。(MT) = 0。
由於矩陣的相乘等於行與列的點積,因此可以轉換為
Function1.jpg
為了讓Function2.jpg 成立必須滿足Funtion3.jpg
因此Function4.jpg 

看到這裡是不是都懂了呢
如果有興趣,可以多翻翻線性代數的書本還有Mathematics for 3D Game Programming and Computer Graphics這本書裡面有個章節有講到 

arrow
arrow
    全站熱搜

    SnakeEater 發表在 痞客邦 留言(1) 人氣()