From 93f982df7b44024d19531816f8f3a91060fa16ad Mon Sep 17 00:00:00 2001
From: Sam <samuelkeiffer@gmail.com>
Date: Mon, 10 May 2021 19:58:32 -0500
Subject: [PATCH] Changed particles to a switch statement.

---
 assets/voxygen/shaders/particle-vert.glsl | 609 ++++++++++++----------
 1 file changed, 320 insertions(+), 289 deletions(-)

diff --git a/assets/voxygen/shaders/particle-vert.glsl b/assets/voxygen/shaders/particle-vert.glsl
index 4064561078..b3adde86cf 100644
--- a/assets/voxygen/shaders/particle-vert.glsl
+++ b/assets/voxygen/shaders/particle-vert.glsl
@@ -169,114 +169,125 @@ void main() {
     Attr attr;
     f_reflect = 1.0;
 
-    if (inst_mode == SMOKE) {
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                vec3(rand2 * 0.02, rand3 * 0.02, 1.0 + rand4 * 0.1)
-            ),
-            vec3(linear_scale(0.5)),
-            vec4(vec3(0.8, 0.8, 1) * 0.5, start_end(1.0, 0.0)),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 0.5)
-        );
-    } else if (inst_mode == FIRE) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            linear_motion(
-                vec3(0.0),
-                vec3(rand2 * 0.1, rand3 * 0.1, 2.0 + rand4 * 1.0)
-            ),
-            vec3(1.0),
-            vec4(2, 1.5 + rand5 * 0.5, 0, start_end(1.0, 0.0)),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3)
-        );
-        } else if (inst_mode == FIRE_BOWL) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            linear_motion(
-                vec3(normalize(vec2(rand0, rand1)) * 0.1, 0.6),
-                vec3(rand2 * 0.2, rand3 * 0.5, 0.8 + rand4 * 0.5)
-            ),
-            vec3(0.2), // Size
-            vec4(2, 1.5 + rand5 * 0.5, 0, start_end(1.0, 0.0)), // Colour
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3)
-        );
-    } else if (inst_mode == GUN_POWDER_SPARK) {
-        attr = Attr(
-            linear_motion(
-                normalize(vec3(rand0, rand1, rand3)) * 0.3,
-                normalize(vec3(rand4, rand5, rand6)) * 4.0 + grav_vel(earth_gravity)
-            ),
-            vec3(1.0),
-            vec4(3.5, 3 + rand7, 0, 1),
-            spin_in_axis(vec3(1,0,0),0)
-        );
-    } else if (inst_mode == SHRAPNEL) {
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                normalize(vec3(rand4, rand5, rand6)) * 20.0 + grav_vel(earth_gravity)
-            ),
-            vec3(1),
-            vec4(vec3(0.25), 1),
-            spin_in_axis(vec3(1,0,0),0)
-        );
-    } else if (inst_mode == BIG_SHRAPNEL) {
-        float brown_color = 0.05 + 0.1 * rand1;
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                normalize(vec3(rand4, rand5, rand6)) * 15.0 + grav_vel(earth_gravity)
-            ),
-            vec3(5 * (1 - percent())),
-            vec4(vec3(brown_color, brown_color / 2, 0), 1),
-            spin_in_axis(vec3(1,0,0),0)
-        );
-    } else if (inst_mode == FIREWORK_BLUE) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
-            ),
-            vec3(3.0 + rand0),
-            vec4(vec3(0, 0, 2), 1),
-            identity()
-        );
-    } else if (inst_mode == FIREWORK_GREEN) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
-            ),
-            vec3(3.0 + rand0),
-            vec4(vec3(0, 2, 0), 1),
-            identity()
-        );
-    } else if (inst_mode == FIREWORK_PURPLE) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
-            ),
-            vec3(3.0 + rand0),
-            vec4(vec3(2, 0, 2), 1),
-            identity()
-        );
-    } else if (inst_mode == FIREWORK_RED) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
-            ),
-            vec3(3.0 + rand0),
-            vec4(vec3(2, 0, 0), 1),
-            identity()
-        );
-        } else if (inst_mode == FIREWORK_WHITE) {
+    switch(inst_mode) {
+        case SMOKE:
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    vec3(rand2 * 0.02, rand3 * 0.02, 1.0 + rand4 * 0.1)
+                ),
+                vec3(linear_scale(0.5)),
+                vec4(vec3(0.8, 0.8, 1) * 0.5, start_end(1.0, 0.0)),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 0.5)
+            );
+            break;
+        case FIRE: 
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                linear_motion(
+                    vec3(0.0),
+                    vec3(rand2 * 0.1, rand3 * 0.1, 2.0 + rand4 * 1.0)
+                ),
+                vec3(1.0),
+                vec4(2, 1.5 + rand5 * 0.5, 0, start_end(1.0, 0.0)),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3)
+            );
+            break;
+        case FIRE_BOWL:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                linear_motion(
+                    vec3(normalize(vec2(rand0, rand1)) * 0.1, 0.6),
+                    vec3(rand2 * 0.2, rand3 * 0.5, 0.8 + rand4 * 0.5)
+                ),
+                vec3(0.2), // Size
+                vec4(2, 1.5 + rand5 * 0.5, 0, start_end(1.0, 0.0)), // Colour
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3)
+            );
+            break;
+        case GUN_POWDER_SPARK:
+            attr = Attr(
+                linear_motion(
+                    normalize(vec3(rand0, rand1, rand3)) * 0.3,
+                    normalize(vec3(rand4, rand5, rand6)) * 4.0 + grav_vel(earth_gravity)
+                ),
+                vec3(1.0),
+                vec4(3.5, 3 + rand7, 0, 1),
+                spin_in_axis(vec3(1,0,0),0)
+            );
+            break;
+        case SHRAPNEL:
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand4, rand5, rand6)) * 20.0 + grav_vel(earth_gravity)
+                ),
+                vec3(1),
+                vec4(vec3(0.25), 1),
+                spin_in_axis(vec3(1,0,0),0)
+            );
+            break;
+        case BIG_SHRAPNEL:
+            float brown_color = 0.05 + 0.1 * rand1;
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand4, rand5, rand6)) * 15.0 + grav_vel(earth_gravity)
+                ),
+                vec3(5 * (1 - percent())),
+                vec4(vec3(brown_color, brown_color / 2, 0), 1),
+                spin_in_axis(vec3(1,0,0),0)
+            );
+            break;
+        case FIREWORK_BLUE:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
+                ),
+                vec3(3.0 + rand0),
+                vec4(vec3(0, 0, 2), 1),
+                identity()
+            );
+            break;
+        case FIREWORK_GREEN:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
+                ),
+                vec3(3.0 + rand0),
+                vec4(vec3(0, 2, 0), 1),
+                identity()
+            );
+            break;
+        case FIREWORK_PURPLE:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
+                ),
+                vec3(3.0 + rand0),
+                vec4(vec3(2, 0, 2), 1),
+                identity()
+            );
+            break;
+        case FIREWORK_RED:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
+                ),
+                vec3(3.0 + rand0),
+                vec4(vec3(2, 0, 0), 1),
+                identity()
+            );
+            break;
+        case FIREWORK_WHITE:
             f_reflect = 0.0; // Fire doesn't reflect light, it emits it
             attr = Attr(
                 linear_motion(
@@ -287,188 +298,208 @@ void main() {
                 vec4(vec3(2, 2, 2), 1),
                 identity()
             );
-    } else if (inst_mode == FIREWORK_YELLOW) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            linear_motion(
+            break;
+        case FIREWORK_YELLOW:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
+                ),
+                vec3(3.0 + rand0),
+                vec4(vec3(2, 2, 0), 1),
+                identity()
+            );
+            break;
+        case LEAF:
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    vec3(0, 0, -2)
+                ) + vec3(sin(lifetime), sin(lifetime + 0.7), sin(lifetime * 0.5)) * 2.0,
+                vec3(4),
+                vec4(vec3(0.2 + rand7 * 0.2, 0.2 + (0.25 + rand6 * 0.5) * 0.3, 0) * (0.75 + rand1 * 0.5), 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
+            );
+            break;
+        case SNOW:
+            float height = mix(-4, 60, pow(start_end(1, 0), 3));
+            float wind_speed = (inst_pos.z - 2000) * 0.025;
+            vec3 offset = linear_motion(vec3(0), vec3(1, 1, 0) * wind_speed);
+            float end_alt = alt_at(start_pos.xy + offset.xy);
+            attr = Attr(
+                offset + vec3(0, 0, end_alt - start_pos.z + height) + vec3(sin(lifetime), sin(lifetime + 0.7), sin(lifetime * 0.5)) * 3,
+                vec3(mix(4, 0, pow(start_end(1, 0), 4))),
+                vec4(1),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
+            );
+            break;
+        case FIREFLY:
+            float raise = pow(sin(3.1416 * lifetime / inst_lifespan), 0.2);
+            attr = Attr(
+                vec3(0, 0, raise * 5.0) + vec3(
+                    sin(lifetime * 1.0 + rand0) + sin(lifetime * 7.0 + rand3) * 0.3,
+                    sin(lifetime * 3.0 + rand1) + sin(lifetime * 8.0 + rand4) * 0.3,
+                    sin(lifetime * 2.0 + rand2) + sin(lifetime * 9.0 + rand5) * 0.3
+                ),
+                vec3(raise),
+                vec4(vec3(5, 5, 1.1), 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
+            );
+            break;
+        case BEE:
+            float lower = pow(sin(3.1416 * lifetime / inst_lifespan), 0.2);
+            attr = Attr(
+                vec3(0, 0, lower * -0.5) + vec3(
+                    sin(lifetime * 2.0 + rand0) + sin(lifetime * 9.0 + rand3) * 0.3,
+                    sin(lifetime * 3.0 + rand1) + sin(lifetime * 10.0 + rand4) * 0.3,
+                    sin(lifetime * 4.0 + rand2) + sin(lifetime * 11.0 + rand5) * 0.3
+                ) * 0.5,
+                vec3(lower),
+                vec4(vec3(1, 0.7, 0), 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
+            );
+            break;
+        case GROUND_SHOCKWAVE:
+            attr = Attr(
+                vec3(0.0),
+                vec3(11.0, 11.0, (33.0 * rand0 * sin(2.0 * lifetime * 3.14 * 2.0))) / 3,
+                vec4(vec3(0.32 + (rand0 * 0.04), 0.22 + (rand1 * 0.03), 0.05 + (rand2 * 0.01)), 1),
+                spin_in_axis(vec3(1,0,0),0)
+            );
+            break;
+        case HEALING_BEAM:
+            f_reflect = 0.0;
+            attr = Attr(
+                spiral_motion(inst_dir, 0.3 * (floor(2 * rand0 + 0.5) - 0.5) * min(linear_scale(10), 1), lifetime / inst_lifespan, 10.0, inst_time),
+                vec3((1.7 - 0.7 * abs(floor(2 * rand0 - 0.5) + 0.5)) * (1.5 + 0.5 * sin(tick.x * 10 - lifetime * 4))),
+                vec4(vec3(0.4, 1.6 + 0.3 * sin(tick.x * 10 - lifetime * 3 + 4), 1.0 + 0.15 * sin(tick.x * 5 - lifetime * 5)), 1 /*0.3*/),
+                spin_in_axis(inst_dir, tick.z)
+            );
+            break;
+        case LIFESTEAL_BEAM:
+            f_reflect = 0.0;
+            float green_col = 0.2 + 1.4 * sin(tick.x * 5 + lifetime * 5);
+            float purple_col = 1.2 + 0.1 * sin(tick.x * 3 - lifetime * 3) - max(green_col, 1) + 1;
+            attr = Attr(
+                spiral_motion(inst_dir, 0.3 * (floor(2 * rand0 + 0.5) - 0.5) * min(linear_scale(10), 1), lifetime / inst_lifespan, 10.0, inst_time),
+                vec3((1.7 - 0.7 * abs(floor(2 * rand0 - 0.5) + 0.5)) * (1.5 + 0.5 * sin(tick.x * 10 - lifetime * 4))),
+                vec4(vec3(purple_col, green_col, 0.75 * purple_col), 1),
+                spin_in_axis(inst_dir, tick.z)
+            );
+            break;
+        case ENERGY_NATURE:
+            f_reflect = 0.0;
+            float spiral_radius = start_end(1 - pow(abs(rand5), 5), 1) * length(inst_dir);
+            attr = Attr(
+                spiral_motion(vec3(0, 0, rand3 + 1), spiral_radius, lifetime, abs(rand0), rand1 * 2 * PI) + vec3(0, 0, rand2),
+                vec3(6 * abs(rand4) * (1 - slow_start(2)) * pow(spiral_radius / length(inst_dir), 0.5)),
+                vec4(vec3(0, 1.7, 1.3), 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3)
+            );
+            break;
+        case FLAMETHROWER:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                (inst_dir * slow_end(1.5)) + vec3(rand0, rand1, rand2) * (percent() + 2) * 0.1,
+                vec3((2.5 * (1 - slow_start(0.2)))),
+                vec4(3, 1.6 + rand5 * 0.3 - 0.4 * percent(), 0.2, 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
+            );
+            break;
+        case EXPLOSION:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                inst_dir * ((rand0+1.0)/2 + 0.4) * slow_end(2.0) + 0.3 * grav_vel(earth_gravity),
+                vec3((3 * (1 - slow_start(0.1)))),
+                vec4(3, 1.6 + rand5 * 0.3 - 0.4 * percent(), 0.2, 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
+            );
+            break;
+        case ICE:
+            f_reflect = 0.0; // Ice doesn't reflect to look like magic
+            attr = Attr(
+                inst_dir * ((rand0+1.0)/2 + 0.4) * slow_end(2.0) + 0.3 * grav_vel(earth_gravity),
+                vec3((3 * (1 - slow_start(0.1)))),
+                vec4(0.2, 1.6 + rand5 * 0.3 - 0.4 * percent(), 3, 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
+            );
+            break;
+        case FIRE_SHOCKWAVE:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            attr = Attr(
+                vec3(rand0, rand1, lifetime * 10 + rand2),
+                vec3((5 * (1 - slow_start(0.5)))),
+                vec4(3, 1.6 + rand5 * 0.3 - 0.4 * percent(), 0.2, 1),
+                spin_in_axis(vec3(rand3, rand4, rand5), rand6)
+            );
+            break;
+        case CULTIST_FLAME:
+            f_reflect = 0.0; // Fire doesn't reflect light, it emits it
+            float purp_color = 0.9 + 0.3 * rand3;
+            attr = Attr(
+                (inst_dir * slow_end(1.5)) + vec3(rand0, rand1, rand2) * (percent() + 2) * 0.1,
+                vec3((3.5 * (1 - slow_start(0.2)))),
+                vec4(purp_color, 0.0, purp_color, 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
+            );
+            break;
+        case STATIC_SMOKE:
+            attr = Attr(
                 vec3(0),
-                normalize(vec3(rand1, rand2, rand3)) * 40.0 + grav_vel(earth_gravity)
-            ),
-            vec3(3.0 + rand0),
-            vec4(vec3(2, 2, 0), 1),
-            identity()
-        );
-    } else if (inst_mode == LEAF) {
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                vec3(0, 0, -2)
-            ) + vec3(sin(lifetime), sin(lifetime + 0.7), sin(lifetime * 0.5)) * 2.0,
-            vec3(4),
-            vec4(vec3(0.2 + rand7 * 0.2, 0.2 + (0.25 + rand6 * 0.5) * 0.3, 0) * (0.75 + rand1 * 0.5), 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
-        );
-    } else if (inst_mode == SNOW) {
-        float height = mix(-4, 60, pow(start_end(1, 0), 3));
-        float wind_speed = (inst_pos.z - 2000) * 0.025;
-        vec3 offset = linear_motion(vec3(0), vec3(1, 1, 0) * wind_speed);
-        float end_alt = alt_at(start_pos.xy + offset.xy);
-        attr = Attr(
-            offset + vec3(0, 0, end_alt - start_pos.z + height) + vec3(sin(lifetime), sin(lifetime + 0.7), sin(lifetime * 0.5)) * 3,
-            vec3(mix(4, 0, pow(start_end(1, 0), 4))),
-            vec4(1),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
-        );
-    } else if (inst_mode == FIREFLY) {
-        float raise = pow(sin(3.1416 * lifetime / inst_lifespan), 0.2);
-        attr = Attr(
-            vec3(0, 0, raise * 5.0) + vec3(
-                sin(lifetime * 1.0 + rand0) + sin(lifetime * 7.0 + rand3) * 0.3,
-                sin(lifetime * 3.0 + rand1) + sin(lifetime * 8.0 + rand4) * 0.3,
-                sin(lifetime * 2.0 + rand2) + sin(lifetime * 9.0 + rand5) * 0.3
-            ),
-            vec3(raise),
-            vec4(vec3(5, 5, 1.1), 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
-        );
-    } else if (inst_mode == BEE) {
-        float lower = pow(sin(3.1416 * lifetime / inst_lifespan), 0.2);
-        attr = Attr(
-            vec3(0, 0, lower * -0.5) + vec3(
-                sin(lifetime * 2.0 + rand0) + sin(lifetime * 9.0 + rand3) * 0.3,
-                sin(lifetime * 3.0 + rand1) + sin(lifetime * 10.0 + rand4) * 0.3,
-                sin(lifetime * 4.0 + rand2) + sin(lifetime * 11.0 + rand5) * 0.3
-            ) * 0.5,
-            vec3(lower),
-            vec4(vec3(1, 0.7, 0), 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3 + lifetime * 5)
-        );
-    } else if (inst_mode == GROUND_SHOCKWAVE) {
-        attr = Attr(
-            vec3(0.0),
-            vec3(11.0, 11.0, (33.0 * rand0 * sin(2.0 * lifetime * 3.14 * 2.0))) / 3,
-            vec4(vec3(0.32 + (rand0 * 0.04), 0.22 + (rand1 * 0.03), 0.05 + (rand2 * 0.01)), 1),
-            spin_in_axis(vec3(1,0,0),0)
-        );
-    } else if (inst_mode == HEALING_BEAM) {
-        f_reflect = 0.0;
-        attr = Attr(
-            spiral_motion(inst_dir, 0.3 * (floor(2 * rand0 + 0.5) - 0.5) * min(linear_scale(10), 1), lifetime / inst_lifespan, 10.0, inst_time),
-            vec3((1.7 - 0.7 * abs(floor(2 * rand0 - 0.5) + 0.5)) * (1.5 + 0.5 * sin(tick.x * 10 - lifetime * 4))),
-            vec4(vec3(0.4, 1.6 + 0.3 * sin(tick.x * 10 - lifetime * 3 + 4), 1.0 + 0.15 * sin(tick.x * 5 - lifetime * 5)), 1 /*0.3*/),
-            spin_in_axis(inst_dir, tick.z)
-        );
-    } else if (inst_mode == LIFESTEAL_BEAM) {
-        f_reflect = 0.0;
-        float green_col = 0.2 + 1.4 * sin(tick.x * 5 + lifetime * 5);
-        float purple_col = 1.2 + 0.1 * sin(tick.x * 3 - lifetime * 3) - max(green_col, 1) + 1;
-        attr = Attr(
-            spiral_motion(inst_dir, 0.3 * (floor(2 * rand0 + 0.5) - 0.5) * min(linear_scale(10), 1), lifetime / inst_lifespan, 10.0, inst_time),
-            vec3((1.7 - 0.7 * abs(floor(2 * rand0 - 0.5) + 0.5)) * (1.5 + 0.5 * sin(tick.x * 10 - lifetime * 4))),
-            vec4(vec3(purple_col, green_col, 0.75 * purple_col), 1),
-            spin_in_axis(inst_dir, tick.z)
-        );
-    } else if (inst_mode == ENERGY_NATURE) {
-        f_reflect = 0.0;
-        float spiral_radius = start_end(1 - pow(abs(rand5), 5), 1) * length(inst_dir);
-        attr = Attr(
-            spiral_motion(vec3(0, 0, rand3 + 1), spiral_radius, lifetime, abs(rand0), rand1 * 2 * PI) + vec3(0, 0, rand2),
-            vec3(6 * abs(rand4) * (1 - slow_start(2)) * pow(spiral_radius / length(inst_dir), 0.5)),
-            vec4(vec3(0, 1.7, 1.3), 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9 * 3)
-        );
-    } else if (inst_mode == FLAMETHROWER) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            (inst_dir * slow_end(1.5)) + vec3(rand0, rand1, rand2) * (percent() + 2) * 0.1,
-            vec3((2.5 * (1 - slow_start(0.2)))),
-            vec4(3, 1.6 + rand5 * 0.3 - 0.4 * percent(), 0.2, 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
-        );
-    } else if (inst_mode == EXPLOSION) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            inst_dir * ((rand0+1.0)/2 + 0.4) * slow_end(2.0) + 0.3 * grav_vel(earth_gravity),
-            vec3((3 * (1 - slow_start(0.1)))),
-            vec4(3, 1.6 + rand5 * 0.3 - 0.4 * percent(), 0.2, 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
-        );
-    } else if (inst_mode == ICE) {
-        f_reflect = 0.0; // Ice doesn't reflect to look like magic
-        attr = Attr(
-            inst_dir * ((rand0+1.0)/2 + 0.4) * slow_end(2.0) + 0.3 * grav_vel(earth_gravity),
-            vec3((3 * (1 - slow_start(0.1)))),
-            vec4(0.2, 1.6 + rand5 * 0.3 - 0.4 * percent(), 3, 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
-        );
-    } else if (inst_mode == FIRE_SHOCKWAVE) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        attr = Attr(
-            vec3(rand0, rand1, lifetime * 10 + rand2),
-            vec3((5 * (1 - slow_start(0.5)))),
-            vec4(3, 1.6 + rand5 * 0.3 - 0.4 * percent(), 0.2, 1),
-            spin_in_axis(vec3(rand3, rand4, rand5), rand6)
-        );
-    } else if (inst_mode == CULTIST_FLAME) {
-        f_reflect = 0.0; // Fire doesn't reflect light, it emits it
-        float purp_color = 0.9 + 0.3 * rand3;
-        attr = Attr(
-            (inst_dir * slow_end(1.5)) + vec3(rand0, rand1, rand2) * (percent() + 2) * 0.1,
-            vec3((3.5 * (1 - slow_start(0.2)))),
-            vec4(purp_color, 0.0, purp_color, 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
-        );
-    } else if (inst_mode == STATIC_SMOKE) {
-        attr = Attr(
-            vec3(0),
-            vec3((0.5 * (1 - slow_start(0.8)))),
-            vec4(1.0),
-            spin_in_axis(vec3(rand6, rand7, rand8), rand9)
-        );
-    } else if (inst_mode == BLOOD) {
-        attr = Attr(
-            linear_motion(
-                vec3(0),
-                normalize(vec3(rand4, rand5, rand6)) * 5.0 + grav_vel(earth_gravity)
-            ),
-            vec3((2.0 * (1 - slow_start(0.8)))),
-            vec4(1, 0, 0, 1),
-            spin_in_axis(vec3(1,0,0),0)
-        );
-    } else if (inst_mode == ENRAGED) {
-        f_reflect = 0.0;
-        float red_color = 1.2 + 0.3 * rand3;
-        attr = Attr(
-            (inst_dir * slow_end(1.5)) + vec3(rand0, rand1, rand2) * (percent() + 2) * 0.1,
-            vec3((3.5 * (1 - slow_start(0.2)))),
-            vec4(red_color, 0.0, 0.0, 1),
-            spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
-        );
-    } else if (inst_mode == LASER) {
-        f_reflect = 0.0;
-        vec3 perp_axis = normalize(cross(inst_dir, vec3(0.0, 0.0, 1.0)));
-        vec3 offset = vec3(0.0);
-        if (rand0 > 0.0) {
-            offset = perp_axis * 0.5;
-        } else {
-            offset = perp_axis * -0.5;
-        }
-        attr = Attr(
-            inst_dir * percent() + offset,
-            vec3(1.0, 1.0, 50.0),
-            vec4(vec3(2.0, 0.0, 0.0), 1),
-            spin_in_axis(perp_axis, asin(inst_dir.z / length(inst_dir)) + PI / 2.0)
-        );
-    } else {
-        attr = Attr(
-            linear_motion(
-                vec3(rand0 * 0.25, rand1 * 0.25, 1.7 + rand5),
-                vec3(rand2 * 0.1, rand3 * 0.1, 1.0 + rand4 * 0.5)
-            ),
-            vec3(exp_scale(-0.2)),
-            vec4(1),
-            spin_in_axis(vec3(1,0,0),0)
-        );
+                vec3((0.5 * (1 - slow_start(0.8)))),
+                vec4(1.0),
+                spin_in_axis(vec3(rand6, rand7, rand8), rand9)
+            );
+            break;
+        case BLOOD:
+            attr = Attr(
+                linear_motion(
+                    vec3(0),
+                    normalize(vec3(rand4, rand5, rand6)) * 5.0 + grav_vel(earth_gravity)
+                ),
+                vec3((2.0 * (1 - slow_start(0.8)))),
+                vec4(1, 0, 0, 1),
+                spin_in_axis(vec3(1,0,0),0)
+            );
+            break;
+        case ENRAGED:
+            f_reflect = 0.0;
+            float red_color = 1.2 + 0.3 * rand3;
+            attr = Attr(
+                (inst_dir * slow_end(1.5)) + vec3(rand0, rand1, rand2) * (percent() + 2) * 0.1,
+                vec3((3.5 * (1 - slow_start(0.2)))),
+                vec4(red_color, 0.0, 0.0, 1),
+                spin_in_axis(vec3(rand6, rand7, rand8), percent() * 10 + 3 * rand9)
+            );
+            break;
+        case LASER:
+            f_reflect = 0.0;
+            vec3 perp_axis = normalize(cross(inst_dir, vec3(0.0, 0.0, 1.0)));
+            offset = vec3(0.0);
+            if (rand0 > 0.0) {
+                offset = perp_axis * 0.5;
+            } else {
+                offset = perp_axis * -0.5;
+            }
+            attr = Attr(
+                inst_dir * percent() + offset,
+                vec3(1.0, 1.0, 50.0),
+                vec4(vec3(2.0, 0.0, 0.0), 1),
+                spin_in_axis(perp_axis, asin(inst_dir.z / length(inst_dir)) + PI / 2.0)
+            );
+            break;
+        default:
+            attr = Attr(
+                linear_motion(
+                    vec3(rand0 * 0.25, rand1 * 0.25, 1.7 + rand5),
+                    vec3(rand2 * 0.1, rand3 * 0.1, 1.0 + rand4 * 0.5)
+                ),
+                vec3(exp_scale(-0.2)),
+                vec4(1),
+                spin_in_axis(vec3(1,0,0),0)
+            );
+            break;
     }
 
     // Temporary: use shrinking particles as a substitute for fading ones