Build with this node

Start with a prompt in Studio, or copy it into your own coding agent.

Ask Studio

@maruaudio/dsp/voices/mouth is a monophonic vocal-tract physical model: an LF glottal-flow source with aspiration drives a Kelly-Lochbaum digital waveguide (44 sections at 48 kHz, stepped twice per frame) with a branching nasal cavity, fricative turbulence at constrictions, stop-release transients, portamento and an inlined Freeverb tail. The source header says it is ported from Neil Thapen's Pink Trombone (MIT) with f32 state. Noise samples are arguments, so it is deterministic.

Parameters

setMouthParam(state, index, value), clamped as coded (44-section grid):

IndexRangeDefault
0 tongue index / 1 diameter12 to 29 (blade + 2 to tip − 3) / 2.05 to 3.512.9 / 2.43
2 constriction index / 3 diameter−1 to the section count / −1 to 3.5−1 / 3
4 velum / 5 tenseness (loudness = t^0.25) / 6 glide0 to 1 / 0 to 1 / 0 to 1 s0 / 0.6 / 0.06
7 vibrato amount / 8 rate0 to 0.1 / 0 to 12 Hz0.005 / 6
9 fricative / 10 reverb mix0 to 10 / 0.2
11 reverb room0 to 1, mapped to feedback 0.7 + 0.28 × roomfeedback 0.82
12 breath / 13 always voice / 14 pitch wobble0 to 10 / 1 / 0
15 movement speed / 16 throat1 to 60 / −1 to 115 / 0

Lifecycle

initMouthVoice(rate) keeps the historical 44-section, two-step geometry at every rate; prepareMouthVoiceSampleRate(state, rate) re-initializes in place with rate-native geometry (mouthTractSteps, mouthTractSections) and resets parameters to defaults → setMouthParam → mouthNoteOn (note clamped to 0..127; from silence the pitch jumps, else it glides) / mouthNoteOff (only the gate note) → mouthTick(state, aspirationNoise, turbulenceNoise) per frame → mouthFinishBlock every mouthBlockFrames(rate) frames (128 at 48 kHz) → resetMouthVoice clears the tract, nasal branch and reverb without reallocating.

When to use it

Keyboard-driven vowels and sung lines where tongue, constriction and velum are performance controls.

Limits

  • Mono, one voice, sample tick; output at unity with no master parameter.
  • The caller supplies and conditions the noise; mouthNoiseGain(rate) keeps its power per hertz at the 48 kHz level.
  • Storage is sized at the maximum rate, so preparing never allocates.

Algorithm properties and proofs

No Lean 4 proof is mapped to this node.

Explore proofs alongside performance

Dependencies

None: this node imports no other node.

Dependents

No other node imports this one.

Used by