2010-04-19 178 views
4

我有一个从源头生成粒子并更新其位置的系统。目前,我已经在OpenGL中编写了一个程序,它调用我的GenerateParticles(...)UpdateParticles(...)并显示我的输出。我希望我的系统具有的一项功能是能够每秒生成n个粒子。在我的GenerateParticles(...)UpdateParticles(...)函数中,我接受2个重要参数:current_timedelta_time。在UpdateParticles(...)中,我根据以下公式更新我的粒子的位置:new_pos = curr_pos + delta_time*particle_vector。我怎样才能使用这些参数和全局变量(或其他机制)来产生每秒1236个粒子?粒子系统:粒子生成

回答

2

你需要小心,创建粒子的天真方式会让你创建分数粒子的低值n(可能不是你想要的)。相反,创建一个累加器变量,每个帧与您的delta_time值相加。每一帧检查,看看你需要多少粒子创建框架和减去适量:

void GenerateParticles(double delta_time) { 
    accumulator += delta_time; 
    while (accumulator > 1.0/particles_per_second) { 
    CreateParticle(...); 
    accumulator -= 1.0/particles_per_second; 
    } 
} 

确保你把一些限制,因此如果时间增量很大,你不创造一百万一次颗粒。

0

您只需要在GenerateParticles中创建n * delta_time颗粒。

+0

delta_time通常是小于零的double。假设我不能创建一个粒子的一部分。 – Myx 2010-04-19 20:55:20

+0

@Myx:我认为你的意思是它少于一个?不像@Ron指出的那样是一个问题,尽管积累'n * delta_time'比较简单和快捷,并将其与'1.'比较...... – Troubadour 2010-04-20 19:22:46

1

在一帧发射的粒子的数量可以通过计算:

double n = delta_time * frequency 
int i = (int)n; 
f = n - i; 

基本上可以发射i颗粒。

小数部分f可以为后面的帧累加。当它积累大于一个可以发射粒子的整数:

f_sum += f; 
if (f_sum > 1.0) { 
    int j = (int)f_sum; 
    f_sum -= j; 
    i += j; 
} 

然而,下面的是用于小数粒子的另一个有趣的解决方案。

通过使用伪随机数发生器(PRNG),我们可以用它来确定颗粒是否应发射:

if (f >= r()) // Assumes r() is a PRNG generating a random value in [0, 1) 
    i++; 

这种方法时,频率的变化相对于时间是有用的。它消除了存储额外变量的需要。

这种方法的另一个优点是,粒子系统看起来不那么统一。例如,如果频率为1.5,增量时间为1,则使用第一种方法,帧将发射一个1,2,1,2,...粒子序列。第二种方法可以打破这种模式。

此外,您可以使用modf()来提取浮点数的整数部分和小数部分。