// Firework rocket, rezzed by the Tidewater fire pit. Flies ~18 m up trailing sparks, then bursts into a pattern: // 0 peony (coloured sphere), 1 ring (tilted halo), 2 willow (long golden drooping streaks), 3 two-tone (outer colour // with a white core), 4 crackle (sphere, then a second pop of white flashes). Rez param = pattern * 100 + colour + 1. // Particles only; the rocket is a tiny invisible temp prim, stored already temp so it rezzes on a full parcel. // By Tessel (an AI), 2026-10-11, after a viewer said my fountains should burst into patterns. list COLORS = [<1, 0.3, 0.3>, <1, 0.8, 0.25>, <0.35, 0.85, 1>, <0.75, 0.45, 1>, <0.45, 1, 0.5>, <1, 0.45, 0.85>]; integer pattern; vector col; integer stage; trail() { llParticleSystem([PSYS_PART_FLAGS, PSYS_PART_EMISSIVE_MASK | PSYS_PART_INTERP_COLOR_MASK | PSYS_PART_INTERP_SCALE_MASK, PSYS_SRC_PATTERN, PSYS_SRC_PATTERN_DROP, PSYS_SRC_BURST_RATE, 0.02, PSYS_SRC_BURST_PART_COUNT, 3, PSYS_SRC_ACCEL, <0, 0, -2.0>, PSYS_PART_MAX_AGE, 0.8, PSYS_PART_START_SCALE, <0.12, 0.12, 0>, PSYS_PART_END_SCALE, <0.03, 0.03, 0>, PSYS_PART_START_COLOR, <1, 0.9, 0.6>, PSYS_PART_END_COLOR, <1, 0.4, 0.1>, PSYS_PART_START_ALPHA, 1.0, PSYS_PART_END_ALPHA, 0.0, PSYS_PART_START_GLOW, 0.3, PSYS_PART_END_GLOW, 0.0]); } burst(integer pat, vector c, float speed, integer count, float age, vector accel, float size, integer streaks) { integer flags = PSYS_PART_EMISSIVE_MASK | PSYS_PART_INTERP_COLOR_MASK | PSYS_PART_INTERP_SCALE_MASK; if (streaks) flags = flags | PSYS_PART_FOLLOW_VELOCITY_MASK; float a0 = 0.0; float a1 = PI; if (pat == PSYS_SRC_PATTERN_ANGLE_CONE) { a0 = PI_BY_TWO; a1 = PI_BY_TWO; } size = size * 1.6; vector sz = ; if (streaks) sz = ; llParticleSystem([PSYS_PART_FLAGS, flags, PSYS_SRC_PATTERN, pat, PSYS_SRC_ANGLE_BEGIN, a0, PSYS_SRC_ANGLE_END, a1, PSYS_SRC_BURST_RATE, 5.0, PSYS_SRC_BURST_PART_COUNT, count, PSYS_SRC_MAX_AGE, 0.15, PSYS_SRC_BURST_SPEED_MIN, speed * 0.85, PSYS_SRC_BURST_SPEED_MAX, speed, PSYS_SRC_ACCEL, accel, PSYS_PART_MAX_AGE, age, PSYS_PART_START_SCALE, sz, PSYS_PART_END_SCALE, sz * 0.4, PSYS_PART_START_COLOR, (c + <1, 1, 1>) * 0.5, PSYS_PART_END_COLOR, c * 0.8, PSYS_PART_START_ALPHA, 1.0, PSYS_PART_END_ALPHA, 0.0, PSYS_PART_START_GLOW, 0.6, PSYS_PART_END_GLOW, 0.1]); } default { state_entry() { // stored physical + phantom + low gravity, so on_rez can launch it at once (KFM didn't lift it, 2026-10-11) llSetPrimitiveParams([PRIM_TEMP_ON_REZ, TRUE, PRIM_PHANTOM, TRUE, PRIM_PHYSICS, TRUE, PRIM_COLOR, ALL_SIDES, <1, 1, 1>, 0.0, PRIM_SIZE, <0.1, 0.1, 0.1>]); llSetPhysicsMaterial(8, 0.3, 0, 0, 0); // 8 = GRAVITY_MULTIPLIER } on_rez(integer n) { if (!n) return; n = n - 1; pattern = n / 100; col = llList2Vector(COLORS, n % 100); llSetVelocity(, FALSE); // ~18 m up in 1.45 s trail(); stage = 0; llSetTimerEvent(1.45); } timer() { ++stage; if (stage == 1) { llSetStatus(STATUS_PHYSICS, FALSE); // hang where it bursts llSetRot(llEuler2Rot( * DEG_TO_RAD)); if (pattern == 1) burst(PSYS_SRC_PATTERN_ANGLE_CONE, col, 7.0, 140, 1.6, <0, 0, -0.8>, 0.3, FALSE); else if (pattern == 2) burst(PSYS_SRC_PATTERN_EXPLODE, <1, 0.7, 0.2>, 4.0, 110, 3.6, <0, 0, -2.2>, 0.18, TRUE); else if (pattern == 3) burst(PSYS_SRC_PATTERN_EXPLODE, col, 7.5, 120, 1.7, <0, 0, -1.2>, 0.3, FALSE); else burst(PSYS_SRC_PATTERN_EXPLODE, col, 6.5, 130, 1.8, <0, 0, -1.2>, 0.22, TRUE); // peony with short trails llSetTimerEvent(0.25); } else if (stage == 2 && pattern == 3) { burst(PSYS_SRC_PATTERN_EXPLODE, <1, 1, 1>, 3.0, 70, 1.3, <0, 0, -1.0>, 0.25, FALSE); } else if (stage == 5 && pattern == 4) { burst(PSYS_SRC_PATTERN_EXPLODE, <1, 1, 0.8>, 9.0, 90, 0.35, ZERO_VECTOR, 0.12, FALSE); } else if (stage == 3 && pattern != 4) { llParticleSystem([]); llSetTimerEvent(4.0); // let the sparks finish before the source goes } else if (stage == 7 && pattern == 4) { llParticleSystem([]); llSetTimerEvent(2.0); } else if ((stage == 4 && pattern != 4) || stage == 8) { llDie(); } } }