昨天,我将经典的 Perlin 噪音(src: http://mrl.nyu.edu/~perlin/doc/oscar.html#noise )移植到 JavaScript 中。奇怪的是,产生的噪音看起来与我的预期有很大不同。经典的 Perlin 噪声使用线性插值/lerp,但噪声是平滑的而不是有边缘的。它看起来更像是余弦插值。 看来 Perlin 以不同的方式使用 lerp 函数。
以下是移植到 JavaScript 的原始代码(带有 Canvas 图片): http://jsfiddle.net/fDTbv/
这是有趣的部分:
t = vec[0] + N;
bx0 = Math.floor(t) & BM;
bx1 = (bx0+1) & BM;
rx0 = t - Math.floor(t);
rx1 = rx0 - 1.;
sx = s_curve(rx0);
u = rx0 * g1[ p[ bx0 ] ];
v = rx1 * g1[ p[ bx1 ] ];
return lerp(sx, u, v);
u 和 v 总是在变化。为什么? u 和 v 不应该代表 sx 之前的点和之后的点,因此不会改变吗?
我将代码更改为“我所期望的”,它的外观如下:http://jsfiddle.net/8Xv8G/
有趣的部分:
bx0 = Math.floor(x) & BM;
bx1 = (bx0+1) & BM;
u = g1[ p[ bx0 ] ];
v = g1[ p[ bx1 ] ];
return lerp(x - Math.floor(x), u, v);
我的问题: 为什么 Perlin 使用 lerp 函数的方式如此不同?
最佳答案
Here你可以从 Perlin 的原始演讲中找到一个 Java 小程序,它非常清楚地解释了整个 2D 噪声计算过程。 Perlin 的噪声函数是连续的,因为在每个点(一维),它是两个“平滑”线性梯度的线性插值。 “平滑”来自 s_curve 函数,它只是 Hermite 函数,实际上是余弦插值的近似。不过,我会将小程序和演示文稿的其余部分留给您,以获得更好的解释。
也许您还可以找到this project of mine有趣的是:这是一个 JavaScript 应用程序,可以在 html5 Canvas 上渲染 Perlin 和 Simplex 2D 噪声。查看源代码,了解这些函数和其他噪声函数的完整 JavaScript 实现。
希望有帮助,再见!
关于javascript - 线性插值在经典柏林噪声中如何工作?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10528988/