TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

遊資網發表於2020-12-11
為期四天的騰訊遊戲開發者大會(Tencent Game Developers Conference , 簡稱TGDC)已於12月7日線上上正式召開。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

在昨晚的主題演講上,騰訊互動娛樂《天涯明月刀》手遊引擎負責人劉冰嘯以「用技術詮釋國風浪漫的歸去來——《天涯明月刀》手遊開發歷程」為主題,分享了《天涯明月刀》手遊如何在移動端平衡畫質、幀率與功耗來詮釋國風浪漫的。

為提升閱讀體驗,內容有刪減和調整:

大家好,我是劉冰嘯,是《天涯明月刀》手遊引擎的技術負責人。這次主要分享一下《天涯明月刀》手遊開發歷程中幾項關鍵點的技術決策和開放經歷。

1.手遊引擎開發三要素

手遊引擎開發需要考慮幾個重要要素。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

首先是畫質。這點可以進行一些選擇,比如是希望它突出遠景,還是突出近景?希望它是優於室內,還是室外?希望整個畫面效果是鮮豔,還是更加自然?是優先光線的表達,還是優先影子的效果?

第二是幀率。對天刀手遊這種強互動性的MMORPG遊戲,我們需要一個高而且穩定的幀率。

通常我們在PC開發的時候,只需顧慮兩個方面:先達成一個畫質的效果表現,然後通過優化不斷地提高幀率;幀率達成一個目標點後,再想辦法引入更好的畫質表現,兩者再不停地迭代。

而手遊,我們還引入了第三個維度——功耗。對手機來說,這是一個非常重要的維度,不僅會產生髮熱,而且還會影響到你遊玩的單次時間。

在這三個維度上,對其中任何一個維度的增加,都會影響到其它另外兩個維度的表達。

2.手遊優化

對天刀手遊的優化來說,開發引擎組採用了各種各樣的技術棧獲取更好的優化效果:

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

對多執行緒渲染引擎進行了優化,把大部分可以並行的工作,比如動畫、布料,都放到其它的執行緒中進行執行;

使用了ISPC自動生成NeonSIMD的程式碼,可以更好地提升CPU的執行效率;

在GPU和CPU的遮擋剔除中,使用了不同粒度的遮擋剔除演算法;

首先啟用了Vulkan API,通過它對GPU的記憶體進行更好的粒度上的管理;

實現GPU driven的渲染管線;

用computer輔助優化各項其它的渲染技術;

畫面上採用PBR材質和真實物理單位的lighting。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

我們在每次測試中都會進入一個重要的優化。

在第一次測試中,我們對unity進行了多執行緒的框架改動,把渲染執行緒和提交執行緒從主執行緒中剝離出來。因為在手遊的開發環境裡面,一個主要執行緒的持續工作,會帶來手機晶片的功率提升,這會導致更加嚴重的發熱。

在第二次測試中,我們引入了Vulkan API。相對GLES來說,Vulkan API有著更好的、更輕量級的呼叫。經過測試,我們可以做到在提交執行緒上獲得30%的CPU的效率提升。

在第三次測試中,我們引入了GPU driven技術。通過它可以把大部分CPU上的工作轉移到GPU上去執行,不僅提升了GPU的效率,也減少了從GPU到CPU之間的各種傳遞的頻寬。這項技術主要運用到地形、植被和家園系統裡面。

三測時我們還修改並提升了整體的光照表達,引入了自動曝光,提升了Tonemapping的效果,解決了由於真實物理單位引入之後,在不同的關照環境下lighting體現的一些細節的顏色丟失問題。

我們重新對sky lighting進行了定義,使得整個場景的室外表現更加豐富且具有對比度。

3.GPU driven技術優化要點

接下來主要分享一下我們採用GPU driven技術對渲染技術進行優化的一些要點。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

在開發過程中,我們經歷了多執行緒的優化,發現了手機平臺上一個優化的甜區:其實手機的多核,要比我們在端遊時代更早的進入了多核時代。現在安卓手機很多都是四加四的多核架構,有點像上一代主機平臺上看到的,在這些架構下,能讓開發者更多地使用這些輔助的計算單元來提升計算效率。

