使用Perlin噪音来制造闪电?

kar*_*erx 5 c++ perlin-noise

实际上我在主题标题中给出了与主题相关的几个问题.

我已经在我的应用程序中使用Perlin函数创建闪电,但我对我的实现并不完全满意.

以下问题基于初始和改进的Perlin噪声实现.

为了简化这个问题,让我们假设我通过使用1D Perlin函数调制由这些节点上的N个节点组成的水平线的高度来创建简单的2D闪电.

  1. 据我所知,传递给Perlin函数的两个后续值必须相差至少一个,否则得到的两个值将是相同的.这是因为使用简单的Perlin实现,Random函数使用int参数,并且在改进的实现中,值被映射到[0..255],然后用作包含值[0..255]的数组的索引]随机分布.是对的吗?

  2. 如何实现Perlin函数返回的第一个和最后一个偏移值(即节点0和N-1)始终为0(零)?现在我用我的Perlin函数调制一个正弦函数(0 .. Pi)来实现这个目标,但这并不是我想要的.将它们设置为零并不是我想要的,因为我想要一条不错的闪电路径,而不是锯齿状的.

  3. 如何改变Perlin功能(这样我可以使用两条不同的路径作为闪电的动画起点和终帧)?我当然可以为每个节点值添加固定的随机偏移量,或者使用不同的设置置换表来改善Perlin噪声,但是有更好的选择吗?

ssu*_*ube 2

  1. 这取决于您如何实现它并从中采样。使用多个八度音程有助于计算整数。

    每个倍频程和额外的插值/采样提供了柏林噪声中的大部分噪声。理论上,您不需要使用不同的整数位置;您应该能够在任何点进行采样,并且它将与附近的值相似(但并不总是相同)。

  2. 我建议使用柏林作为乘数而不是简单的加法,并在闪电过程中使用曲线。例如,将柏林设置在 [-1.5, 1.5] 范围内,并在闪电上设置正常曲线(两端为 0,中间为 1),lightning + (perlin * curve)将使端点保持静止。根据您实现柏林噪声发生器的方式,您可能需要类似的东西:

    lightning.x += ((perlin(lightning.y, octaves) * 2.0) - 0.5) * curve(lightning.y);

    如果perlin返回 [0,1] 或

    lightning.x += (perlin(lightning.y, octaves) / 128.0) * curve(lightning.y);

    如果它返回 [0, 255]。假设lightning.x以给定值(也许是 0)开始,这将给出一条仍符合原始起点和终点的有点锯齿状的线。

  3. 为闪电添加的每一个维度都为噪声添加一个维度。如果您要在一维(水平锯齿状)修改闪电,则需要一维柏林噪声。如果你想制作动画,你需要 2D。如果您想要在两个轴上呈锯齿状且具有动画效果的闪电,则需要 3D 噪声,等等。