從開始接觸 Shader 就對風格化渲染感興趣了,也有學習過相關的技術知識,但因為美術能力不足而從未實行目標,直到半年前的某些機會開始深入美術領域,總算達成自己的里程碑了。
前言
2023 年六月時,我在 Youtube 看到風格化場景的線上課程宣傳,主要教場景美術需要的知識與技能,並在 UE4 中重建各種場景原畫,學生作品都相當吸睛,因此我在經濟與時間的評估下決定購買,並利用暑假期間學習了大多內容。
除此之外,這學期(二上)也有一門跟 3D 場景有關的選修,期末作業需要交出整個城鎮場景,我就趁這機會抱走班上所有 3D 美術大腿,跟組員做出精美的期末成果。
成果展示
先上成果,風光明媚的城鎮。除了 Skybox 是免費資產以外,其他內容都是我們製作的,包括房屋、佈景、材質貼圖、花草樹木跟牆外的巨人。
注意事項
這篇日誌的成果是在「分組作業」的情況下完成,選修科目《3D 場景設計》中除了我(小呈)以外還有三位隊友(YukiO3O、NatsuNa、水い),內文會替組員的工作註名。
雖然是學校作業,但製作內容是完全超出課程範圍的,先註明以免產生誤會。我在暑假就進行過兩次個人練習,先前也已自學電腦圖學、著色器與相關數學知識三年半,因此這次作業應該視作過去累積經驗的實施,而非單個學期(四個月)內就達成的快速成果。
專案儲存庫放在文末,有興趣的讀者也可以下載原始檔研究。內文會根據閱讀性進行編排,但大致符合現實時間軸,我們的製作流程並不正規,再加上篇幅問題可能省略部分細節,所以分享內容僅供參考歐 :P
建築製作
使用工具與環境:
Unity 2021.3.8
Blender, 3DS Max, ZBush
Substance Designer, Substance Painter
以下正文!
尋找參考
我們在第一堂客完成組隊,並在 ArtStation 上找了各種作品參考風格。學校課程的前半是室內場景,但我們提早往分組的期末準備了。
剛開始其實找得很零散,這張圖是為了文章才湊出來的
建築設計
總之,在有粗略方向後也嘗試設計過外觀…但這顯然這不是我擅長的,只拉出某些詭異幾何結構。
後續交給組員(Yuki030)重新設計,對方先製作了兩款初版(左上)與合併後的次版(右上),最後再根據參考圖製作出最終版的外觀,主建築與高塔(亮晶晶的兩張)。
另外兩位組員也設計了其他款式的建築、高塔(左 NatsuNa)與風車(右 水い)。
貼圖製作
為了節省資源,場景建築會製做成可重用的模組,因此貼圖方式也會受到影響。單體物件可能會先拆 UV 再畫貼圖,但模組物件則要先規劃好貼圖的使用與分配,製作或規劃完才拆,所以這裡也是先製作貼圖。
Google 3D modular building
我們的背景設定在中世紀歐洲,材質可以參考動畫和現實中的結構,以磚牆為例可能有三層:最內的結構層(磚塊),中間的填充層(水泥)與最外的塗料層(油漆)。
Google 羅滕堡照片,他們建築狀況維護的不錯
貼圖製作由我負責,使用的工具是 Substance Designer 2023(Steam 版),但這是許多大廠都會使用的程序貼圖製作工具,相當方便。基本上就是連連看,運作(數學)原理類似距離場的加減。
製作過程就跟寫程式一樣,將目標拆解成基本元素,分析最終效果是怎麼構成的,再一步步組合成貼圖。以磚塊為例,從基本模式(Pattern)開始,添加細節、添加顏色、添加光影、添加輪廓,最後再調整色調、添加筆觸效果。
除了磚塊以外還做了木板、石磚、水泥、青苔和屋瓦,都是建築會使用到的 PBR 材質,但透過模糊、預繪光影、加強輪廓與覆蓋筆觸等方式讓貼圖看起來更風格化。貼圖採用四方循環(Tileable),確保任何方向都能無限延伸。
材質的四張貼圖分別是 Albedo, Normal, Roughness 與 Ambient Occlusion
放進引擎測試,檢查實際渲染時的色調與大小,解析度為 2m : 512px,教學說這是手遊低標。程序生成的好處就是修改方便,我能直接帶檔案到學校給組員操作,他們只要調調參數就能改變磚塊大小、破損程度、色調飽和或筆觸效果。
飽和度過高的初版磚塊貼圖
模組拆解
完成貼圖後就是模組化作業,拆解工作也由我進行。合併零碎物件、隱藏外部裝飾、根據原始設計重建簡略版建築,還要將尺寸修正為整數,確保後續組裝時的規格是統一的。
接著把模型拆解成立體拼圖,包括各種尺寸的屋頂、牆面、木條與地基,要確認「每顆頂點」都在正確位置的繁瑣作業,沒對齊的話後續組裝就會產生縫隙,是過程的枯燥惡夢之一。
另一項枯燥的惡夢就是拆 UV,一樣要確認「每顆頂點」都在理想位置,否則也會出現貼圖接縫。因為貼圖採樣有循環模式,所以 UV 超出範圍也沒關係。
拆完(或拆的同時)給物件上材質,如果模組同時有多個部分則透過多重材質達到效果。以使用四種材質的屋頂為例,它使用了外側瓦片、內側木板、封邊木條和磚牆牆面。
木條貼圖是由組員(YukiO3O)雕刻與烘培的,同樣超出課堂範圍,我只有簡單解釋製程和提供筆記而已,剩下都是對方獨自完成的,效果相當不錯。
視需求與做法差異,牆面裝飾可能會直接製作或另外嵌入,我們選後者。窗戶物件都是由組員(NatsuNa)製作的。
湊齊所有拼圖後就能組裝了,引擎中的相關工作也由我進行。輸出 FBX、導入 Unity、建立 Prefab、分配材質最後拼起房屋。還寫了簡單的對齊工具,修正 Unity 物件旋轉的誤差問題。
材質效果
雖然已經有完整建築了,但視覺表現還不理想,主要的問題是貼圖的一致與重複性讓建築顯得單調。最簡單的方案是進行混合,將先前製作的覆蓋材質(水泥、青苔)疊加在基礎材質上(磚塊、屋瓦)。
普遍的混合方式是插值(Lerp),透過權重調整兩種貼圖顯示的比例,但他的問題是缺乏細節,混合效果往往呈片狀(如左圖)。另一種進階技巧是高度混合(Height Lerp),利用高度圖作為閾值,材質只會在權重高於閾值顯示(如中圖,右圖是判斷示意圖)。
圖片來源為 UE4: Detailed Texture Blending with HeightLerp and Vertex Painting
高度混合的好處是能提供「巨量」細節,而計算成本也不會高到難以接受,只要多一個 smoothstep()
即可,以下是 HSLS 算式。
hlsl
void HeightLerp_float(float4 a, float4 b, float transition, float height, float fade, out float4 result) { float t = smoothstep(height - fade, height + fade, transition); result = lerp(a, b, t); }
混合權重可以使用世界座標噪聲決定,但這種方法就無法控制其發生時機。另一種方式是使用模型資料中的頂點色(Vertex Color),利用 Shader 讀取並將 RGB 數值作為不同圖層的權重混合。
如此一來,就能利用程式修改頂點色,達成手動控制混合的效果。為了實現功能,我也做了自製筆刷工具,可筆刷能隨意調整大小、強度與漸變範圍,還有遮罩功能避免畫到不同材質,主要是編輯器做工繁瑣,沒什麼技術深度,就真的很繁瑣。
青苔從屋瓦縫隙生長,而不是直接覆蓋在上面
最後,為了讓平面模型看起來有更多細節,我也抄了一段視差遮擋(Parallax Occlusion)的程式來用。他會在高度圖上進行射線投射(射線邁進),根據視角檢測會不會發生遮擋,決定實際繪製的像素為何者。
組合後的房屋,但這次多了混合貼圖與視差效果,顯得精緻不少。抱歉了效能但我真的想要那個酷酷的立體效果。
地形環境
主要地形是使用 Unity 內建工具(Terrain)製作的,也安裝了官方的功能擴展包 Terrain Sample Asset Pack,可以在 Package Manager 的 Terrain Tools 中找到下載連結。
我們使用的功能包括地形筆刷、貼圖筆刷以及樹木、細節繪製功能,Unity 基礎知識這裡就不多贅述。我用 Substance Designer 製作了三種不同的地形材質,草地、沙石地與石磚道路。
材質是預設的 URP Terrain Lit,支援 Height-base Blend(Height Lerp)功能,開啟後也能讓材質交界產生更多細節。只要在 Terrain Layer 中設置 Mask Map,並在 Paint Texture 功能中開啟 Enable Height-base Blend 即可。
Mask Map 的 RGBA 分別為 Metallic, AmbientOcclusion, Height, Smoothness
給場景添加一些綠意,蓬蓬樹製作起來不難,只要建出樹幹再放一堆使用 Alpha Clip 的葉片,然後設置葉片的 Normal 方向就好了。比較要注意的是效能問題,但這裡也先不深入優化部分。
植被屬於大量出現在場景的物件,一棵棵手動種是很不切實際的,場景編輯會用更有效率的方式進行。這裡使用的是 Terrain 內建的 Paint Tree 功能,能直接用筆刷刷出樹木。
花草也用相似方式製作,在共用貼圖上繪製圖像(或雕刻烘培),再建立低模、貼上、渲染。上面是我練習時先做的,下面色彩更鮮豔的是組員(Yuki030)在作業期間製作,也是十分精緻。
草地使用地形內建的 Details Paint 繪製密度圖,但我製做了額外的地形混合效果。簡單來說就是:拍攝一張地形顏色和深度圖,再用距離場混色讓物件底部融入地形,避免不自然的植被交界。
除了地表混色之外,我也給草添加了環境漸變,不然整片草原顏色都相同太不自然了。我做了漸變遮罩讓草根據世界座標混色。
最後,給環境放上漂亮的水就完事了,找了 URP 水面教學來參考,也額外拿軌跡粒子做了風。花草刷上、放片池塘、打光後再放棟房屋,風光明媚小場景(期中作業)就完成了。
城鎮設計
該有的物件都大致湊齊了,我們也加快腳步製做期末,目標是一個城鎮。
參考概念
我們沒有參考的場景原畫,只是先在引擎中畫了簡單地形,餵給 AI 看能不能生出個所以然,咒文詠唱與魔法的跌代由組員(YukiO3O)進行。
區域規劃
圖是有了…但細節過於抽象也沒派上多少用途,而我購買的課程是根據原畫重建場景,不包括設計場景的部分,所以城鎮規劃初期蠻混亂的。道路看起來像醜醜的麥田圈,背景塞了幾座簡陋的山當邊界阻擋。
後面交給組員(YukiO3O)設計,用道路分割出比較有結構性的區域。左邊為山地、中後方是城堡高地、中間的凹陷空地是廣場,道路之間則穿插了居住區。
然後再交給另一位組員(水い)接手,劃出建築區塊後重新調整房屋擺設,讓整體看起來不那麼凌亂。
最後再交回我與組員(YukiO3O)將佈局修改到最終版本。把高地修的更有層次並擺上房屋,填平中間的凹陷。最後決定放棄城堡,畢竟組員還扛著各科作業跟教授的案子,歡迎來到設計系。
封邊岩石
用高度圖生成地形是很普遍的做法,但他的缺點是過於平滑與斜坡的著色效果不好,所以在山壁這種會產生劇烈起伏的地方會很難看。
這種情況就要用非地形的模型「封邊」,放上預製的石塊或牆面擋住斜坡,讓地形顯得更有稜角。時間關係牆面(右圖)做的有點敷衍,但應該能看出差異。
山石的效果不錯,是組員(水い)製做的,我再用簡單的方向混色,讓朝上的部份畫出草地材質。
來張俯瞰圖,把醜醜山壁跟的斜坡堵上,把不同高度間的階梯補上之後就更有樣子了。背景的山也放了跟石頭相同的材質。
市集活動
我們從規劃開始就預留了廣場空地,最後決定在這裡擺放市集。請組員(NatsuNa)製作了相關物件,箱子、籃子、推車和棚子等,還將水果圖片塞進容器讓物件看起來更多樣。
將物件擺放成市集該有的樣子,城鎮顯得更繁榮了!
細節佈置
最後的最後就是點綴一些細節,刷上樹木、灌木與花花草草,擺上柵欄、路燈與稻草人等佈景,主要由組員(Yuki030)完成。
調整 FOG 讓遠處有點霧茫茫的效果。地圖還有離島,但沒時間擺設就空著了。邊界放了一隻巨人,是組員(水い)製作的 ww
河床使用深色的泥土材質,再埋一些石塊就有樣子了,雖然水擋著其實看不太到東西。
感謝閱讀
完工!!!!!!!!!!!!!
我也抓了第一人稱控制的資源來用,錄一些場景內走動的畫面。
工作總結
感謝三位組員的努力,最後來做一下工作總結,截個漂亮的圖讓大家放進作品集。首先是我(小呈)的部分,主要負責技美與引擎相關工作,材質貼圖、著色器、渲染、花草樹木和模組拆解。
組員(YukiO3O)負責建築設計,製做大型房屋與配件、主塔、木條貼圖、佈景物件、花草樹木、詠唱概念圖與場景細節編輯。
組員(NatsuNa)負責建築設計,製做中小型房屋、小塔、窗戶、柵欄與市集物件。
組員(水い)負責山石製作,完成大小石塊、特殊建築、初步城鎮規劃與超大型巨人。
心得感想
這裡是專案儲存庫,所有模型、貼圖、著色器與自製工具都在裡面,感興趣的人歡迎下載看看,僅供學術研究歐!
https://github.com/angus945/3D-Scene-Design-Course
雖然有做一些 Shader 來達成自訂效果,但部分物件還是使用 URP 預設的 Lit 材質,其實預設只要貼圖給對,放好 Skybox 與 Post Processing 就有不錯的畫面了。
可惜的是效能問題尚未解決,實時 FPS 表現不穩定,最大開銷是材質的多層採樣與視差計算,再來是植被渲染之類的,應該能透過 LOD 設置緩解?
其實我也看不懂,只是放進來讓我感覺更專業而已 (X
而這篇文章也只是「城鎮場景」製做過程,而非「遊戲場景」設計,因為遊戲場景是為機制服務的,但我們的成品並沒有考量任何機制內容,只針對視覺表現做設計。
由於上面兩項因素,雖然成果看上去很漂亮,但目前仍不具有應用價值。出於時間考量,後續也沒打算進行更多修正,恐怕得等出現真正需求時才會深入。
大致就醬,從開始場景課題到現在也過了半年,在兩次個人練習後帶著組員完成這項宏大任務,而我研究 Shader 的最初目標總算達成了,走三年半總算摸到了最大的里程碑,成就感滿滿。
感謝閱讀,這篇日誌是我們場景製作過程的總結,寫完也代表課題暫時告一段落了,有任何想法或疑問歡迎在文章底部或轉載社群留言噢!
下一個目標是什麼呢~
資源參考
線上課程課官方 Youtube 頻道:魔灯Modeng
我買的是他們的課程錄影(無回饋版):Modeng Stylized Scene Creation In Unreal Engine V1.0 (No Feedback Service)
地形混合:Terrain and Mesh Blending in Unity
URP 自訂光影:Custom Lighting in Unity URP Shader Graph! Ready for Toony Lights
蓬蓬樹: How to Make a Stylized Tree by using Blender and Unity
視差著色器:Parallax Mapping in Unity Shader Graph
水面:3D Stylized Water with Refraction and Foam Shader Graph - Unity Tutorial
高度混合:UE4: Detailed Texture Blending with HeightLerp and Vertex Painting
Blender 批量導出:Batex
Skybox:Fantasy Skybox FREE