我們引擎組採用了兩個方向。一個是儘可能地剝離主執行緒上的計算,通過dispatch到其它執行緒上來提升它的計算效率;另一個是把計算轉入GPU compute,它相當於現代渲染框架的一個基石,除了GPU進行光柵化處理的部分之外,compute能夠完成大量的GPU渲染流程上的操作。

值得注意的是,compute的渲染語言其實完全能和GPU本身的硬體對應起來,例如裡面的Local Data Storage機制,ThreadGroup和Thread利用率的概念。

另外就是使用compute能發揮Vulkan更大的潛力,因為我們可以使用後者對GPU的同步行做出非常好的控制。

Compute作為一個獨立的單元,可以很好地把它的計算和GPU的其它計算並行起來。另外compute還是一個單獨的Queue,對比vs和ps的整套pipeline,它是一個非常簡化的單元,容易隨處擺放。

採用compute可以給GPU driven和Bindless開啟更廣闊的優化空間,甚至可以使用Async compute方式進一步並行compute和GPU的單元。

對天刀手游來說,開啟compute的關鍵突破點,就是GPU driven的地形系統。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

先看一下行業的發展方向。在最近幾年,GPU driven其實是一個相對比較熱門的研發方向。在SIGGRAPH 15上,育碧有一篇關於GPU driven的渲染管線的文章,主要將《刺客信條:大革命》的開發;2016年GDC上,EA的寒霜引擎也提到了GPU driven的pipeline;2018年,育碧的《FarCry5》也實現了相關的功能。

再講一下GPU驅動的渲染管線。它是GPU掌握實際的渲染控制,可以提供更細緻的渲染力度。例如在做渲染剔除的時候,CPU只能控制在object level,使用Object Bounding做剔除,但在GPU層面上,我們可以做到更進一步的控制,在Mesh cluster級別上,通過切分Mesh來獲得更好的力度控制。

它的另外一個好處是不需要GPU和CPU之間的資料來回傳遞,在理想的情況下,GPU driven甚至可以使用一個Drawcall繪製完成整個場景。當然,這個需要compute shader的支援,已經indirect drawing相關API的提供。

接下來看一下在天刀手遊裡,GPU地形實施之後的結果。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

在這之前,先介紹一下CPU地形常用的演算法。我們上一個版本里面的地形演算法是CPU端的Geometry Clipmap演算法,它採用視錐裁剪剔除方式;對比GPU driven,少了depth剔除;計算LOD的方式是根據距離計算的,而GPU driven可以根據距離和地形塊的複雜度來計算。

送入clipmap方式的頂點處,因為有兩個pass,其中一個要通過Virtual Texture來使用,這樣就需要21萬乘2的定點數。而在GPU driven的情況下,因為獲得比較好的剔除效果,只需要8萬6的頂點數。

再看一下GPU時間。在GPU driven的情況下,在iPhone8P上可以獲得2.9毫秒的時間開銷,這比通過CPU的方式節省了近四分之一的成本;而在CPU端獲得的收益更大,提交執行緒和渲染執行緒每個都可以獲得5毫秒以上的收益。

GPU driven的流程主要包含GPU driven和Virtual Texture兩個演算法,彼此的實現有互相交叉,出於簡化,接下來只講一下GPU driven。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

首先是一個深度mips生成,這部分演算法是在compute裡面實現的;

其次,我們是在compute裡面實現GPU遮擋剔除,它主要通過計算你所送入的patches的尺寸,看它處在哪一級的深度緩衝上,再對比這一級深度緩衝的深度和你的深度,來決定是否被depth剔除掉;

通過這個流程,我們可以獲得可視的patches數目,據此通過compute做indirect的Arguments buffer生成;

最後是把這些準備好的indirect buffer繪製出去,這就是整個地形GPU driven的渲染流程。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

其中有一個非常重要的優化,主要是利用compute裡面的Thread shared memory方式,減少了CPU到GPU之間的多次dispatch,也減少了binding memory pingpong操作。

它能應用的範圍主要在於對buffer做filter,例如我們經常在渲染管線中提到的Bloom、高斯模糊、自動曝光,這些對於區域進行filter的操作,都可以採用這些方法來獲得優化。

在天刀手遊中,我們會做第一次的dispatch,它會產生16*16的執行緒組,每組128條執行緒,這128條執行緒讀入深度,然後放入mips裡;第二步通過同步的方式,再把上一級mips相鄰的四個點取出來,合併選擇最深的單位,寫到第二級的mips裡,以此類推,完成四級的寫出。

