'《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的'

"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Particle Lights | 粒子光源

遊戲中幾乎每一個粒子都是自發光的。其中許多同時也照明瞭環境。許多粒子不是將粒子視作物體而渲染,而是可以在3D空間的所有方向上發光的簡單的點光源。

觀察建議:注意無論相機如何移動,發光的餘燼是如何在3D空間內獨立移動的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Particle Lights | 粒子光源

遊戲中幾乎每一個粒子都是自發光的。其中許多同時也照明瞭環境。許多粒子不是將粒子視作物體而渲染,而是可以在3D空間的所有方向上發光的簡單的點光源。

觀察建議:注意無論相機如何移動,發光的餘燼是如何在3D空間內獨立移動的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:雪粒子在《曠野之息》中是視為粒子光源渲染的。一種產生了雪粒子能夠反射太陽光的錯覺的方法。不過這也可能僅僅是不同的美術選擇就是了。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Particle Lights | 粒子光源

遊戲中幾乎每一個粒子都是自發光的。其中許多同時也照明瞭環境。許多粒子不是將粒子視作物體而渲染,而是可以在3D空間的所有方向上發光的簡單的點光源。

觀察建議:注意無論相機如何移動,發光的餘燼是如何在3D空間內獨立移動的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:雪粒子在《曠野之息》中是視為粒子光源渲染的。一種產生了雪粒子能夠反射太陽光的錯覺的方法。不過這也可能僅僅是不同的美術選擇就是了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意螢火蟲是如何照明它們周邊環境的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Particle Lights | 粒子光源

遊戲中幾乎每一個粒子都是自發光的。其中許多同時也照明瞭環境。許多粒子不是將粒子視作物體而渲染,而是可以在3D空間的所有方向上發光的簡單的點光源。

觀察建議:注意無論相機如何移動,發光的餘燼是如何在3D空間內獨立移動的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:雪粒子在《曠野之息》中是視為粒子光源渲染的。一種產生了雪粒子能夠反射太陽光的錯覺的方法。不過這也可能僅僅是不同的美術選擇就是了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意螢火蟲是如何照明它們周邊環境的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Puddle formation and evaporation | 水坑的形成與蒸發

可能是遊戲中最奇妙但也最聰明的渲染解決方案了。在遊戲世界的整個地形之下,存在一層水面材質的平面,當下雨時,水面材質將升高與降低以用水填充水池,並在太陽回來時蒸發掉這些水。根據水面與地面的相對距離,會用上一個水沫材質層。這一過程非常簡單,同時也是遊戲中又一個令人印象深刻的動態效果。

觀察建議:仔細觀察在下雨時水池是如何"填充"滿水的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Particle Lights | 粒子光源

遊戲中幾乎每一個粒子都是自發光的。其中許多同時也照明瞭環境。許多粒子不是將粒子視作物體而渲染,而是可以在3D空間的所有方向上發光的簡單的點光源。

觀察建議:注意無論相機如何移動,發光的餘燼是如何在3D空間內獨立移動的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:雪粒子在《曠野之息》中是視為粒子光源渲染的。一種產生了雪粒子能夠反射太陽光的錯覺的方法。不過這也可能僅僅是不同的美術選擇就是了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意螢火蟲是如何照明它們周邊環境的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Puddle formation and evaporation | 水坑的形成與蒸發

可能是遊戲中最奇妙但也最聰明的渲染解決方案了。在遊戲世界的整個地形之下,存在一層水面材質的平面,當下雨時,水面材質將升高與降低以用水填充水池,並在太陽回來時蒸發掉這些水。根據水面與地面的相對距離,會用上一個水沫材質層。這一過程非常簡單,同時也是遊戲中又一個令人印象深刻的動態效果。

觀察建議:仔細觀察在下雨時水池是如何"填充"滿水的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

水坑的生成



觀察建議:仔細觀察雨停且太陽出來時水面是如何"蒸發”的。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Particle Lights | 粒子光源

遊戲中幾乎每一個粒子都是自發光的。其中許多同時也照明瞭環境。許多粒子不是將粒子視作物體而渲染,而是可以在3D空間的所有方向上發光的簡單的點光源。

觀察建議:注意無論相機如何移動,發光的餘燼是如何在3D空間內獨立移動的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:雪粒子在《曠野之息》中是視為粒子光源渲染的。一種產生了雪粒子能夠反射太陽光的錯覺的方法。不過這也可能僅僅是不同的美術選擇就是了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意螢火蟲是如何照明它們周邊環境的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Puddle formation and evaporation | 水坑的形成與蒸發

