記一次 glTF 模型的繪製性能提升:從ppt到dove,絲滑感受

測試不易,機會難尋。轉載請帶連接://www.cnblogs.com/onsummer/p/13543826.html;全網@秋意正寒

轉換思路

同樣一個模型,分別取如下轉換思路:

  • 原始模型👉fbx👉gltf
  • 原始模型👉obj👉gltf

但是我在打開中間格式fbx和obj時,發現這兩者雖然頂點數量一致,三角形數量一致,但是使用 Windows 3D 查看器查看時,發現前者的繪圖調用次數高達1600多次,而後者的繪圖調用次數只有217次,效果是完全相同的。
遂打開gltf文件進行分析,對比gltf數據對象如下:

對比gltf對象 fbx obj
node數量 1600多+2500多 1
mesh數量 1600多 1
primitive總量(每個mesh的primitive數量和) 1600多 217
特點 1個mesh存1個primitive,有2500多個node用於記錄層級關係 用1個node包裹1個mesh,mesh下有217個primitive

所以,故推斷影響 gltf、3dtiles(b3dm格式)渲染性能的一個重要指標,就是 primitive 的數量,primitive 是 GL 庫繪製圖形的最小單元。

在上表中看到有2500多虛node其實是不直接引用 mesh 的,所以即使 node 的總數有 3700 多個,但是實際上只復現了 1600 多次 mesh,且由於 1個 mesh 只有 1個 primitive,所以繪製次數等於1600多次很正常。

要性能還是要邏輯?

這是一個很難取捨的話題,如果需要在 gltf 層面組織好屬性數據、數據邏輯分層,那麼要儘可能控制好 node 的樹狀結構,控制好負責引用mesh的node的數量,控制好 primitive 的總數,盡量把材質一樣的 primitive 合併。

而如果要追求極致的性能,就不用太在意 node、mesh的組織,只要遇到材質一樣的 primitive,合併就是,遇到相對坐標不一樣,上轉換矩陣算它。

空間換時間

三維渲染是一個極其昔時的話題,因為現在似乎磁盤容量是足夠的——什麼你跟我說文件大了下載慢?你搞辣么大的模型幹啥?有大模型不會分拆嗎嗎嗎嗎

所以,很多時候要用空間換時間。

gltf 允許 1個mesh 由多個node 引用,那麼這個 mesh 的繪製次數就會累加,雖然復用了mesh下轄的 primitive所指向的數據,不用存儲多份mesh可以達到「只存一份數據重複繪製多次」的效果,但是這對性能毫無卵用,因為總的 primitive 數量還是上去了。

這個時候可以把需要重複的頂點根據 node 的坐標轉換信息計算出來,重複塞到盡量少的primitive中去。

有人說你這樣頂點數量上去了,文件體積也上去了:朋友,普通的750ti亮機卡繪製100w個點沒什麼壓力的~,文件體積這個,就需要數據轉換者自己權衡到底是重複mesh的引用,還是把重複的圖形多存一份(位置不一樣)塞到 primitive 中了。