Just as explained here https://www.youtube.com/watch?v=7hC_QT4GLiU
NOTE: GeForce GTX 660 limits:
-
GL_MAX_UNIFORM_BUFFER_BINDINGS -> 84
-
GL_MAX_UNIFORM_BLOCK_SIZE -> 65536 (bytes)
-
GL_MAX_VERTEX_UNIFORM_BLOCKS -> 14
-
GL_MAX_FRAGMENT_UNIFORM_BLOCKS -> 14
-
GL_MAX_GEOMETRY_UNIFORM_BLOCKS -> 14
-
See light_module.cc, current implementation is not good enough for having particle lights. I need the Light structure to be directly integrated in a new ParticleData (like in particle_core_data.hh).
struct ParticlesLight {
float intensity;
float radius;
float attenuation;
};
struct LitParticlesData {
std::unique_ptr<float[] > m_lifetime;
std::unique_ptrglm::f32vec3[] m_velocity;
std::unique_ptr<glm::u8vec4[] > m_color;
std::unique_ptrglm::f32vec3[] m_position;
std::unique_ptr<ParticlesLight[]> m_light;
...
};
NO, in fact the attributes of ParticlesLight will be shared for all particles. So ParticleCoreData is enough, I only need a light updater (CPU or GPU). If CPU, this light updater only needs to update the UBO block, which will look like this:
layout (std140, binding = WHATEVER) uniform ParticleLightsData {
vec4 ParticleColors[2000];
vec3 ParticlePosition[2000];
float Radius;
float Intensity;
float Attenuation;
}
The 2000 is a rounded value that matches GL_MAX_UNIFORM_BLOCK_SIZE (65536 byte for Geforce GTX 660) for the UBO above (total size is 56012 bytes).
Also, UBOs are usually faster than SSBOs, and it is quite standard to use uniforms this way, (see https://github.com/andreasmuller/NoiseWorkshop/blob/05eacee5dc58e48265e0153aba9ad2782190f185/ParticleCloudGPU/src/ParticleSystemGPU.cpp#L128)
-
A parameter will determine what is the percentage of particles that will emit lights. This percentage will cap at PERCENTAGE * NUMBER_OF_PARTICLES * SIZEOF(LIGHTDATA) < GL_MAX_UNIFORM_BLOCK_SIZE (in other words, needs to be < GL_MAX_UNIFORM_BLOCK_SIZE/(NUMBER_OF_PARTICLES * SIZEOF(LIGHT_DATA))). So with the data above, if particle_count = 5000, the percentage must cap at <=40% (0.4*5000 = 2000).
-
Since the alive particles (in the pool) are not sorted, the first ones could be the lit particles. To make sure this is truly "random", the life of each particles should be randomized (their age should be randomized and capped at maximum lifetime)