可能是遊戲中最奇妙但也最聰明的渲染解決方案了。在遊戲世界的整個地形之下,存在一層水面材質的平面,當下雨時,水面材質將升高與降低以用水填充水池,並在太陽回來時蒸發掉這些水。根據水面與地面的相對距離,會用上一個水沫材質層。這一過程非常簡單,同時也是遊戲中又一個令人印象深刻的動態效果。

觀察建議:仔細觀察在下雨時水池是如何"填充"滿水的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

水坑的生成



觀察建議:仔細觀察雨停且太陽出來時水面是如何"蒸發”的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

水坑的蒸發



我其實還回去翻閱了一下這遊戲的文本轉儲,幾乎證實了我所提到的所有內容。看來我應該先去翻翻文本轉儲而不是在遊玩過程中調查引擎,這樣就輕鬆多了!

總之,這裡是Pastbin鏈接:https://pastebin.com/Jc9b0BCp

於是,本次分析就已經結束了。與往常一樣,如果你對帖子中所提供的信息有任何疑問的話,歡迎隨時告訴我。


"

文/未來遊戲研究所

本文原載於B站專欄未來遊戲研究所,已獲譯者授權。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的


我其實很久以前就想做一篇正式的《塞爾達傳說:曠野之息》引擎分析文章了,但一直沒時間去弄。然而,現在Switch有了新的視頻錄製功能後,我想這是一個完美的時機來重遊這款遊戲並通過我上傳到Twitter上的視頻來分享我的想法(本文中以動態圖與靜態圖代替)。

我將先從我的研究結果摘要開始,但我也會在文章的後面對每一個技術特性進行細分以便通俗易懂。同時我也會盡可能避免出現重複內容。比如說像是Digital Foundry這樣的已經分析了引擎的一部分特性,那我就不會再在這裡提及到了。這篇帖子的目的是為了讓更多的人接觸到其他人不打算費心去調查的,遊戲中的技術成就。

總之,這裡就是這款引擎特性的總結:

  • Global Illumination | 全局光照 (更具體來講,是光能傳遞)
  • Local Reflections | 局部反射 (由菲涅爾反射計算)
  • Physically-based Rendering | 基於物理的渲染
  • Emissive materials/area lights | 自發光材質/區域光源
  • Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽
  • Dynamic Wind Simulation system | 動態風力模擬系統
  • Real-time cloud formation | 實時雲體變形 (受風力影響)
  • Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射
  • Full Volumetric Lighting | 完整體積光照
  • Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值
  • Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體
  • Aperture Based Lens Flares | 基於光圈的鏡頭光暈
  • Sub-surface Scattering | 次表面散射
  • Dynamically Localized Lightning Illumination | 動態局部閃電照明
  • Per-Pixel Sky Irradiance | 逐像素天空輻照度
  • Fog inscatter | 霧光散射
  • Particle Lights | 粒子光源
  • Puddle formation and evaporation | 水坑的形成與蒸發


Global Illumination/Radiosity | 全局光照/光能傳遞

首先我想要聲明一點,所有所謂的實時全局光照方案都是以某種方式偽造出來的,都具有著不同程度的準確性。任何僅僅因為沒有使用路徑追蹤之類的而忽略了《塞爾達:曠野之息》中的全局光照方案的人們應該仔細想想自己究竟在說些什麼。最重要的一點是,這一切都是實時渲染的;這不僅僅是烘培入紋理中的光照,這對於一款開放世界遊戲來說(尤其是在Wii U上)非常令人欽佩。

那麼,光能傳遞到底是個什麼東西?嘛,在3D圖形渲染中,它是從不同表面反射的光,並在這個過程中講顏色信息從一個表面傳輸到另一個表面的全局光照近似法。光能傳遞越是準確,為了傳輸適當的顏色就需要計算更多的反射光。

在《曠野之息》中的引擎用的是光照探針在整個環境中收集在光照探針附近不同表面的顏色信息。並沒有什麼模擬反射光,只是一個給定區域中基本顏色的一些近似值。《曠野之息》用於計算此信息的算法尚不清楚,但我的最佳猜測是球諧函數或之類的東西,基於顏色平均值與光能傳遞局部化。與《超級馬里奧:奧德賽》不同,《曠野之息》中的光能傳遞並非二進制而是粒子。從光照探針計算的照明信息似乎與LOD系統在同一個渲染管線層次捆綁串流,使得其效率極高。

