起
最近需要做球面随机地形,然后想起之前写的体积云相关https://blog.csdn.net/qq_41524721/article/details/101516784?spm=1001.2014.3001.5501顺便重温了iq大神的U管视频教程和神殿代码。
神殿的地面就是fbm4做的随机地形:
这就是我需要的。noise3D然后再fbm4。
由于体积云那篇的代码也是一样的noise3D,fbm4,而且我记得我当时上传了那张专门为3D噪声而有特殊偏移的noise2D贴图,所以准备直接照搬到项目里
承
noise3D有实时计算和基于贴图。
其中,实时计算是理论上更精确的Noise。在一般需求里,其实基于贴图的noise够用了,基本没有区别。
但我的项目是SDFTrace建模的无限细节游戏,具体效果还是有差别的:
远看:实时计算的noise3D
远看:基于贴图的noise3D
近看:实时计算的noise3D
近看:基于贴图的noise3D
当然,效果差异除了noise3D精度不一样,还跟我的SDFTrace算法有关。
但最主要的是,实时计算的noise3D太耗了,吃不消。
所以准备用基于贴图的noise3D。
当我准备拿之前体积云那篇的noise3D直接用时,发现当时上传的偏移图是糊的...
糊的图直接拿来用,产生的3D空间噪声是不连续的。网上找ShaderToy那张原图也找不到。
没办法,直接用Unity.c#写CPU代码生成了。这里重新上传一下:
g通道=r通道+(37,17)
转
但这样还是不对,我的代码几乎是照抄的,那问题就只能出在我自己写的SampleLevel里了:
float noise_texBase(in float3 x)
{
float3 p = floor(x);
float3 f = frac(x);
f = f * f*(3.0 - 2.0*f);
float2 uv = (p.xy + float2(37.0, 17.0)*p.z) + f.xy;
float2 rg = NoiseRGBTex.SampleLevel(noise_point_repeat_sampler, (uv + 0.5)/256, 0).yx;
return lerp(rg.x, rg.y, f.z);
}
我拿2D结果看了一下,发现noise生成出来是离散的,那估计不能用point去sample,还是得用bilinear。于是noise_point_repeat_sampler换noise_linear_repeat_sampler。这种SamplerState名是Unity特殊规定的,具体不表。
合
这下终于好了。
想想我也是nc,既然是用作noise,肯定是要随便缩放采样的,怎么可能用point。
基于贴图的效果,虽然没有实时计算的完美,但也算另一种风格,有点像机刻出来的粗糙感。
实时计算可能有优化的空间,但是应该属于可发paper级别了,先做其他功能...
————————————————————
后期补充
在SDF建模的应用场景下,应用基于贴图的noise3D,适当放宽估计normal用的eplision,可以在近处获得接近实时noise的效果。(不过此时更大的画质问题是trace精度。)