在第二個dispatch裡,我們用同樣的方法dispatch一個執行緒組、128條執行緒,同樣把後面32*16的mips寫入完成。

我們還有另外一個機制需要優化,那就是LOD體系。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

在《FarCry》的實現裡面,它主要採用的是CPU四叉樹的方式來組織LOD的patches,根據距離更新四叉樹上的節點,然後根據相機的距離選擇這些節點,送入GPU進行indirect buffer和GPU Culling。

而天刀手遊則把這些patch資訊先通過offline的方式bake出來。我們在每一個相機發生位置變動的時候,會去更新這些bake出來的資訊,再根據這些資訊對改變的patch做過濾,然後生成新的indirect buffer。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

在我們完成GPU driven地形之後,引擎組會把所有的流程重新梳理一遍,再根據這些梳理出來的流程選擇可以應用GPU driven的其它渲染模組。

其中一個比較重要的渲染模組就是場景的植被管理。有經驗的渲染程式可能會直接意識到,其實草的geometry和地形的patch,或者是sector的管理是一個非常類似的概念,他們都有LOD,都有不同的geometry的表現。我們繪製這些geometry LOD的時候,最好的方法是通過Multi Draw Instanced Indirect的方案來做。

另外一點是每種型別的草的Texture,其實對應在地形上更像是一個地形的Virtual Texture機制,我們也可以用bindless的方式做繫結。

可是在Vulkan 1.0的平臺下,我們這兩個API Multi Draw Instanced或者是bindless都沒辦法獲得更好的支援。所以在天刀手遊的實現裡,我們只能將草的每種型別完成一次GPU driven的culling和Driven Indirect Buffer的生成。

TGDC | 天刀手遊引擎負責人:頂級畫面背後,我們解決了哪些難題?

在天刀手遊裡面,比較適合GPU driven的另外一個場景是家園的渲染。家園玩法要讓玩家儘可能地定製整個家園的地形、地表、牆壁、地板、物件等等,它需要非常多的geometry型別;再者它的區域相對比較小,只有128米*128米的自定義空間,在這種情況下,遮擋剔除必須要做得非常好。綜合這兩點,GPU driven是最適合的。

問題在於,家園裡的這些物件,其實和草的型別一樣,非常依賴Multi Draw Instanced Indirect和bindless這兩種API的實現。

對天刀手游來說,我們只能退而求其次,利用地形步驟算出來的HiZ的buffer做遮擋剔除,送入一套做遮擋剔除buffer的內容,通過CPU從readback的方案來獲得這些buffer的遮擋剔除的結果,然後在CPU端組織儘量多的instance物件。

Q&A

1.效能優化有什麼技術難點?聽說你們能以更低的規格實現更高標準,是怎麼做到的?

我們在實現的過程中,沒有特別去顧慮高規格和所謂的低規格,一般是設定一個標準,然後在這之上找一些平衡。舉個例子,前面提到的光照或者陰影表達,我們認為陰影的表達是弱於光照效果的,所以我們仍然採用了比較傳統的lightmap來bake shadow的方式,在大世界裡面並沒有使用實時的陰影。

這其實更像一個平衡的問題,要基於你的遊戲本身去承受的技術點,優先選擇面,最終達成一個適合你遊戲要求的技術方式。

2.像《天涯明月刀》這類從端遊移植到手遊的經典IP,從引擎技術角度如何更好地還原端遊品質?

這個問題要從兩方面回答。

一方面,明確我們需要去還原端遊的哪些特點。這個對我們遊戲的選擇還是十分明顯的:第一要更加註重遠景的表現;第二要有更好的角色表現。

另一方面是基於以上這些,我們要從端遊還原到手游上的一些畫面技術點,我們會去制定關鍵的技術要素,例如我們延續了端遊的PBR管線,但使用了比端遊更好的基於物理光照單位的一個lighting方式,使得我們的手遊在暗光的情況下表現非常好。

以上就是我今天的所有分享內容,謝謝各位。


整理:手遊那點事
地址:https://mp.weixin.qq.com/s/i11G_ZQvPp5-45ySB9pDrQ

相關文章