觀察建議:注意當相機靠近該區域時,岩石懸崖是如何從草地上接收到綠色色調的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

全局光照演示動態圖


(更新)起初我假設可能整個環境中都有放置球諧函數來收集色彩採樣,因為當林克在整個環境中移動時,它似乎會更新為基本顏色。然而,經過進一步調查後,我現在知道了那些基本顏色反射是由於環境中缺乏顏色變化。當我在一個彼此相鄰的許多不同顏色表面的區域測試全局光照時,其全局光照系統是如何運作的就變得豁然開朗了。注意林克在接觸紅牆時,其顏色是如何傳遞到面向相反方向上所有表面上的。在紅牆相反方向的綠牆也是如此(儘管效果並不是很強烈,因為探針更靠近紅牆,因此紅牆的顏色本身反射更強烈)。事實上,在任何給定的點上,這在各個方向上都會發生。地面向上傳遞顏色,而林克頭部正上方的任何天花板或是彩色表面都會傳遞其顏色。探針不斷地動態的採樣並傳遞顏色(我們可以認為這就是反射光了),因為探針會因為新的傳遞而拾取更多的顏色,並且還必須對他們進行採樣。最後,最終結果將會停止改變,因為最靠近探針的樣本將具有最主要的顏色,無論顏色轉移量如何。這一過程井然有序,但非常局部化且速度相當的快。探針具有有限的採樣範圍,並將這些結果應用於世界空間中的材質上。由於如此般的效率,探針能夠近似出許多反射光的效果,但只有在距離探針最近的區域中看起來準確。

(更新)這是一個非常重要的發現。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近紅牆時其他材質也"染"成紅色


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

靠近綠牆時其他材質也"染"成綠色



全局光照實際上會近似多次反射。在林克的頭部上有一個光照探針可以對環境中的大多數材質的色彩進行採樣。然後,每一個採樣的顏色被傳遞並以相反的方向反射。有趣的是,強度有被考慮為因素,其受到探針最接近的表面以及反射光的強度影響。

在戶外可能看起來效果不太明顯,但是當有多個相鄰的表面時,全局光照的效果看起來很不錯。

Local Reflections | 局部反射

(更新) 那麼,自從我開始分析這款遊戲以來,總是讓我頭疼的一個區域似乎就是局部反射了。有著如此多看似不一致的情況,因為我的理論最初滿天飛。現在我可以自信的說,我已經解開了局部反射是如何運作背後的謎團了。顯然,這是一種根據具體情況而三管齊下的方案。

  • Specular Lighting | 鏡面光照


陽光,天光,閃電,點光源都屬於此類別。起初我以為神廟,塔也是如此(因為它們是自發光的,因此我就假設它們是區域光源),但看到神廟與塔所展現出的非常能夠揭露真相的加工痕跡(artifact)時,就可以排除這一點了。不是所有發光的材質都能夠照明環境,而神廟與塔可以歸屬於那些不能的發光材質。

  • Aperture mapped reflections | 光圈映射反射


如果這個術語對你來說感到很新穎,那可能因為它就是如此。基於這款遊戲的文本轉儲,《曠野之息》開發人員標記了他們對虛幻引擎4的場景捕獲2D反射的看法。環境是這樣反射出來的。林克頭部(明確來講,是光圈)上方的虛擬相機有著相對較小的視野,因此當林克移動時就會使得反射(實時顯示)在它們適當的空間內移動,直到光圈再次捕獲環境。你可以在以下的視頻中看到這類的加工痕跡與視野。

  • Screen Space Reflections | 屏幕空間反射


只有那種看起來像層壓材質的才會使用這種模型,而這些僅限於神廟之中。在光澤貼圖中的一個數值告訴引擎僅對這些材質使用屏幕空間反射。它們會反射屏幕上的任何內容,能夠在任何材質的入射餘角看到。然而,這些材質上同樣也有使用光圈映射來進行環境反射,這也是讓我感到迷惑的源頭之一。這些材質反射的不協調錶現使得我對神廟外的其他材質也做出了假想。值得慶幸的是,我們把這一點理清了。

觀察建議:看看林克的反射與藍燈的反射的對比。林克必須得在屏幕上才能顯示出其反射,而藍燈不需要在屏幕上也能顯示出反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間反射+鏡面高光


(更新)局部反射之謎解開了!


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

正面的牆不能反射,而側面的牆則可以



那麼,神廟材質具有一層額外的光澤反射層,但他們在外部反射上也使用了同樣的反射模型。怪不得這麼讓人迷惑!

