# LlmHelper Audio MCP

An MCP server that turns a script into voice clips with OpenAI text-to-speech: one numbered audio file per line plus a manifest of each clip's duration, ready to lay onto a video (for example with Jig's `demo_narrate`). An agent writes the script, picks voices, generates under a spend limit and exports.

## Install

On a machine with LlmHelper installed, in PowerShell:

```
irm https://shakytext.com/audio/install.ps1 | iex
```

That installs the server to `%USERPROFILE%\LlmHelper\mcp\audio`, registers it with Claude Code as `llmhelper-audio` (user scope) when the `claude` CLI is present, and prints the next steps. Re-run it to update. To register by hand:

```
claude mcp add --scope user llmhelper-audio -- "%USERPROFILE%\LlmHelper\mcp\audio\LlmHelper.Audio.Mcp.exe"
```

Needs the .NET 8 Runtime (the installer offers it via winget).

## Keys

None to configure here. Open **LlmHelper** and save your **OpenAI** key once (API Keys); this server reads it from LlmHelper's database. `OPENAI_API_KEY` as a user environment variable also works.

## Narrating a Jig demo take

1. `save_project` with one segment per narration line, in speaking order.
2. `check_script`, then `generate` with `max_cost_usd` a little above the estimate (a 2-minute demo is about 3 cents).
3. `export_clips` (wav). Each clip's `seconds`, `speechStartSeconds` and `speechEndSeconds` are in the result and in `manifest.json`.
4. Film with Jig: before each step, `demo_mark {kind: "say", text: <the exact line>, holdMs: <clip seconds x 1000>}`.
5. `demo_end`, then `demo_narrate {takeDir: <take folder>, clipsFolder: <the export_clips folder>}`.

Jig also needs **ffmpeg** (it finds ShareX's copy or one on PATH).

The clips folder: `001.wav`, `002.wav`, ... in script order, plus `manifest.json` (`clips[]` with `file`, `seconds`, `text`, `kind`, `speechStartSeconds`, `speechEndSeconds`) and `manifest.csv`. These field names are stable.
## Tools

| Tool | Paid | What it does |
|---|---|---|
| `get_guide` | no | Syntax, cast, writing advice, prices, spend rules. Read first. |
| `list_providers` | no | Providers, models, prices, whether a key is set, today's MCP spend. |
| `list_voices` | no | Voices per provider, filterable; cached 7 days. |
| `list_projects` / `get_project` | no | Projects; one project's script, cast and status. |
| `save_project` | no | Create/update script and cast; returns the check report. |
| `check_script` | no | Per-segment speaker/voice/cached/estimate/errors with line numbers. |
| `generate` | **yes** | Voices uncached segments. Requires `max_cost_usd`; refuses (sending nothing) above it or past the daily cap. |
| `export_clips` | no | One numbered WAV/MP3 per segment + manifest.json/.csv (duration, start time, speech start/end, speaker, text). |
| `export` | no | Joins the project into MP3/WAV. |
| `splice` | no | Joins arbitrary existing files with trims, gain and gaps. |
| `add_asset` | no | Copies a file into the project's `assets\` for `[[file=...]]`. |
| `audio_info` | no | Duration, rate, channels, peak dBFS. |
| `preview_voice` | **yes** (cached) | Speaks a sample line in one voice; returns the WAV path. |
| `transcribe` | **yes** (localwhisper free) | Audio/video → .txt (+ .srt with timestamps). OpenAI, Azure or the tower's Whisper. |
| `list_transcriptions` | no | Saved transcriptions. |
| `transcript_to_project` | no | Transcript → editable script project. |

Prompts: `write_script`, `fix_lines`.

## Spend rules

- `generate` always takes `max_cost_usd`.
- Daily MCP cap: `mcpDailyCapUsd` in `%USERPROFILE%\LlmHelper\Audio\settings.json`, default $2.00.
- Every paid call is appended to `spend.jsonl` there.
- Cached segments cost nothing, and the cache is shared across projects.

The same features are in LlmHelper's Audio window (menu Audio → Audio Studio).
