summaryrefslogtreecommitdiff
path: root/drivers/gles3/shaders/particles.glsl
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gles3/shaders/particles.glsl')
-rw-r--r--drivers/gles3/shaders/particles.glsl115
1 files changed, 93 insertions, 22 deletions
diff --git a/drivers/gles3/shaders/particles.glsl b/drivers/gles3/shaders/particles.glsl
index e72f12cc5e..347b15d639 100644
--- a/drivers/gles3/shaders/particles.glsl
+++ b/drivers/gles3/shaders/particles.glsl
@@ -22,16 +22,21 @@ struct Attractor {
#define MAX_ATTRACTORS 64
-uniform mat4 origin;
+uniform bool emitting;
uniform float system_phase;
uniform float prev_system_phase;
-uniform float total_particles;
+uniform int total_particles;
uniform float explosiveness;
+uniform float randomness;
uniform vec4 time;
uniform float delta;
uniform vec3 gravity;
uniform int attractor_count;
uniform Attractor attractors[MAX_ATTRACTORS];
+uniform bool clear;
+uniform uint cycle;
+uniform float lifetime;
+uniform mat4 emission_transform;
out highp vec4 out_color; //tfb:
@@ -53,52 +58,116 @@ MATERIAL_UNIFORMS
#endif
+uint hash(uint x) {
+
+ x = ((x >> uint(16)) ^ x) * uint(0x45d9f3b);
+ x = ((x >> uint(16)) ^ x) * uint(0x45d9f3b);
+ x = (x >> uint(16)) ^ x;
+ return x;
+}
+
+
void main() {
bool apply_forces=true;
bool apply_velocity=true;
+ vec3 current_gravity = gravity;
+ float local_delta=delta;
float mass = 1.0;
- float restart_phase = float(gl_InstanceID)/total_particles;
- restart_phase*= explosiveness;
+ float restart_phase = float(gl_VertexID)/float(total_particles);
+
+ if (randomness>0.0) {
+ uint seed = cycle;
+ if (restart_phase >= system_phase) {
+ seed-=uint(1);
+ }
+ seed*=uint(total_particles);
+ seed+=uint(gl_VertexID);
+ float random = float(hash(seed) % uint(65536)) / 65536.0;
+ restart_phase+=randomness * random * 1.0 / float(total_particles);
+ }
+
+ restart_phase*= (1.0-explosiveness);
bool restart=false;
- bool active = out_velocity_active.a > 0.5;
+ bool active = velocity_active.a > 0.5;
if (system_phase > prev_system_phase) {
- restart = prev_system_phase < restart_phase && system_phase >= restart_phase;
+ if (prev_system_phase < restart_phase && system_phase >= restart_phase) {
+ restart=true;
+#ifdef USE_FRACTIONAL_DELTA
+ local_delta = (system_phase - restart_phase) * lifetime;
+#endif
+ }
+
} else {
- restart = prev_system_phase < restart_phase || system_phase >= restart_phase;
+ if (prev_system_phase < restart_phase) {
+ restart=true;
+#ifdef USE_FRACTIONAL_DELTA
+ local_delta = (1.0 - restart_phase + system_phase) * lifetime;
+#endif
+ } else if (system_phase >= restart_phase) {
+ restart=true;
+#ifdef USE_FRACTIONAL_DELTA
+ local_delta = (system_phase - restart_phase) * lifetime;
+#endif
+ }
}
- if (restart) {
- active=true;
+ uint current_cycle = cycle;
+
+ if (system_phase < restart_phase) {
+ current_cycle-=uint(1);
}
- out_color=color;
- out_velocity_active=velocity_active;
- out_custom=custom;
+ uint particle_number = current_cycle * uint(total_particles) + uint(gl_VertexID);
- mat4 xform = transpose(mat4(xform_1,xform_2,xform_3,vec4(vec3(0.0),1.0)));
+ if (restart) {
+ active=emitting;
+ }
+ mat4 xform;
- out_rot_active=rot_active;
+#if defined(ENABLE_KEEP_DATA)
+ if (clear) {
+#else
+ if (clear || restart) {
+#endif
+ out_color=vec4(1.0);
+ out_velocity_active=vec4(0.0);
+ out_custom=vec4(0.0);
+ if (!restart)
+ active=false;
+
+ xform = mat4(
+ vec4(1.0,0.0,0.0,0.0),
+ vec4(0.0,1.0,0.0,0.0),
+ vec4(0.0,0.0,1.0,0.0),
+ vec4(0.0,0.0,0.0,1.0)
+ );
+ } else {
+ out_color=color;
+ out_velocity_active=velocity_active;
+ out_custom=custom;
+ xform = transpose(mat4(xform_1,xform_2,xform_3,vec4(vec3(0.0),1.0)));
+ }
if (active) {
//execute shader
{
- VERTEX_SHADER_CODE
+VERTEX_SHADER_CODE
}
#if !defined(DISABLE_FORCE)
- {
+ if (true) {
- vec3 force = gravity;
+ vec3 force = current_gravity;
for(int i=0;i<attractor_count;i++) {
- vec3 rel_vec = out_pos_lifetime.xyz - attractors[i].pos;
+ vec3 rel_vec = xform[3].xyz - attractors[i].pos;
float dist = rel_vec.length();
if (attractors[i].radius < dist)
continue;
@@ -119,17 +188,19 @@ void main() {
}
}
- out_velocity_seed.xyz += force * delta;
+ out_velocity_active.xyz += force * local_delta;
}
#endif
#if !defined(DISABLE_VELOCITY)
- {
+ if (true) {
- out_pos_lifetime.xyz += out_velocity_seed.xyz * delta;
+ xform[3].xyz += out_velocity_active.xyz * local_delta;
}
#endif
+ } else {
+ xform=mat4(0.0);
}
xform = transpose(xform);
@@ -162,6 +233,6 @@ MATERIAL_UNIFORMS
void main() {
{
- FRAGMENT_SHADER_CODE
+FRAGMENT_SHADER_CODE
}
}