使用光澤材質,可以在屏幕空間(屏幕空間反射)內捕獲所有內容的反射。而使用非光澤材質(幾乎所有的外部材質),使用與虛幻引擎4中所用到的場景捕獲2D反射技術幾乎完全相同的技術來捕獲環境反射。基本上,虛擬相機(具有自己的視體與視野)位於林克的頭部正上方,始終面對主相機的地平線,無論林克的定向如何(這使得有限的屏幕外反射得以實現)。然後將捕獲的圖像饋送到產生反射的材質中,就好像向電視發出現場直播信號。這意味著圖像的饋送是以遊戲所運行的任何幀率(30幀)實時投射的。這樣使得材質的不同元素得以無需等待新的捕獲就能更新。但是,實際捕獲畫面本身會以低得多的幀率(4到5幀)而更新。只要場景捕獲相機從其絕對位置移動,你就能看到這一點。在更新捕獲反射之前,當前捕獲畫面於材質內(例如,水)在相機移動的任何方向實時移動(30幀)。然而,一旦材質接收到更新的捕獲,就會更正反射。這種更正的延遲是我們得以真實地瞭解捕獲更新即沿著材質的痕跡(4到5幀)。

你能夠在下方鏈接瞭解到更多關於捕獲技術的知識:

https://docs.unrealengine.com/latest/INT/Resources/ContentExamples/Reflections/1_7/


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

橋柱的反射稍微有些延遲



你可以在這裡看到,過時的反射仍然可以平滑地跟蹤林克的行動。沒有任何卡頓。然後當新的捕獲更新時,反射就得以更正了。這與反射貼圖的運作原理不同,反射貼圖僅在貼圖本身更新時才會更新反射。在這,捕獲的反射顯然已經過時了,但它仍然以30幀的速度改變自身的位置。

你可以在以下動圖中體會到捕獲相機的FOV:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



現在為什麼所有非自發光材質都只有菲涅爾反射就講得通了。使用這樣的反射技術,這些是它唯一可以正常運作的角度了!

我碰巧找到了這個拱門,並意識到了這是測量捕獲相機視野的完美設置:


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



結合上一些基本的三角學來看


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



我估算其水平視野為大約115°。在林克還沒有穿過拱門前,拱門的反射就已經離屏了,因此我們得知它肯定不是180°的視野了,因為如果是的話,拱門的反射就不會像這樣出現視覺錯誤了。

你還能夠看到,當相機距離拱門數英尺並且垂直於拱門時,反射是傾斜的並且與視野成比例,這使得我們可以觀察到它的寬度。它會測量場景捕獲相機的相對水平視野。

不過我想重申一下,這僅僅是粗略的估算,所以我可能會偏上個10°左右,但在有的角度下使用這個視野是不可能的,因此通過排除法,我們至少能有一個估算值。

Physically-based Rendering | 基於物理的渲染

在有人問起來前,不,這並不意味著"物理上看起來正確的材質"。這只不過是應用於3D圖形渲染管道的一種方法,所有的材質(紋理表面)在與光交互時獨特的改變它們的行為方式。現實世界中就是這樣的,這也就是為什麼它被稱作基於物理的渲染(基於現實世界光物理的概念)。不同的材質導致光的行為不同,也就是為什麼我們能夠在視覺上區分不同的表面。

傳統上,渲染管道依賴於美術師對光與不同的真實世界材質的交互方式的理解,並基於那份理解定義紋理貼圖的效果。作為結果,不同的紋理表面之間存在著很多不一致性,以及它們與現實世界中的對應物相比之下(這一點是可以理解的,因為我們不能指望美術師對現實世界中的所有物質都有著百科全書般的知識)。對於PBR,光物理的基本原理是管道本身的一部分,並且所有的紋理表面都被歸類為具有獨特性質的材質,這些性質將導致光根據這些獨特性質運轉。這樣使得不同表面得以放置於不同的光照條件以及動態相機角度之下,並動態的調整光與這些表面的交互方式。美術師不必像傳統工作流程那樣預定義這種交互方式。一切都是自動的。由於PBR的效率,開發人員更想要製作其中所有材質都有著影響光的獨特性質的遊戲。

