略談手機3D開發要點

2021-04-12 18:47:54 字數 3784 閱讀 1008

寫幾個非常有用的要點:

0 杜絕浮點運算

因為arm cpu一般不具備fpu協處理器,需要軟體方式模擬,經常需要數千個時鐘週期才能完成浮點數的加減計算,所以必須使用定點數。

這個大家都知道,但是要提一下的是,如果能夠為定點數提供封裝,然後作為內建型別使用,以後一定會方便很多。

再有乙個就是精度問題,軟體渲染中會為定點數精度的問題頭疼的地方會有很多。最好能在不同的場合使用不同小數字精度。一般來說,16:16與8:24是最常用的選擇。

1 記憶體讀寫絕對是最浪費時間的操作

大多數手機都使用一條16位bus來獲取指令和資料。由於所有指令都是32位的,bus速度就應當是cpu速度的兩倍,才能滿足需要。但實際上bus速度要比cpu慢,速度比在1:2到1:4之間。為了解決這個問題,大多數arm cpu都有乙個指令cache和乙個資料cache,通常這兩個cache的大小均為8k。只要cache中出現請求的指令或資料,cpu就能以全速直接獲得它們,而一旦需要訪問尚未載入到cache中的**和資料,就必須通過bus訪問記憶體。並且每次讀取乙個尚未到達cache的位元組時,cpu都要先填充一整條cache line,一條cache line可能是64 byte。由於bus是16位的,因此它將被占用 32個週期,而如果bus速度只有cpu的一半,cpu將會延遲64個週期。

因此,要確保記憶體盡可能緊密,同時還要檢查記憶體訪問模式,以判斷是否可以調整結構以使執行效率更高。如果需要定期訪問某一結構中的乙個資料成員並要處理大量這樣的結構,則要考慮將這個特殊的資料成員移到它自己的陣列中。基於同樣的原因,應該盡可能使用位元組或雙字,而且盡可能使用無符號型別。

但要注意的是,使用一系列ldr指令讀取連續記憶體塊的速度,要優於使用同樣數量的ldrb或ldrh指令,間斷地讀取這塊記憶體的速度。也就是說,讀取乙個word的速度可能快於讀取乙個byte!(實際測試過的確如此)

2 杜絕除法

arm cpu不支援除法,需要軟體方式模擬,這會消耗數千個時鐘週期。132-mhz的arm在理論上可以每秒執行1.32億條指令(或者2.64億條指令,如果其中一半運算是移位運算)。但是每秒7萬次的除法運算就會超過cpu的最大能力。也就是說,如果遊戲執行速度是每秒60幀,則每一幀僅做1000次除法就會達到cpu的極限。

