Fix randomness in particles with identical properties

Several issues:

 - The RNG wasn't copied with the value provider (which is always
   copied), resulting in unseeded RNGs.

 - Separate PCG streams with the same seed start with identical values.
   As particles often draw only a single value, we just always advance
   the RNG a bit to make the streams diverge.

 - The C++ specification requires a <= b for its distributions, but that
   wasn't guaranteed by the particle startValue/endValue.
liquid_container
Lukas Werling 2016-04-23 23:29:15 +02:00
parent cea685f7ea
commit 5471fe6cff
1 changed files with 4 additions and 1 deletions

View File

@ -218,6 +218,7 @@ C4ParticleValueProvider & C4ParticleValueProvider::operator= (const C4ParticleVa
valueFunction = other.valueFunction;
isConstant = other.isConstant;
keyFrameCount = other.keyFrameCount;
rng = other.rng;
if (keyFrameCount > 0)
{
@ -419,7 +420,9 @@ float C4ParticleValueProvider::Random(C4Particle *forParticle)
// particles lie on the heap we just use the address here.
const std::uintptr_t ourAddress = reinterpret_cast<std::uintptr_t>(forParticle);
rng.set_stream(ourAddress);
std::uniform_real_distribution<float> distribution(startValue, endValue);
// We need to advance the RNG a bit to make streams with the same seed diverge.
rng.advance(5);
std::uniform_real_distribution<float> distribution(std::min(startValue, endValue), std::max(startValue, endValue));
currentValue = distribution(rng);
}
return currentValue;