在《曠野之息》中,其PBR有一點藝術天賦,因此你可能甚至不會注意到其引擎有依賴於這樣的管道,因為紋理並不一定需要看起來很逼真。然而,材質上所用到的BDRFs(雙向反射分佈函數)使得引擎有用PBR這一點比較明確。對於每一個動態光源,它的鏡面高光(光源本身顯示為反射表面的部分)和這些高光的反射率/折射率是根據入射角(入射光相對於表面法線的角度)和光與之相互作用的任何材質的折射率(當光線接觸其表面時,材質"彎曲"了多少的光)動態生成的。如果遊戲使用的是傳統管道,分配在木頭與金屬上的鏡面高光之間就不會有太大的差異。但在這個遊戲中,鏡面高光的產生完全取決於光與之相互作用的材質。

另一個表明《曠野之息》使用PBR的關鍵因素是所有材質上的Fresnel(s不發音) | 菲涅爾反射。首先,大部分使用傳統管道的遊戲甚至都不會用上菲涅爾反射,因為這樣還不如直接用PBR了。正如我之前在討論局部反射時所解釋的那樣,菲涅爾反射在入射餘角處變得可見(入射光幾乎與觀察者/相機的視角相互作用的表面平行的角度)。根據菲涅爾反射係數,所有材質在入射餘角下都達到了100%的反射率,但反射率的有效性將取決於材質的粗糙度。因此,程序員可以區分"反射率"與"折射率"。一些材質反射所有方向的光(漫反射材質)。即使在100%的反射率下,100%的光也可能從整個表面區域反射出來,但並非所有光都在同一方向上反射,因此光線均勻分佈,而你看不到任何鏡面反射(表面周圍的鏡像)。其他材質只會反射入射光相反方向的入射光(鏡面材質),因此你只能在適當的角度看到反射,接近90%的光都被反射了。漫反射和鏡面反射材質的反射率即便是在入射餘角下,其反射率(材質反射入射光能力的有效性)也不總是100%,這就是為什麼在入射餘角下所有材質都看不到完美的鏡面反射,哪怕是在現實世界中也是如此。菲涅爾反射的清晰度將隨著產生反射的材質而變化。

觀察建議:注意桶子木頭上的綠色光源是如何在所有角度看起來都是相同的,而這一相同的綠色光源似乎還改變了金屬桶箍(桶上的金屬圓圈)的反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於物理的渲染效果演示



Emissive materials and area lights | 自發光材質與區域光源

這一個比較簡單。發光物件的材質提供獨特的光源,以與材質本身相同的形狀照明環境。這些並不是在所有方向上傳播的點光源,甚至有時會是在一個方向上照明的簡單定向光源。有一點很重要值得一提,只有全局(太陽/月亮/閃電)光源才能投射陰影。然而,雙向反射分佈函數仍然應用於遊戲中所有的光源。

觀察建議:注意火劍所投射的光的形狀。這一形狀與劍本身的形狀相匹配,但光的強度將取決於劍與它所照明的表面之間的距離。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

自發光材質與區域光源效果圖



Screen Space Ambient Occlusion | 屏幕空間環境光遮蔽

在現實世界中,當光在環境中反射後會有一定量的"環境光"為環境著色,使其變得完全漫射。如果說陰影是遮擋直射陽光物體的產物的話,那麼環境光遮蔽可以被認為是環境中縫隙阻擋環境光的產物。

《曠野之息》中所使用的方案稱為SSAO(屏幕空間環境光遮蔽),因為它計算了屏幕空間中的環境光遮蔽並且取決於視點依賴。環境只會在相對於相機垂直時它才會接收環境光遮蔽。

觀察建議:當從正面看時,在牆壁中的縫隙中尋找黑暗,陰影的噪聲模式效果。同樣的噪聲模式也從這個角度勾勒出了林克的輪廓。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

屏幕空間環境光遮蔽效果演示圖



Dynamic Wind Simulation system | 動態風力模擬系統

這一個讓我感到很驚訝,因為我完全沒想到它會如此的強勁。基本上來說,物理系統與風力模擬系統是相關聯的。它是完全動態的,並根據各自的重量值影響不同的物體。受影響效果最突出的對象是草地與程序生成的雲。

觀察建議:如果你仔細觀察的話,可以在這裡看到草和雲的方向性流動是如何與風的變化方向相匹配的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

動態風力模擬系統效果演示圖



Real-time cloud formation | 實時雲體變形

這個遊戲沒有使用任何意義上的傳統天空盒。雲體是基於引擎設置的參數程序性生成的。它們會投射出實時的陰影。它們根據太陽在天空中的位置接收到了光照信息。據我所知,雲被視為遊戲中的實際材質。它們並不是體積雲,所以你不會看到任何雲隙光之類的東西,但同時它們也不是"天空盒"的雲。它們的形成也受到風力系統的影響。

