


這個效果的制作主要學(xué)習(xí)了UVMapping的活用。
這個護(hù)盾的效果可以主要分為以下幾個模塊:首先在Maya中生成一個柏拉圖多面體,然后在y=0處用多切割把下半球分離出來并舍棄掉,得到使用的模型。使用的材質(zhì)Shader隊(duì)列需要設(shè)置為Transparent,并且分兩個Pass(一個Cull Front一個Cull Back),用以正確顯示護(hù)盾后和護(hù)盾中的物體。兩個Pass都用的同一段代碼,并且模糊效果是直接寫在Shader里對
GrabPass得到的_GrabTexture處理的,因此在護(hù)盾內(nèi)外都可以得到正確的效果。另外,每個面上的點(diǎn)的法線是未經(jīng)過插值的面法線,用之前學(xué)習(xí)過的ddx和ddy對世界空間的坐標(biāo)求偏導(dǎo)叉乘得到法線即可。
然后就是接下來詳細(xì)分析的動態(tài)色彩/消融/UV扭曲/面描邊/輝光效果。
動態(tài)色彩/UV扭曲
我希望的效果是每個面都有互不相同、能夠變化的顏色,但是我嘗試采用shader內(nèi)實(shí)時(shí)計(jì)算不僅效果不好,而且未免太大材小用。后來我采用了這種辦法:首先在Maya中將每個面的UV打散,并且放在UV空間的隨機(jī)位置,賦予隨機(jī)方向。

接下來在shader內(nèi)使用這個UV加上隨時(shí)間變化的量,對如下的圖(Photoshop中中心點(diǎn)一個點(diǎn)然后高斯模糊)進(jìn)行采樣。

然后,得到的采樣值再去采樣或者計(jì)算用戶自定義的Color Ramp即可。由于不同面之間的UV是全部分散毫無關(guān)聯(lián)的,因此就可以得到每個面互不相同顏色的效果。
我還增加了一個菲涅爾效果,面法線和視角接近垂直的面采用另一套Color Ramp。
對于表面類似折射扭曲的效果,同樣采用這一套UV加隨時(shí)間變化的量對法線貼圖采樣,使用法線的xy對grabPos扭曲即可。同樣的,因?yàn)槊總€面UV殼方向也是隨機(jī)的,因此我們能看到效果圖中每個面“流動方向”不同的效果。
消融
這個也算是比較常用的效果,首先用戶自定義一張消融數(shù)值圖,然后采樣這張圖的數(shù)值,如果這個值達(dá)不到shader預(yù)先規(guī)定的閾值就舍棄這個片元(或直接返回當(dāng)前點(diǎn)采樣的_GrabTexture)。

這里我輸入的是一個柏林噪聲圖。但是,我們需要讓面與面之間的消融的“洞”或者剩下的“島”具有連續(xù)性,這時(shí)我們就不能采用上述的打散的UV了,而是使用直接對未剪開邊的網(wǎng)格unfold后的UV生成另一套UV集。

最后,我們還可以增加一個邊緣尺寸的量輸入shader,消融數(shù)值接近閾值的部分我們增加一個發(fā)光的效果。
另外,上面兩個灰度圖我們還可以放到同一張圖的不同通道里。

面描邊
重心坐標(biāo)
這里涉及到一個三角形重心坐標(biāo)系的概念,若重心坐標(biāo)的某一個值接近0,說明這個值越靠近三角形邊緣。我們知道在fragment shader中是經(jīng)過插值處理的,但是我們還是沒有辦法能夠直接得到當(dāng)前片元的重心坐標(biāo)。
不過好在我們還可以讓模型有更多的UV集,只要我們把網(wǎng)格的每個三角面的UV殼頂點(diǎn)放到UV空間的(0,0)(1,0)(1,1)處我們就能輕易在shader中計(jì)算得到重心坐標(biāo)了。
于是我們在Maya的UV編輯器中直接對全部拆開的面使用單位化,最后得到想要的結(jié)果儲存為第三套UV集。

在shader中,我們只需要使用如下方式就能得到重心坐標(biāo)的最小分量:
float uvDist = min(min(i.uv3.y, 1 - i.uv3.x),(i.uv3.x - i.uv3.y)/1.414);
這個值小于預(yù)先設(shè)定的閾值的話,這個片元就是我們要描邊的片元。
輝光
沒有什么特別要說的,基本和之前寫的物體輝光效果一樣的方法,需要用到腳本處理,甚至沒有用到第二個相機(jī)。需要說明的是,在護(hù)盾自身的shader中我將發(fā)光處的alpha設(shè)為了0,并且在后處理輝光時(shí)只提取了alpha通道分量做模糊處理。因此,若是相機(jī)中會出現(xiàn)其他半透明/透明的物體時(shí),這個方法就不適用了,那就需要使用另一個相機(jī)和更多的腳本工作去得到正確的效果,如果要考慮到還有Alpha Blending的話,情況就更復(fù)雜了。