VR渲染需要左右眼兩幅不同的畫面,現在的大部分引擎都是暴力的直接渲染兩遍,這樣做想想性能也很難達到75FPS(或90FPS)。
以Oculus DK2為例,1920x1080@75FPS,加上Super Sampling就變成了(UE4默認135%)2592x1458@75FPS。
如果是Oculus的消費者版本和HTC Vive,分辨率和刷新率更是提升到了2160x1200@90FPS, 推薦配置是GTX980驚恐,以135%的Super Sampling為標準的話,只是Color Buffer每秒的數據量就有2160x1200x1.35x90x8 byte ≈ 2.34GB。這還沒算Post Processing里的N多張Render Target和Deferred Rendering的GBuffer、Light Buffer。
性能永遠是VR渲染的最具有挑戰的部分,本著能省一點是一點的思路,VR的渲染優化我總結了這么一些:
雖然VR渲染需要左右兩幅畫面, 但是有很多效果是不需要畫兩次的:
Shadow Map
部分的Reflection
Occlusion Query
大多數Post Processing
API層面的優化,有這么幾個思路:
如果實現了多線程的渲染,一般會有一個Command Buffer,直接分別以不同的View提交兩次。針對每個物體分別提交兩次, 相比上面這個State切換開銷會節省一些。使用Geometry Shader直接把Mesh分成左右眼的,drawcall不會翻倍了。但是坑爹的GS性能不咋地。使用Instancing一次drawcall繪制兩個Viewport, 跟GS類似,但性能大約是GS的3倍。這只是減少一些API調用、State切換還有Vertex處理的消耗,那瓶頸最大的Pixel處理的消耗怎么減少呢?
Valve使用一個Stencil Mesh, 剔除了17%的像素。
NVIDIA的GameWorks也提供了一種方法, 叫Multi-Resolution Shading,大概的思路就是邊緣的像素經過變形后會損失一些,另外人眼對視線中心的像素更敏感,所以周圍一圈可以降低分辨率來渲染。通過這種方式可以節省25%到50的像素。
硬件方面,NVIDIA和AMD都推出了雙GPU渲染的支持,即每塊GPU渲染一只眼睛的畫面。嗯,這一定是個陰謀,他們肯定在偷著樂:這下顯卡不愁賣了。
SONY的PS VR在PS4的機能下實現了120FPS。聽起來不可思議,實際是60FPS通過reproject插值出中間幀,跟Killzone的Temporal Reprojection 和Oculus的Timewrap差不多原理。