天空盒研究记录

本文初衷是针对Unity内Skybox/Procedural着色器的研究。因为研究过程涉及的知识面稍多,所以特地开设文档记录。

对于天空颜色原理,网上很容易查到大量文章介绍,但是对于一些细节如天空颜色的变化分布,却很少有人研究总结,本文结合大量实际观察和文献查阅,简单阐述了一些现象原理,希望能对大家有所帮助。

Procedural Shader在场景烘培中起着重要作用

首先天空为什么是蓝色的,答案非常明确就是瑞利散射,蓝色光波长较短受大气分子影响产生散射,所以直接照射在地表的光线为接近白色,也就是我们看到太阳的颜色。而太阳以外的大气范围显示为蓝色。

有人可能会想,紫色波长更短,为什么天空不是紫色的?几个复合原因导致:一个是紫光功率谱本来就低;二是人眼对紫色不敏感;三是臭氧层强烈吸收紫外线,在外太空观察地球是可以看到暗紫色的,观察比较仔细的同学也可以在航空照片里宇航员白色衣服和航天器的暗部反光部分看到紫色倾向。

天和舱外定向摄像机拍摄神舟12号对接画面

跟Procedural Shader默认设置的情况一样,在地面上观察,当天空非常晴朗的情况下,穹顶越靠近头顶上方的天空越暗,越往远方的区域越亮,在接近地面的地方逐渐过渡为白色。

这种现象产生的原因主要有两个,一个是大气层顶部的空气密度低,瑞利散射作用较弱,空气散射的蓝光较少。另一个原因是远处视角看到的大气更厚,产生的散射光线叠加的也更多。

就像在水底,看头顶上的水面最亮一样的道理。因为从视角位置观察,正上方的水面最近,只不过太空是黑的,所以我们看到的天空就更暗。

甚至,如果当大气层变得更厚,我们看到的结果就会被反过来,过多的蓝色被散射掉,到达物体表面的直接光颜色变成了剩余的红色部分,也就是朝霞和晚霞的颜色。

(这也是为什么红色在大气中传播更远,信号灯普遍采用红色的原因。当然并不是说红色灯光会传播更远,白色灯光明显比红色光源拥有保留更多光谱的可能性,但是如果必须使用某种颜色标识的情况下,红色光源是比其它颜色更有优势的~)

 

从图上可以看出,早上和晚上的阳光因为照射角度的原因,光线需要穿过更厚的大气层抵达观测点

但是无论是清晨还是傍晚的时分,除了红色的云彩,我们仍然能看到蓝色的天空。这是怎么回事呢?

要想完全理解这个问题,我们就不得不再谈一下另一种散射现象:米氏散射。

米氏散射的基本原理其实跟瑞利散射是一样的,只不过造成米氏散射的粒子更大,如水气,尘埃等,它们的半径远大于可见光的波长,所以他们不只会散射蓝光,而是无差别的反射所有可见波段的光线,也就是白色光。

米氏不同于瑞利散射呈对称状分布,而是散射在光线向前的方向比向后的方向更强,方向性比较明显。

米氏散射在我们的日常生活中非常常见,比如天空的云彩、白色的浪花,都是米氏散射的作用。另外在我们谈到的天空颜色渐变上,接近地平线的天空会变得非常接近白色,很大原因也是由于近地处水气和尘埃的增多而造成的米氏散射。

所以如果天空被乌云遮盖,或者满是雾霾的天气,我们看到的昏暗的白色,也是米氏散射的原因。

那么再回过头看一下朝霞和晚霞对于天空的影响,可以很明显的看出红色的光线只是影响了米氏散射的区域,也就是直接光可以照射造成米氏散射的区域。而其它的天空区域,依然是被蓝色的瑞利散射占据。

如果天上没有云彩,那么红色的光线就只会影响到近地平线的那条原本的白色天空区域,当然还有地面上可以被阳光照射的物体。

以上是天空颜色的原理,再补充一点海洋颜色的知识。

海水呈蓝色的大致原因也是瑞利散射。但是如果只是按照瑞利散射去解释的话,按照晚霞的色彩原理,在深水下观察光源,光线的蓝色部分被散射掉,那么光源的颜色应该呈现红色。但事实并非如此,我们在水下观察光源的时候,光源甚至仍然呈蓝色。

这是因为水分子跟大气分子是不一样的,水会大量的吸收光谱中的红色部分。也就是说,在水中,波长更长的红光穿透力更差。

这时候大家又会问,刚才不是说红光穿透力更强吗?这要弄清楚“穿越”和“穿透”两个词的区别了,红光在可见光里属于长波,长波更容易“穿越”障碍物,其原理更类似一种衍射,比如无线电波,可以轻易的穿越大楼建筑等等。而短波频率更密集,能量更高,“穿透”力更强,更容易进入介质的内部,比如X光、紫外线等等。

光在水中的传播就取决于光波的“穿透”力,红光最容易被吸收,深入到水下两三米就被消耗殆尽,所以我们看到的大部分光线就只有蓝光,能够在水中被散射的光线也只有蓝光了。所以越深的水,越是偏蓝色,再深一些,连蓝色也被散射吸收光了,就逐渐变成黑色。