大家都知道,所有除法都可以都替換成移位和乘法運算。但是,最好的方式還是用查詢表。但如果分子和分母都是32位整數,所需的查詢表就遠遠超出了可用的記憶體容量。一種解決方案就是縮小資料的範圍。因為a / b = a * ( 1 / b ,那麼實際上只需要乙個倒數表。再假設在大多數情況下16位精度就已經足夠,那麼查詢表只需要65536項。當然輸入輸出資料必須進行移位來保證正確的範圍,但最差的情況也將少於100個時鐘週期。

3 使用查詢表完成所有可能的任務

典型的查詢表有倒數、三角函式、alpha混合,光照等。也許還可以想到更多。

4 使用最高效的場景管理辦法,哪怕它最不靈活。

對於室內場景(其實非標準的室外場景也適用)bsp絕對是最好的選擇。場景資料不要使用3ds max或者其他的什麼東西建模,自己寫乙個csg的工具,用brush建模是最高效的選擇。

如果可能,不要使用實時的portal engine,預計算的pvs是最高效的,不要為那稍顯漫長的編譯時間耿耿於懷。要確保split plane選取得最好,要採用2-pass的bsp樹建立,要檢查visibility計算直至絕對沒有任何問題,而且要採用一切可以提速的手段,比如為su***ce打上hide,black的標籤,並且使用occluder。

不要忘了使用bsp對碰撞檢測加速,如果出現bug,看看是不是忘了加epsilon和brush hull。

bsp對於網路傳輸和ai計算等等也有很大幫助,bsp也可以通過radiosity計算lightmap而極大提高場景的視覺效果。如果覺得方方正正的場景過於枯燥,你還可以匯入3d模型。別忘了匯入模型也可以利用pvs的,而且也可以參與lightmap計算。

榨乾bsp的能力,同時不要理會別人對於bsp不靈活性的指責,手機上做3d最關心的還是效率。

5 僅在必需時使用透視紋理對映

大部分多邊形只需要仿射對映就足夠了,特別是手機的螢幕那麼小。但的確有些時候透視校正是必需的,比如當一塊很大的面距離鏡頭很近而且法線幾乎和視線垂直。那麼為了效果就去堅決校正它吧,但要把這個判斷條件寫得盡可能精巧。

提醒一下,每16個點才校正一次,效果是還可以接受的。而且有時候把過大的三角形切分一下,也是不錯的做法。

忘記constant z-slope或者分塊演算法或者別的什麼,它們太不成熟,如果研究就意味著浪費時間。

6 必須使用z-buffer

不要因為昂貴的記憶體訪問而拋棄z-buffer,無論你怎麼sort object,最後效果一定很差,而你也一定會在猶豫和掙扎中痛苦。

為了實現商業級遊戲的深度測試,z-buffer絕對是唯一的選擇。

但是z-sort(畫家演算法)並不是沒有用了,尤其是開著z-test的時候,我們可以用z-sort來優化。

7 把frame-buffer和z-buffer合併

這樣會顯著減少光柵化器訪問記憶體的次數。其實這個方法實現起來很簡單,關鍵是你是否能想到?

8 不要做frustum clipping

除了nearclip以外,不要做其它的clip,因為nearclip是在div-w之前做的,所以(被迫)不存在透視校正問題。而一般來說其它的clip因為效率問題都希望放在screenspace下進行,這就會帶來透視校正問題。

如果檢查底層貼圖扭曲的bug但很久沒找到原因,那應該立即看看是不是frustum clipping的問題。

9 vertex pipeline的規劃很重要

把各種transform,lighting,backface culling,div-w,clipping等等的順序認真思考一下,仔細排一排,而且減少不必要的步驟和計算,你會發現效率起碼提高幾倍。

10 使用boundingbox做clip

不要用sphere,它的形狀日後會成為追求最高效率極限的障礙。box clip同樣可以寫得很高效,提示一下就是用accept point和reject point,別忘了這個演算法也可以用在clip bspnode的時候。

11 可以做影子,甚至是真正的影子,但是別企圖完美

忘了shadow volume/map,soft shadow之類的東西,它們不是我們能承受的。當然,利用lightmap實現的效果除外。

12 即使是真正的3d遊戲,也可以使用偽3d的技術。

各種billboard,z-buffered 2d-sprite,2d-skybox等等,如果能夠聰明的使用,效果可能比用多邊形還要好。

13 做一些亮點

實現它們,這不會花掉太多時間。同時記住為特定的遊戲,定製特定的效果,才是最聰明的做法。

14 記住有時候你不得不面對的,幾個s級的效率殺手

糟糕的場景規劃(這個主要考驗關卡設計師的能力)

過多的透視校正

過多的alpha混合(即使你已經用了查詢表)

大面積的dynamic lightmap(動態光照圖)

15 不要猶豫使用彙編

當演算法級別的優化已經到達極致,不要畏懼於大規模的arm彙編優化,即使你以前只懂得pc彙編。

雖然沒有很多特殊的指令,但是大部分arm指令都很有特點,先研究它們,然後再把每乙個關鍵函式的優化都做到極致。

實踐證明,arm彙編優化對效率的提高絕對是非常顯著的。

16 先竭盡全力去把引擎做到最強,然後再忘記它的能力

最終遊戲的畫面要看整個團隊的努力和實力,無論多麼強大的引擎也無法掩飾糟糕的遊戲和美術設計。

多和策劃和美術討論,不要太快對他們的某個設計下結論。同時不要認為他們會以程式的角度思考問題,我們需要足夠的細心和耐心去溝通。

努力把特效,貼圖,調色盤,多邊形數量,骨骼動畫,以及各種設計做到最優。那麼最終的效果一定會讓人懷疑他真的在拿著乙個沒有任何硬體加速,不是專為遊戲設計的,普普通通的手機。

3D手機遊戲引擎

一,寒霜2引擎 frostbite 2 engine 但手機上貌似不支援 二,虛幻3引擎 unreal engine 3 沒用過 三,unity 引擎 本人使用過 以上3d引擎我推測應該都是基於 opengl es2.0圖形庫支援嵌入式裝置。2d手機遊戲引擎 一,cocos2d x cocos2d ...

手機支架3d列印模型 3D列印工藝模型製造

深圳風谷3d列印公司主要製作如下產品 3d列印手板模型,手板加工,sla雷射快速成型,電腦產品類,電子產品類,雷射成型類,家用電器類,交通類,手機,數碼產品,太陽能,通訊產品類,玩具產品,工藝品模型等.手板模型的作用 1.檢驗外觀設計。手板不僅是可視的,而且是可觸控的,它可以很直觀的以實物的形式把設...

不要為3d而3d

和以前的幾個朋友聊天,也有做game的。發現大家對3d技術都非常熱衷,但是這種熱衷顯得刻意的 為3d而3d,就有點捨本逐末。1 遊戲最重要的是策劃,需要具體的滿足人心底的某種需求,2 3d需要 好顯示卡的支援,這樣就將一部分使用者排斥在外面了。3 現在3d engine已經 很成熟了,通過這些上面的...