@maruaudio/dsp/physical/bloom approximates a tam-tam's nonlinear upward energy cascade without a nonlinearity in the sample loop: each mode's excitation is split into a part that arrives at contact and a part deferred behind a one-pole rise. A mode's audible gain is base + frac · rise, with base = 1 − frac fixed at the strike and rise climbing towards 1, while the resonator underneath keeps decaying. Higher modes defer more. The strike that calls it supplies the strength, scaled by velocity squared in the gong voice, so quiet strikes defer little.
| Function | Law |
|---|---|
bloomModeFraction(mode, count, amount) | amount · (mode / (count − 1))^1.5 · 0.85; 0 for mode 0, amount ≤ 0 or one mode |
bloomRiseCoefficient(seconds, rate) | 1 − exp(−1 / (seconds · rate)), f32; seconds floored at 0.0001 |
bloomEnvelopeStep(rise, coeff) | rise + coeff · (1 − rise), f32 |
bloomModeGain(base, frac, rise) | base + frac · rise |
Lifecycle
None: stateless stage functions with no imports or allocation. Per strike the caller stores base and frac per mode and computes the rise coefficient; per sample it advances one rise state with bloomEnvelopeStep and multiplies each mode by bloomModeGain.
When to use it
A tam-tam or large gong voice whose upper modes should grow after the attack on a hard strike, built on a modal bank.
Limits
- At most 85 % of a mode is deferred (
BLOOM_MAX_FRACTION), so every mode receives some energy at contact. - The fundamental never defers, and
amount = 0gives fraction 0 on every mode, so bloom is defeatable to the bit. - The rise state is rounded to f32 at each step; a non-positive sample rate falls back to 48 kHz.
- It is a separable approximation of the cascade, not a coupled nonlinear solver.