MiniMax Speech 2.8 HD · Text to Speech
400 voices, and one field does the acting
- audio
- task id
Thirteen inputs and the one that changes everything is emotion. Not speed, not pitch, not the voice picker - those are mixing moves. emotion is the difference between a narrator reading a line and a character meaning it, and it's the reason a hosted TTS call can beat a local Piper or Kokoro run for anything with acting in it.
What it is
The HD tier of MiniMax Speech 2.8, exposed as a node in the PopNow pack. It takes text and returns a ComfyUI AUDIO clip. Billed per 1,000 characters at 18 credits ($0.18), and it runs on PopNow's servers, so there's nothing to install and no VRAM spoken for. In a video pipeline this is the node that turns a script into a voice track you can feed to an audio-driven avatar node, or just save and cut against.
Why HD over Turbo? Both take the same inputs and produce the same shape of result. HD is roughly 1.7× the price for better fidelity - worth it for a hero voice-over, wasteful for placeholder scratch tracks.
How it works
The text goes out with your voice and delivery settings, PopNow renders the speech, and the node downloads it and decodes it into the standard AUDIO format ComfyUI understands. Nothing clever, nothing cached - text and voice are the payload, and each run is a fresh render, which is why the per-character billing matters.
The text field does more than plain words. Sound tags like (sighs) or (laughs) are performed rather than read aloud, which is a cheap way to get a beat of acting without writing it into the sentence. Keep them in parentheses and use them sparingly; a paragraph of stage directions competes with the speech.
The inputs that matter
text- the words, exactly as written, up to 5000 characters. Billed per 1,000.voice_id- the system voice;Calm_Womanis the default and the list runs past 400 entries, labelled with the language each was built for. The English set alone is huge:English_expressive_narrator,English_Aussie_Bloke,English_Husky_MetalHead,English_Whispering_girl_v3. There are proper names in there for every language from Arabic to Afrikaans.emotion-neutralby default, withhappy,sad,angry,fearful,disgustedandsurprisedalongside.speed,pitch,volume- speaking rate (1 is normal), pitch in semitones (0 is the voice's own), loudness multiplier. Nudge, don't shove: ±2 semitones and 0.9–1.1 speed covers most needs.language- a pronunciation hint,autoby default. Setting it explicitly helps on mixed-language text.output_format,sample_rate,bitrate,audio_channels- delivery settings.mp3is the default;pcmis headerless 16-bit little-endian, which is what you want if something downstream is doing its own parsing. Leaving these on their model-default values is fine.english_normalization- off by default. Turn it on when the text has numbers, dates or abbreviations that should be read like a person would say them ("$4.50" as four fifty, not four dollars dot five zero).pronunciation_dict- a JSON list of{"alias", "pronunciation"}objects for names the voice keeps mangling.
Outputs: audio and task id.
A voice-over workflow that doesn't fight you
Write for the ear, not the page: short sentences, one idea each, and punctuation where you want the pause. Then pick two voices and render the same 200 characters through both before committing to a full read - voice choice is the decision most likely to be wrong, and it costs almost nothing to audition.
Keep pronunciation_dict for the second pass. Get the read right first, then fix the three words it fumbled. Building a big dict before you know what breaks is wasted effort.
Install
Manager → search PopNow → Install, or:
cd ComfyUI/custom_nodes
git clone https://github.com/popnow-ai/popnow-comfyui
Restart, paste a key from popnow.ai/api/console/keys into Settings > PopNow, restart once more. No dependencies - the pack declares none and uses the PyAV that ships with ComfyUI for decoding.
Errors you'll actually see
No PopNow API key is set is a missing key. PopNow 40201 is credits. A PopNow 400 naming pronunciation_dict means the JSON didn't parse - it wants a list of objects with alias and pronunciation, not a plain dictionary. PopNow 40310 means the account's email isn't verified yet, which is worth knowing before you assume the voice list is broken.
Inputs (13)
| Name | Type | Default | Description |
|---|---|---|---|
| text | STRING | The words to be spoken, exactly as written. Sound tags such as (sighs) or (laughs) are performed. Billed per 1,000 characters. | |
| voice_id | COMBO | Calm_Woman | System voice. The label shows the voice name and, where known, the language it is built for. |
| emotion | COMBO | neutral | Emotion of the reading. |
| speed | FLOAT | 1.000.5–2 | Speaking rate; 1 is the voice's normal pace. |
| pitch | INT | 0-12–12 | Pitch shift in semitones; 0 keeps the voice's own pitch. |
| volume | FLOAT | 1.00.1–10 | Loudness multiplier; 1 is the normal level. |
| language | COMBO | auto | Language hint that improves pronunciation; auto detects it from the text. |
| output_format | COMBO | mp3 | File format of the result; pcm is headerless 16-bit little-endian samples. |
| sample_rate | COMBO | model default | Sample rate in Hz. The model uses 32000 when omitted. |
| bitrate | COMBO | model default | MP3 bitrate in bits per second; ignored for other formats. The model uses 128000 when omitted. |
| audio_channels | COMBO | model default | Mono or stereo output. Mono when omitted. |
| english_normalization | BOOLEAN | false | Read numbers, dates and abbreviations in English text the way a person would say them. |
| pronunciation_dict | STRING | Custom pronunciations: each alias in the text is read as its pronunciation. JSON. A list of objects with "alias", "pronunciation". |
Outputs (2)
| Name | Type | Description |
|---|---|---|
| audio | AUDIO | Several results come back as a batch; Save Audio writes one file each. |
| task id | STRING | The PopNow task id, for the API console logs or support. |