在Unity中如何進行水墨風3D渲染

雞年到了,在這裡先送給大家一副年畫,祝大家生活紅紅火。

這張圖可不是在木君用PhotoShop做的,而是在Unity里老老實實的寫Shader渲染出來的哦。因為畢設需要走非主流國畫風,所以最近一直在研究中國風的Shader。這幅聞雞起舞也算是階段性成果了吧。好了,廢話不多說,讓我們來看看這隻水墨風的雞是怎麼做出來的吧。

創意·Inspiration

第一步當然是到各大網站尋找一些好看的作品作為我們的參考,待會我們在Unity裡面做起來也能有跡可循嘛。說到這裡,大家是不是下意識的打開百度谷歌了呢。不!百度谷歌的圖片搜索功能的效率十分低下,偶爾還會蹦出一些非主流的畫風出來嚇人。在這裡,在木君給大家推薦Pinterest這個網站,檢索效率非常高。下面是我在輸入「Chinese Painting Chicken"後的一些檢索結果:(圖片來源為網路,侵權必刪)

雞的動態非常好,濃墨部分很精彩,特別是尾巴的部分,看似簡單的幾筆就把雞尾演繹得栩栩如生。仔細觀察,濃墨部分是通過色彩深淺的變化來營造出層次的,在Unity內也可以通過透明度的變化來勾勒出雞毛的層次,受教了!