觀察建議:注意天空中的雲體粒子是如何隨機地聚集在一起的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

實時雲體變形效果演示圖



Rayleigh scattering/Mie Scattering | 瑞利散射/米氏散射

在現實世界中,當光線到達地球的大氣層時,會被空氣分子散射,從而形成了地球的藍天,因為較短波長的藍光比其他顏色的光更容易散射。然而,當太陽接近地平線時,它就必須得穿過更多的大氣層,從而導致大部分藍光在太陽光到達觀察者眼鏡時散射,留下波長更長的橙色和紅色光到達肉眼。《曠野之息》數學上地近似了這個算法(我其實是在今年早些時候通過文本轉儲代碼中發現的!)顯然這一算法也解釋了米氏散射的由來,它使得霧得以在天空中出現。

老實說,要不是我查看了該文本轉儲中的代碼,我是絕對不可能想到遊戲中有模擬這一現象的。想要偽造出這種效果很容易。然而,在觀察了水中天空的倒影之後,這一切都說得通了。這種散射光實時地反射入整個環境中。若是單純的天空盒會使得這一點不可能實現。

觀察建議:注意天空中橙色與紅色的不同色調是如何以相同的顏色反映在環境上的。儘管未在動圖中展示這一點,但是天空中的散射光也以其他的顏色照明瞭環境以及水面,這取決於光是如何散射的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意隨著太陽落山,雪的顏色也隨之發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:在此動圖開頭,水面至少有5個不同的反射。神廟(藍色),山丘(綠色),旗幟(黑色輪廓),天空(橙色)和太陽(粉色)。山丘,旗幟,和神廟的反射都通過場景捕獲反射而實現,太陽則通過鏡面光照(作為鏡面高光)而實現,天空也通過鏡面光照而實現反射,但並不是鏡面高光。隨著暴雨的來臨,反射的變化是完全動態的。來自烏雲的天空遮蔽會實時改變天空中瑞利散射的光照。最終,橙色天光不能夠再達到水的表面而逐漸消失,但太陽仍然存在,因為它沒有被完全遮擋住。然而,由於天空中如此多的米氏散射,太陽的顏色從粉色變成了白色!即便如此,最終雲體變得對太陽來說太多了,完全遮擋了它,僅留下了來自神廟的光與山丘的部分反射。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其一




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

由瑞利/米氏,鏡面光照以及屏幕空間反射所呈現的光照系統其二



Full Volumetric Lighting | 完整體積光照

除了天空中的雲,環境中的每個部分及其中的每個物體都有可能在適當的光照條件下實時創建光束。這個遊戲使用的是屏幕空間環境光遮蔽來輔助這一效果,但體積光照並非視點依賴。你可以在本文中的陰影體部分找到更多有關體積光照運作原理的信息。

觀察建議:注意光束是如何在大型建築結構投射的陰影中產生的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

完整體積光照效果演示圖



Bokeh DOF and approx. of Circle of Confusion | Bokeh景深與模糊圈的近似值

我認為引擎所用到的另一個令人驚訝的功能是延遲光照/著色。那麼我要稍微簡化一點,因為這可以真正地在技術上解釋首先為什麼現實世界中會出現散景效果。可以說當光進入肉眼/相機的光圈(開口)時,入射光線開始會聚到焦平面的單個點上。隨著光越來越集中在這個平面上,它的外觀變得越來越銳利,越來越小。隨著光遠離該平面並變得更加散焦,它的外觀變得越來越大,越來越模糊。

家喻戶曉的散景效應是當進入相機鏡頭的光點呈現出在它們通過光圈時的形狀(例如,六邊形)。模糊圈是當人類無法區分完全聚焦的光點與略微失焦的光點時的聚焦區域。景深通常由模糊圈來決定。有趣的是,當使用希卡望遠鏡與相機符文時,《曠野之息》會模擬出這兩種概念。我的猜測是它是基於紋素(紋理要素)數據在屏幕空間中計算的,然後作為後期特效應用。

觀察建議:注意相機的十字線與金屬盒上閃耀的藍色燈光。當相機對焦於遠離光源的遠景時,光源就會變得模糊,同時變得更大。當相機直接對焦於光源時,則會出現相反的情況。藍色光源所形成的圓形形狀稱為散景效果。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

Bokeh景深效果演示圖



Sky Occlusion and Dynamic Shadow Volumes | 天空遮蔽與動態陰影體

除了遊戲中的物理系統以外,這些著色特性毫無疑問是《曠野之息》中計算方面上來講性能損耗最高的要素。

