Efficient curl noise for particles

Started by
3 comments, last by CarlML 5 years, 5 months ago

Hi, so I have implemented curl noise for my particles based on the code here:
https://github.com/cabbibo/glsl-curl-noise/blob/master/curl.glsl

For the noise calculation I used the simplex noise code from here:
https://github.com/ashima/webgl-noise/blob/master/src/noise3D.glsl

Works great and produces a nice fluid, swirly effect. But, as you can see in the curl code it calls the "snoise" function a total of 18 times for each curl calculation. I don't think that is necessary because other examples I have seen only calls noise 3 times, once for each axis, while calculating the derivates used to calculate curl at the same, in the noise function. Like here:
https://github.com/rajabala/CurlNoise/blob/master/CurlNoise/Curl.cpp
It uses this noise: https://github.com/rajabala/CurlNoise/blob/master/CurlNoise/Noise.cpp

That code uses regular perlin noise though, not simplex noise like I'd like to use (and it is c++ code, I'm using hlsl). My question is, how can I calculate the derivates for the curl as in the last example (PerlinNoise3::EvaluateNoise), but using the simplex noise code from above? From what I read you should get the derivatives almost for free when calculating simplex noise. I'm not so concerned about understanding the exact math behind it, some example code would be great.

Advertisement

A little googling turned up this implementation of 3D simplex noise (other dimensions plus several other noise types also included in that github) complete with analytical derivatives in GLSL.

2 hours ago, JTippetts said:

A little googling turned up this implementation of 3D simplex noise (other dimensions plus several other noise types also included in that github) complete with analytical derivatives in GLSL.

Thanks for that! I have it implemented and working now, swirling away :). I believe it is a lot more efficient than what I had. For reference, here is the code for calculating the curl direction:


float noiseScale = 0.05f;
float3 posX = particle.pos.xyz * noiseScale;
float3 posY = posX + float3(31.341f, -43.23f, 12.34f); //random offset
float3 posZ = posX + float3(-231.341f, 124.23f, -54.34f); //random offset
float3 derivX = SimplexPerlin3D_Deriv(posX);
float3 derivY = SimplexPerlin3D_Deriv(posY);
float3 derivZ = SimplexPerlin3D_Deriv(posZ);
float3 curlDir = float3(derivZ.y - derivY.z, derivX.z - derivZ.x, derivY.x - derivX.y);

I changed the SimplexPerlin3D_Deriv function to only return the derivatives.

I found another version of a cheap kind of noise with derivatives calculated here:

This noise is a bit simpler so the swirlyness in particles won't be as complex and rounded, but it still looks cool so if performance is an issue I think using this would be ok.

I havn't looked into the viability of using noise textures for lookup but that could be an option.

 

I anybody wants to have a go at extending the original noise function with derivatives that would be welcome too since I think it is a bit more lightweight than the one referred to by JTippetts. This is the one:
https://github.com/ashima/webgl-noise/blob/master/src/noise3D.glsl

This topic is closed to new replies.

Advertisement