一個大大的雞屁股 :[ ,雞身部分淡墨的使用非常考究,通過墨水浸染加紙面紋理的方式,把雞的身體描繪得十分寫意。而雞脖子那部分的留白,簡直神來之筆。通過留白製造意境也是水墨風渲染可以借鑒的手法呢,學習啦!

這幅畫的點在於紋理和筆觸勾勒。紙張表面的特殊紋理會賦予畫面一種很強烈的質感。在Shader的編寫過程中疊加一個Overlay的質感圖片可以達到這種效果。

素材·Assets

在Unity里做風格化的渲染其實就和PS差不多,都是素材堆砌加後期處理的過程。用過PS的同學們應該知道,好的素材是成功的一半,所以素材的重要性,不言而喻。

我們從3d模型找起。在這裡我用的是Asset(tao) Store(bao)上的一組帶動畫的鳥的模型。下圖中間那隻公雞就是我在渲染測試中使用的模型。

另外,我還需要一些筆觸,墨水痕迹以及紙面紙面質感的素材。當然這些素材是我在一邊調試一邊搜集的,這裡先放幾張出來,給大家找找感覺。

著色器·Shader

接下來就到重頭戲了!關於水墨風的shader怎麼寫,相信這個問題不少同學也曾經煩惱過,今天我就來展示一下我研究的成果吧。

首先上一張原本的模型,這個模型是注重真實感的,就是給人一種想把這隻雞殺了煲雞湯的感覺(在木君廣東人的身份就這麼暴露了嗎O.O)。這個模型本身的質量很高,但是現在我們需要把它變成國畫風。

綜合網上的一些研究,國畫風的著色器在編寫方面有兩個關鍵的部分:一個是邊緣檢測,就是給這隻大公雞描個黑邊,把它的輪廓勾勒出來;一個是調色,一般會用到降低色階,水墨畫里的用色通常是很少的,色彩太豐富就不像畫出來的啦。最後我還會介紹一下我進行後期質感處理的一些方法。

  • 邊緣檢測

邊緣檢測的原理非常簡單,就是法線和視線的點乘。公式如下:

Edge = Dot( Normal , View );

大家想想越是物體邊緣的地方,是不是法線(物體表面朝外的方向)和視線(觀察者看向物體的方向)的夾角越接近90度?把法線和視線點成得到了一個邊緣參數,這個參數越接近0說明該點越處於邊緣。用這個原理,就可以把邊緣的顏色描黑。在我們的工程中中描黑後的雞模型就變成了這樣:

/*哇,光禿禿的可以做成白切雞呢*/

這樣做出來的邊緣有一個漸變的趨勢,但是我們要的是描邊,而不是漸變。所以我們需要對邊緣參數設定一個閾值,並且把高於閾值的地方設定為白色,對低於閾值的地方進行一個平方的處理,公式如下:

EdgeOpt = (Edge > thred)? 1 : Edge * Edge ;

效果圖如下:

好像有那麼點水墨的感覺了呢,如果加上原來的材質會是什麼樣的呢?

一隻被勾了邊的雞出現了!但是雞的顏色還是有些奇怪,一般的水墨畫可沒有這麼斑斕的色彩,都是以極少的幾種甚至是單種顏色構成的。為了讓渲染的顏色更加接近於繪畫,我們需要進行顏色的調節。

  • 調節顏色

首先我們對貼圖進行降低色階的處理。所謂的降低色階就是把貼圖中相臨近的顏色合併,以減少總的顏色數量。這裡我們需要用到一個取整函數floor,簡單來說,就是先把表示為0~1之間的顏色參數擴大,然後取整,相當於分組合併,最後把顏色參數再縮放到0~1,整個過程還是挺巧妙的。降低色階的公式如下:

ColorPaint = floor( ColorTex * _Tooniness ) / _Tooniness;

以下是效果圖:

/*哇,變成碳燒雞了耶*/

色階降低之後伴隨的問題就是原本豐富的色塊邊緣被除掉,整個模型顯得死板沉悶。這時候我們就需要引入一些帶有質感筆觸的圖片,來增強色塊邊緣的質感。

這裡可以和大家分享一下我找的圖片。圖片是從Pinterest上找的,我主要的目標是一些有大色塊,並且有明顯的紙張材質感和邊緣筆觸的圖片。

之後就可以把找來的圖片和現在的渲染顏色相疊加。疊加圖片的思路大概是通過各種奇怪的演算法算出一個新的uv值,然後再從圖片中得到色彩值,再經過一系列奇怪的運算之後,得到最後的顏色值。和ps里的後期處理一樣,都是通過不斷的嘗試和調整得到才會得到一個比較好的結果。如果實在想不出好的疊加函數,可以參考ps里的函數(柔光,強光等等)。

對黑邊來說,我是用邊緣參數和點的uv值進行線性的疊加得到的一個新uv參數,再把圖片的顏色轉化成透明度。效果圖如下:

模型的邊緣可以看到有虛實的變化了,特別是尾巴的部分,顯得更有層次感了。

接下來我們對黑邊以內的部分進行調整。這裡我使用了一個小竅門,即用一個vector里的四個參數對一張圖片進行縮放旋轉處理。這個vector的xy可以作為二維偏差值,z可以作為旋轉的角度,w可以是縮放值。這樣就可以對加入的圖片進行移位,旋轉和縮放的調整了。

調整的效果如下:

可以看到內部的顏色也出現了一些筆觸,並且有留白,留白部分是透明的。

此外,對比參考圖片,我們發現雞的冠以及下巴上的胡會被畫上紅色,而雞脖子的部分會留白,尾部會用黑色來描繪,以下是我參考圖片做的渲染,其中疊加的紋理圖片是根據貼圖來製作的。

/*我聞到了濃濃的烏雞湯的味道!*/

這種方法涉及到對於單個模型貼圖的編輯,相當於美工給模型畫貼圖,泛用性比較差,僅供大家參考。

  • 整理·Finalization

接下來是P圖時間!我們需要利用一些濾鏡對畫面進行最後的修改。比如可以用Scree Overlay來做紙張的紋理,用Color Correction來提高飽和度。最後配上幾個裝逼用的文字,播放雞奔跑的動畫,就大功告成了。

  • 參考·Reference

在邊緣檢測方面,我的主要參考文章是下面這篇。原文發在facebook上,作者是Hui-Ku Shih。我引用了一篇轉載的,傳送門如下:

Unity Shader 05: 空間中的魔法參數 view direction

原文還附贈了一個可下載的.shader文件,是存在google drive上的。翻牆有困難的同學別著急,我會在文章的最後附上我自己的shader。

另外我還參考了一篇卡通風渲染的文章,用了裡面的降色階的代碼。傳送門如下:

【Unity Shader實戰】卡通風格的Shader(一)

最後就是分享我寫的Shader了,在木君已經把它打包成一個UnityPackage供大家使用!

【在木的遊戲作坊】水墨風聞雞起舞

提取密碼:sy6j

Github 地址

以下是我的公眾號的二維碼,歡迎關注哦!

weixin.qq.com/r/ZkSLk6T (二維碼自動識別)

公眾號名稱:在木的遊戲作坊

推薦閱讀:

井上雄彥為什麼能用毛筆畫漫畫?

TAG:Unity游戏引擎 | 独立游戏开发 | 水墨动画 |