即便雲本身沒有任何體積,但它們仍能將(軟)陰影投射到環境當中。然而,太陽與來自天空的散射光動態地照明整個環境,而環境與其中所有的物體根據該照明投射出自己的陰影。如果環境中的照明即便是在天空完全被陰雲覆蓋的情況下仍然保持不變的話就會顯得很不真實。由於遮蔽區域的直接光照比較少,環境光(漫反射,非定向光)將會在這些區域的照明中發揮更大的作用,並且這些區域中的所有陰影都將變得更為柔和並開始匹配它們周邊環境的顏色。

該引擎還是用了陰影體而非簡單的陰影貼圖,並且遊戲中的每一個陰影投射器都是這樣實現的。陰影體在指定的3D空間內投射,而不僅僅是環境中的表面與物體。除了在執行陰影體時看起來更為真實的天空遮蔽,同時當它與能夠接收陰影的大氣層霧相結合時,在3D空間內動態生成陰影體還可以提供完整實時體積光照所帶來的優勢,而在《曠野之息》中正是如此。

觀察小技巧:觀察旗幟的硬陰影是如何變得更加柔和,並隨著突如其來的暴風雨開始從環境光中接收更多的顏色。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其一



觀察建議:注意旗幟的運動是如何與產生的光束相關聯的。光束之間的暗區是因旗幟的陰影體而存在的。旗幟的動態扭曲告訴了我們這些陰影體是實時生成的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

天空遮蔽與動態陰影體其二



Aperture Based Lens Flares | 基於光圈的鏡頭光暈

99%玩這個遊戲的人都忽視了這一特性,所以老實說我都不確定到底值不值得實施這玩意。

基本上,當來自明亮光源的光線以某種傾斜的角度進入相機鏡頭時,由於在相機要素內部反射的光線,它們會產生稱為鏡頭光暈的光學加工痕跡。大多數遊戲只是將光暈作為後期效果來模擬這種效果,當相機略偏於相機視體時就會出現這種效果。光在相機本身內部反射這一概念甚至沒有被作為因素而考慮。

在《曠野之息》中,由於引擎已經模擬了景深的相機光圈,它可以追蹤光圈與太陽的相對位置,並計算出應該生成多少鏡頭光暈,即便太陽並不在屏幕上。但這還並不是一切!具有變焦功能的相機更容易出現鏡頭光暈,並且光暈會根據光圈的形狀/大小和變焦級別而改變形狀與大小。令人驚訝的是,《曠野之息》也近似出了這些效果!

觀察建議:你可以看到,即便太陽在屏幕外,鏡頭光暈(圓形光線加工痕跡)仍然存在。更重要的是,鏡頭光暈的形狀,大小與清晰度隨著相機變焦級別而變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

基於光圈的鏡頭光暈效果演示圖



Sub-surface Scattering | 次表面散射

在現實世界中,有些表面是半透明的(不要與透明混淆),這意味著光能穿過其表面並散射於其內部。現實世界中半透明表面的部分例子為人體皮膚,葡萄,蠟,以及牛奶。在3D圖形中對光的這種獨特行為建模稱作次表面散射或SSS。與大多數實時3D渲染方案相同,程序員已經提出了數種近似這種效果的方法,而無需在分子水平上模擬光的反彈。《曠野之息》中所用的方法相對簡單但很有效。

任何應具有一定程度半透明度的表面都將會有多層材質以生成次表面散射。第一層是內部材質。這種材質通常用照明信息來烘培,使其具有半透明的樣子。光穿過材質但實際上並沒有實時照明材質本身。在這種材質之上的材質就是表面材質。這種材質在兩者中持主導地位,在大多數光照條件下你所看到的都是這種材質。

這些材質之間的關係以這樣的方式運作,即任一材質的主要外觀總是由入射光與透射光之間的比率決定。如果表面材質反射的光比內部材質透射的光更多,那麼表面材質的不透明度將與其接收的光成正比例增長。如果內部材質透射的光比表面材質反射的光多,那麼表面材質的不透明度將與其未接收的光成正比例降低。根據入射率/透射率來平衡表面材質的不透明度是非常巧妙且效率高的一種方法,可以使材質具有次表面散射效果。

觀察建議:注意能夠在外部表面看到馬廄內部的光的漫反射照明。林克在屋頂上的陰影同時也被了來自內部的光照照明,但當在地面時不會這樣。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其一



更新:對次表面散射的進一步調查。當更多的太陽光照明這些植被時,其下側的亮度/顏色會發生變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(1)




