Unity预计算全局实时GI(gi params)
Unity提供許多進階的光照貼圖控制方法,這些設定被放在一個光照參數集(LightmapParameters)的資源里,好讓設定能在不同的項目場景或是透過版本控制和團隊一起共享。
要建立一個Lightmap Parameters資源,先找到Project窗口
從Create下拉選單建立(Create> Lightmap Parameters)
我們也可以在Project接口里右鍵單擊選(Asset> Create > Lightmap Parameters)來建立。
透過這個參數集可以針對烘焙光照或預計算GI做更高階的設定
建立完成的光照參數集可以被指定給靜態對象。
從Hierarchy接口選擇你要指定變量集的對象,對象必須是帶有Mesh Renderer組件的靜態對象。
開啟Lighting接口(Window> Lighting)并選擇Object頁簽
從Advance Parameters下拉選單指定你的變量集給對象,右邊的"Edit"按鈕是開啟編輯光照變量的快捷方式。
從Lighting接口里的AdvancedParameters字段指定光照參數集
同一個光照參數集可以指定個許多不同的對象,你只要從Hierarchy接口一次把要指定的對象全選起來,執行上面說明的步驟把檔案指定到Advanced Parameters字段即可。
光照參數集:實例(per-instance)還是預制(per-Prefab)好?
和拆UV的部分很像,光照參數集可以指定給Prefab預制對象或給場景里的獨立對象,一旦參數集被貼上對象就會覆蓋掉對象身上舊有的設定。
這個方法的好處是你可以把正常情況下會用到的光照設定貼在預制對象上,然后依照不同需求修改覆蓋場景里實例對象身上的光照參數設定。
本教學里,我們會從一個實例對象身上示范如何使用光照參數集,主要是因為我們想根據使用的對象來選擇不同的光照參數集。
預設參數集
這部分適合用來設定場景預設的光照參數,這個參數集待會會被指定給所有場景里面帶有Mesh Renderer組件但卻還沒指定Lightmap Parameters的對象。場景里建立的任何帶有Mesh Renderer的對象都會以此為基礎,這樣可以省下手動指定的時間。
開啟Lighting接口(Window> Lighting)并選擇Scene頁簽
從General GI區塊里找到DefaultParameter,選擇你剛才建立的光照參數集。
雖然新的對象會開始采用這個預設設定值,你仍然可以從Advanced Parameter參數單讀覆蓋它。
默認的設定會反映到所有新的靜態對象
Unity預設有幾組光照參數集可以選,分別是:
Default - HighResolution
Default - Medium
Default - LowResolution
Default - VeryLowResolution
這幾個不同的設定存有會影響到光照結果的設定像是光照貼圖分辨率,光照圖大小以及其他一些進階選項設定,可以用來快速調整總體結果。
光照參數集說明
Unity默認的參數組合事實上已經很適合大多數的情況,但我們還可以建立自己的參數組并做更多的微調,來讓GI計算達到比預期更好的結果。
Unity手冊上關于光照參數集有個別的詳盡說明,但針對這個教學我們也會重點說明幾個最有用的設定。
Resolution
分辨率的值確訂了對象采用的光照貼圖解析,這個值會和Lighting接口里的分辨率做加乘。比如說,如果場景分辨率設為2,這里的分辨率設為0.5,那所有帶有這個參數集的對象都會采用1texel/unit來計算光照貼圖。
由于PRGI只會呈現場景里的漫反射(diffuse)和間接照明,所以我們不需要用到像傳統烘焙貼圖那么高(20-30)的采樣值,通常設定2-3已經很好了。如果是戶外場景,甚至可以縮小很多倍像是0.1就足以提供足夠的細節。
分辨率值很大光照貼圖所產生的影子斑點可以把Irradiance Budget這個參數調高來獲得緩解。
注意,當分辨率值很大時,在較低分辨率下可能會產生奇怪的陰影,這些陰影在最終的光照貼圖里可能看起來像是斑點或臟污。如果有這種情況可以試著把Irradiance Budget參數提高來獲得改善。
Cluster Resolution
叢集分辨率用來決定1個像素里能有多少叢集數量。假如這個值設為1,代表光照圖里面每個像素都都會有一個叢集,0.5代表一個像素會有2個叢集,換句話說叢集會是光照圖的兩倍大。
進一步來說,可以想象如果我們把場景的分辨率設為1,并建立一個1x1x1的方塊,然后指定這個光照參數集給對象,那么方塊的每一面都會有1個叢集。如果我們把分辨率改為2,結果就會變成2(1x1),方塊的每一面叢集會變成4個。
上圖可以看到一個分辨率設為1的1x1x1方塊,光照參數設定叢集分辨率(Cluster Resolution)為1和光照貼圖分辨率為2時,我們每一面都會有4個叢集。
在大多數的情況下,Cluster Resolution只需要設為低于貼圖像素(lightmap texels)大小即可,例如Default -HighResolution設定值為0.6。
一個場景中叢集太多的話會很快拉高預計算時間,還會影響到實時場景的光照效能,因此必須要把叢集的數量花在刀口上,永遠以保持質量盡可能的降低叢集數量為目標。
將光照貼圖解析和叢集分辨率保持指定比例,這樣我們可以和場景整體的分辨率建立一個相對關系。我們可以把Lighting接口里面的分辨率定義為高分辨率作為整體設定,然后針對個別對象微調各自的光照參數集。
Unity采用這種分層法方便讓開發者能更全觀的控制場景光照,不然要針對每個對象手動都設定光照參數的值會很麻煩。
Irradiance Budget
我們之前說明過光照計算是如何用叢集來計算靜態對象的預計算光照,在預計算的過程里,叢集之間的關系被建立起來,好讓光線得以在叢集網內快速傳遞。
在本質上,光照貼圖像素值的算法是基于叢集從該像素的位置對場景的一個檢視所計算得來,這會讓我們可以很快計算叢集之間的光照反射最后產生一個全局光照,這些叢集就能在畫面渲染完之前給予適當的樣本數。
Irradiance Budget(輻照度范圍)用來制訂當叢集采樣時每個光照貼圖像素所使用到的內存量,這會決定照明結果的精度,數值太低代表每個貼圖像素在記錄時使用較少內存同時提升CPU效能,代價就是會失真,數值越低光照結果會越模糊。反過來看,數值拉高GI會更準確,但內存和CPU的消耗都會提升。
如果我們的預計算在Runtime執行時更新有點慢或會lag,可能降低這個值會得到改善,這個設定比較適合用在不用精細的對象,很大、模糊或遙遠的物件。
Irradiance Quality
當計算PRGI時,每個光照貼圖像素會開始對場景投出射線,然后將可視數據報告給附近的叢集,然后貼圖像素就會得到每個叢集的百分比數值,這個值用來定義光照貼圖里每個像素從叢集所分到的可視數據,而一欄設定就是用來設定每個像素能對場景投射多少射線。
如果場景里的對象和周圍對象光照不合的情況下可以斟酌加大這個值,有時該暗的時候光照結果卻意想不到的亮,有可能是因為投射到場景的射線不足或遮擋到,導致漏算叢集資料。同樣該亮的的放如果射線沒有檢查到,可能會造成過暗。
提高射線的投射量就能解決類似的問題,代價就是增加預計算的時間,要優化這個時間,我們應該找出最適合的值來達到我們理想的照明效果。請注意,這個值不會影響到Runtime時的效能。
Backface Tolerance
當射線從光照貼圖像素投射出,從場景叢集搜集光線時有時會打到幾何的背面,當計算全局光照時我們只需要關心投射到物體表面的光照,從背面來的光照資源通常都會忽略掉,這些從背面來的光照數據會破壞光照結果,因此調整這個值能防止這類情況發生。
這里的地板上的陰影就是Unity在計算期間從對象無效的背面所創造的,增加Backface Tolerance能改善這個問題。
Backface Tolerance必須指定從前方光源來的百分比,好讓正面的像素被判定為有效。假如一個貼圖像素沒通過測試,Unity會采用鄰近的像素值嘗試算得正確光照數據。
調整這個值并不會影響PRGI運算效能,也不會對預計算時間長度有太大影響。反而是蠻適合在調整Irradiance Budget都無法解決的場景貼圖太亮或太暗問題時,Backfacetolerance會是一個不錯的除錯工具。
Modelling Tolerance
有時候在場景靜態對象中存在小間隙的區域會產生黑色的光暈或是不需要殘像,很容易發生在鄰近有相反幾何圖形的區域,像是地板上的對象:
像這樣物品的黑暗邊緣通常可以透過加大Modelling Tolerance來改善
通常在這樣的情況下,物體和物體之間存在著小小的縫隙,因為沒有太多光線可以進入,導致非常暗的光照圖產生。當光照分辨率低的時候,這些黑暗像素的大小可能會導致它們跑出遮擋物的邊界并產生不協調的黑色塊。
Modelling Tolerance是用來忽略比Threshold值還小的細節,提高這個值可以確保Unity在計算GI時忽略掉非常靠近其他物體表面的幾何面,這個值越高代表Light Transport這個階段需要額外計算忽略這些間隙,調低ModellingTolerance也能確保小對象不會被遺漏計算。
Modelling Tolerance不會影響PRGI的優化,對于計算時間和執行效能也沒甚么負面影響,它能用在一些除錯流程上,解決連Irradiance Budget都無法改善的殘影問題。
開始建立Lightmap Parameters光照參數資源
現在我們已經明白光照參數能做甚么了,可以開始嘗試建立這些資源。
打開LightingTutorialStart場景
在Project窗口找到Assets >LightmapParameters目錄并點進去
從Project窗口最上面的下拉選單建立一個光照參數集(Create > Lightmap Parameters
把對象名稱改為"TutorialTerrainLow"
這個對象從鏡頭看起來非常大,蠻適合設一個光照參數集而不是用場景預設的
接下來我們要把剛剛新建的光照參數集指定給這個對象
在場景窗口里,選擇最接近主場景的兩座山,這些山都已經被命名為"MountainPeak"。注意,我們將忽略最遠的山。
從Inspector接口確認兩個對象都是設定為靜態對象
開啟Lighting窗口(Window> Lighting)并選擇Scene頁簽
確保最底下的Auto是打勾
改選擇Object頁簽
從Advanced Parameters下拉選單選擇剛建立的TutorialTerrainLow
單擊右邊的Edit按鈕,準備開始調整設定
預設的光照參數集
首先我們要看的是Resolution,降低這個值可以加速預計算時間同時也提升執行效能,所以我們應該目標定在不影響畫質的前提下采用較低的分辨率。
會很接近看的對象可以設比較高的值,但是兩座山距離鏡頭都非常遠,因此這個例子設低一點是比較好的。這些大對象表面材質相當一致,從鏡頭的角度來看,接收到光的顏色變化也不大,所以可以降低這個值而不會影響結果質量。
像是山或地形的大場景,采用默認值反而很浪費
使用較低的分辨率犧牲質量但可以大大節省預計算和執行效能
慢慢的降低TutorialTerrainLow光照參數集里面的Resolution參數并觀察結果的變化。
請記得這里的分辨率和Lighting窗口里的場景分辨率是會相乘的,目前場景分辨率是1,代表如果這里的分辨率小于1的話,輸出的光照貼圖每unit也會小于1像素(texel)
兩座山和其他的對象距離非常遠,它們不可能接受頻率很高的光照,因此如果我們采用較低的分辨率損失的質量不會太多。教學里我們發現用0.05就足以采樣該有的光照數據。
從Project窗口點選TutorialTerrainLow對象
從Inspector界面把Resolution設為0.05
然后來看看Cluster Resolution的值,之前討論過,這個值也是一個用來和光照貼圖像素數量相乘計算叢集的乘法器,當數值是1的時候叢集的數量就等于光照貼圖像素的數量,因此低于1會比較好。叢集本質上是為了計算PRGI所產生類似靜態場景的仿真體,所以只有在數量不足以反映物體的光照反射時才需要加大這個值。
和光照貼圖解析很像,這兩座山的叢集分辨率可以設很低,如果把它設的跟其他小場景一樣的話,代表可能會需要幾百個小場景的叢集量來覆蓋這兩座山。
對于很大的對象,叢集分辨率可以設很低
把Scene窗口左上方的繪制模式改為Clustering
從Project窗口選擇TutorialTerrainLow光照參數集
從Inspector界面里把ClusterResolution的值慢慢降低,彩色色塊會慢慢變大,數量會慢慢變少
或是改用Lit Clustering繪制模式來評估設定的分辨率是否足以采樣場景細節的光照。
把Scene窗口左上方的繪制模式改為LitClustering
從Project窗口選擇TutorialTerrainLow光照參數集
從Inspector接口里把ClusterResolution的值慢慢降低,觀察場景的變化。
調整到這里時,可以問問自己是否能接受更低的叢集數值,如果繼續調高對畫質已經沒有好處了,那就應該要往下修正。請記住叢集數量對于預計算的時間和GI有很大的影響,這個案例我們發現用0.4是很適合的值。
從Project窗口選擇TutorialTerrainLow光照參數集
設定Cluster Resolution為0.4
LitClustering繪制模式可以用來評估場景里是否有足夠的叢集
需多情況下只是單單降低光照和叢集的分辨率就足夠提升很大的效能,但是我們還能用IrradianceBudget和Irradiance Quality做更進一步的改進.
首先我們先看看Irradiance Budget,如之前所提,這個值控制貼圖像素會占用多少內存計算,為了執行時的效能,我們應該使用最低的值以免產生負面的影響。
如果預計算的結果模糊不清的話可以試著調大這個值,對于場景里有著高對比度度卻沒有被精確表達出來的區域是很有用的。
Irradiance場景繪制模式可以用來評估調整Irradiance Budget或Quality的值
兩座山照明的頻率沒有很高,也沒有任何高對比度的光照處理,代表在不影響質量的情況下,默認值128還能再低。
把Scene窗口左上方的繪制模式改為Irradiance
從Project窗口選擇TutorialTerrainLow光照參數集
從Inspector界面里把IrradianceBudget的值慢慢降低
你會看到當我們減少這里的值時,兩座山上的照明會變得柔和一點
經過一些實驗之后,我們發現將Irradiance Budget設定為64最好
從Project窗口選擇TutorialTerrainLow光照參數集
從Inspector界面里把IrradianceBudget的值設為64
現在來看看另外一個Irradiance Quality,像之前所說的,Irradiance Quality影響著當計算光照像速時從叢集所投射出來的射線數量,不像Irradiance Budget只會影響到預計算時間,這個設定會影響到Runtime執行效能。
我們的兩座山是非常大的對象,代表不太容易錯過鄰近的叢集,因此我們可以透過降低IrradianceQuality來提升預計算的效能。
把Scene窗口左上方的繪制模式改為Irradiance
從Project窗口選擇TutorialTerrainLow光照參數集
從Inspector界面里把IrradianceQuality的值慢慢降低
隨著值的下降,產生的光照貼圖變得越來越模糊
我們發現2048是一個既可保持我們要的質量又能提升計算效能的平衡點,雖然準確對度會有點損失,但整體來看是利多于弊的。
從Project窗口選擇TutorialTerrainLow光照參數集
從Inspector界面里把IrradianceQuality的值設為2048
把設定好的光照參數集指定給場景其他對象
現在我們可以幫LightingTutorialStart場景里剩余的靜態對象建立并指定光照參數集。
我們之前討論如果決定一個分類方法。基于特征(例如大小或是距離鏡頭的距離)將場景對象分組,以方便我們能更容易為對象指定光照參數集。
當我們在處理Environment對象底下其余的子對象時,請盡量幫能共享光照參數集的對象分同一類,例如:對象是否會很接近?這樣如果提高該對象的分辨率對于結果會明顯的改善,如果是很遠的對象你就不需要相同的設定值,如果物體材料無法反映材質的大量變化,高分辨率就沒甚么好處。
分組不需要太細,對于大多數情況下,幾組差異性大的設定就夠了,分太細也不好管理,可能每個細節都要針對對象獨立修改。
在我們完成的場景LightingTutorialOptimal里面,我們分組依據如下:
RockLow:距離鏡頭有段距離的光滑石頭,因為距離遠所以分辨率低。
RockMedium:光滑石頭,更接進玩家區域,所以需要高一點分辨率和設定。
StructuresHigh:需要高分辨率呈現的重要的建筑物,同時也需要更高的IrradianceBudget和Quality設定。
StructuresLow:遠距離的建筑物,只需要低分辨率設定。
TerrainLow:大,遙遠的網格,比如山
TerrainPlayable:會很靠近鏡頭的大型地形,需要一個光照貼圖分辨率來平衡,大的地形把叢集數量降低也還是很合理
TerrainVeryLow:非常遙遠和假的仿真地形,低分辨率和低叢集數量,IrradianceBudget和Quality也都很低
除了這些自定義參數之外,在完成的教學LightingTutorialOptimal里面,我們還放了一些使用預設光照參數的結構,這里我們用默認的Default-Medium。
使用場景中大多數靜態對象默認的參數集可以減少很多手動的工作,將常用值指定為預設參數設定很有幫助,對于我們的目的,Default-Medium和默認1像素的分辨率搭配使用很適合。
Irradiance繪制模式用來評估場景照明非常有用,因為它只會顯示對PRGI有貢獻的靜態對象光照結果。
當要決定你的光照設定決策時,可以用LightingTutorialOptimal來當作一個評估基礎,將光照參數集指定給場景的對象不會花你太久的時間。記住,當你設定這些對象時,要不斷的思考調高參數值所帶來的好處有多少,如果調低帶來的負面影響不多,那不管如何都是首選。
總結
以上是生活随笔為你收集整理的Unity预计算全局实时GI(gi params)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: jquery 加法 乘法运算 精
- 下一篇: 民生车主信用卡年费收取标准是多少