《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其二(2)



觀察建議:注意表面材質是如何因為接收了更多的光線而變得更不透明,使其內部材質變得模糊。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(1)



觀察建議:注意表面材質是如何因為接收了較少的光線而變得更加清晰,使其內部材質變得清楚。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

次表面散射其三(2)



Dynamically Localized Lightning Illumination | 動態局部閃電照明

許多遊戲通過將閃電作為全局光源而實現環境照明,在整個環境中閃爍,所有陰影投射器都以預定的大小和方向投射陰影。

在《曠野之息》中,雷擊基本上就是超大的一坨相機閃光燈,每一個都有著自己的半徑與強度,並且能夠在地圖上的任何一處劈下,無論玩家位於何處。《曠野之息》其閃電的有趣之處在於陰影動態地對應於陰影投射器最近的雷擊的強度與位置。這一系統可能是我在所有遊戲中見過的最酷的閃電系統。

觀察建議:注意每一次雷擊時其陰影大小,方向與對比度的變化。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Per-Pixel Sky Irradiance | 逐像素天空輻照度

如果說輻射率是來自太陽的輻射量的話,那麼輻照度就可以說是給定表面實際接收的輻射量。對於散射天光來說,這是一個相當重要的變量,因為我們之所以能夠在夜晚看向太空的主要原因就是因為沒有它!《曠野之息》使用一種跟蹤太陽相對於天頂位置的算法來計算輻照度,並且在日落期間,它開始逐像素地移除天光,直至沒有剩下的輻照度為止。當天空中沒有了雲層與米氏散射後,星星將開始出現在天空中,即便天還沒有完全黑下來。夜晚與白天之間的顏色漸變過渡實在是令人印象深刻。

觀察建議:本身你是可以在太陽落山時星星出現的,但由於Twitter+動態二重壓縮,這一點也就看不到了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Fog inscatter | 霧光散射

在現實世界中,霧像物理對象那樣接收光與影。如果霧是體積的話,那麼計算機圖形的計算效率就會很低。《曠野之息》通過創建一份霧噪聲模式(類似於它們的環境光遮蔽噪聲模式,但不限於屏幕空間)並應用來自太陽和天光的輻射值來生成光散射來解決這個問題。當你將其與陰影體結合使用時,不僅可以獲得體積光照,即便在沒有體積的情況下它看起來也會像是有體積的霧。

觀察建議:注意山上的霧是如何呈現出環境中可用光的顏色的,同時看起來還很有體積感。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Particle Lights | 粒子光源

遊戲中幾乎每一個粒子都是自發光的。其中許多同時也照明瞭環境。許多粒子不是將粒子視作物體而渲染,而是可以在3D空間的所有方向上發光的簡單的點光源。

觀察建議:注意無論相機如何移動,發光的餘燼是如何在3D空間內獨立移動的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:雪粒子在《曠野之息》中是視為粒子光源渲染的。一種產生了雪粒子能夠反射太陽光的錯覺的方法。不過這也可能僅僅是不同的美術選擇就是了。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



觀察建議:注意螢火蟲是如何照明它們周邊環境的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



Puddle formation and evaporation | 水坑的形成與蒸發

可能是遊戲中最奇妙但也最聰明的渲染解決方案了。在遊戲世界的整個地形之下,存在一層水面材質的平面,當下雨時,水面材質將升高與降低以用水填充水池,並在太陽回來時蒸發掉這些水。根據水面與地面的相對距離,會用上一個水沫材質層。這一過程非常簡單,同時也是遊戲中又一個令人印象深刻的動態效果。

觀察建議:仔細觀察在下雨時水池是如何"填充"滿水的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

水坑的生成



觀察建議:仔細觀察雨停且太陽出來時水面是如何"蒸發”的。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的

水坑的蒸發



我其實還回去翻閱了一下這遊戲的文本轉儲,幾乎證實了我所提到的所有內容。看來我應該先去翻翻文本轉儲而不是在遊玩過程中調查引擎,這樣就輕鬆多了!

總之,這裡是Pastbin鏈接:https://pastebin.com/Jc9b0BCp

於是,本次分析就已經結束了。與往常一樣,如果你對帖子中所提供的信息有任何疑問的話,歡迎隨時告訴我。


《塞爾達傳說:曠野之息》技術分析:神作是怎麼煉成的



原作者:Redneckerz

地址:https://www.bilibili.com/read/cv3239418【編譯自resetera】

"

相關推薦

推薦中...