@kolbo/mcp 1.110.3 → 1.112.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/package.json +1 -1
- package/src/apps/widgets/generation.js +48 -6
- package/src/tools/_shared.js +4 -0
- package/src/tools/generate.js +40 -8
package/README.md
CHANGED
|
@@ -147,7 +147,7 @@ Without the optional skill, the config block alone already exposes every tool
|
|
|
147
147
|
| `generate_lipsync` | Source image/video + audio → lipsynced video (Sync-3 adds active-speaker selection, emotion, model mode, temperature) |
|
|
148
148
|
| `generate_creative_director` | One brief → N coordinated scenes (image or video) |
|
|
149
149
|
| `generate_music` | Text (+ optional lyrics) → song. Style, title, negative tags, length, and Suno fine-controls (style weight, weirdness, audio weight, persona / singing voice) |
|
|
150
|
-
| `generate_speech` | Text + voice → spoken audio. Full expressive/style control: Google/Gemini named voice-direction presets (`style_instructions_preset_id`: warm/dramatic/whisper/…) or free-form `style_instructions`, preset styles + emotions (DeepDub / MiniMax / Cartesia), speed, accent/`language`, and per-provider voice settings (ElevenLabs similarity/style, DeepDub accent/variance/tempo, MiniMax pitch/volume/intensity/timbre). Status returns the same fields for reuse. |
|
|
150
|
+
| `generate_speech` | Text + voice → spoken audio. `eleven_model` (eleven_v4 / eleven_v3 / eleven_multilingual_v2) picks which ElevenLabs model speaks an ElevenLabs voice (stock or own clone; omit = the voice's default; same price; `turbo` needs v4). Full expressive/style control: Google/Gemini named voice-direction presets (`style_instructions_preset_id`: warm/dramatic/whisper/…) or free-form `style_instructions`, preset styles + emotions (DeepDub / MiniMax / Cartesia), speed, accent/`language`, and per-provider voice settings (ElevenLabs stability/similarity/style/speaker boost/seed, `enforce_language`, `output_format` mp3/wav, `text_normalization`; DeepDub accent/variance/tempo, MiniMax pitch/volume/intensity/timbre), plus `audio_effect` (phone/radio/megaphone/small_room/hall/distant) + `audio_effect_strength` for any voice at no extra credits. Status returns the same fields for reuse. |
|
|
151
151
|
| `generate_sound` | Text → sound effect. Duration, prompt influence, and per-provider controls (Stable Audio guidance, Kie loop/tempo/key, Seed-Audio voice/speed/volume/pitch + reference audio/image) |
|
|
152
152
|
| `generate_3d` | Text or reference images → 3D model (GLB/FBX/OBJ/USDZ) |
|
|
153
153
|
| `transcribe_audio` | Audio/video URL or file → text + SRT subtitles. Language, speaker diarization, audio-event tagging, and SRT formatting (words/line, lines/subtitle, caption stretch) |
|
package/package.json
CHANGED
|
@@ -230,6 +230,47 @@ function modelLabel(sc) {
|
|
|
230
230
|
}
|
|
231
231
|
function voiceLabel(sc) { return sc.voice_name || sc.voice || (sc.settings || {}).voice; }
|
|
232
232
|
|
|
233
|
+
// generate_speech controls. What the API reports it APPLIED wins: \`speech\`
|
|
234
|
+
// (status / completed payload; a key there is authoritative even when null),
|
|
235
|
+
// then the raw status result's own fields, then what the caller submitted.
|
|
236
|
+
var SPEECH_KEYS = ['eleven_model', 'turbo', 'speaking_speed', 'stability', 'similarity_boost', 'enforce_language',
|
|
237
|
+
'output_format', 'audio_effect', 'audio_effect_strength', 'seed'];
|
|
238
|
+
var SPEECH_MODELS = { eleven_v4: 'V4', eleven_v3: 'V3', eleven_multilingual_v2: 'V2' };
|
|
239
|
+
var SPEECH_FORMATS = { mp3_44100_128: 'MP3 128', mp3_44100_192: 'MP3 192', wav_44100: 'WAV' };
|
|
240
|
+
function withSpeech(settings, a) {
|
|
241
|
+
SPEECH_KEYS.forEach(function (k) { if (a && a[k] != null) settings[k] = a[k]; });
|
|
242
|
+
return settings;
|
|
243
|
+
}
|
|
244
|
+
function speechVal(sc, k) {
|
|
245
|
+
if (sc.speech && Object.prototype.hasOwnProperty.call(sc.speech, k)) return sc.speech[k];
|
|
246
|
+
var vs = sc.voice_settings || {};
|
|
247
|
+
if (vs[k] != null) return vs[k];
|
|
248
|
+
if (sc[k] != null) return sc[k];
|
|
249
|
+
return (sc.settings || {})[k];
|
|
250
|
+
}
|
|
251
|
+
function num(v) { return String(Math.round(Number(v) * 100) / 100); }
|
|
252
|
+
function speechChipsHTML(sc) {
|
|
253
|
+
if (sc.tool !== 'generate_speech' && !sc.speech) return '';
|
|
254
|
+
var h = '', v;
|
|
255
|
+
v = speechVal(sc, 'eleven_model'); if (v) h += chip('Model ' + esc(SPEECH_MODELS[v] || v));
|
|
256
|
+
if (speechVal(sc, 'turbo') === true) h += chip('Turbo');
|
|
257
|
+
v = speechVal(sc, 'speaking_speed'); if (v != null) h += chip('Speed ' + esc(num(v)) + '×');
|
|
258
|
+
v = speechVal(sc, 'stability'); if (v != null) h += chip('Stability ' + esc(num(v)));
|
|
259
|
+
v = speechVal(sc, 'similarity_boost'); if (v != null) h += chip('Similarity ' + esc(num(v)));
|
|
260
|
+
v = speechVal(sc, 'enforce_language');
|
|
261
|
+
h += chip('Language ' + (v ? esc(String(v).toUpperCase()) : 'Auto'));
|
|
262
|
+
v = speechVal(sc, 'output_format'); if (v) h += chip(esc(SPEECH_FORMATS[v] || v));
|
|
263
|
+
v = speechVal(sc, 'audio_effect');
|
|
264
|
+
if (v && v !== 'none') {
|
|
265
|
+
var strength = speechVal(sc, 'audio_effect_strength');
|
|
266
|
+
var name = String(v).replace(/_/g, ' ');
|
|
267
|
+
h += chip(esc(name.charAt(0).toUpperCase() + name.slice(1)) +
|
|
268
|
+
(strength != null && Number(strength) < 1 ? ' ' + Math.round(Number(strength) * 100) + '%' : ''));
|
|
269
|
+
}
|
|
270
|
+
v = speechVal(sc, 'seed'); if (v != null) h += chip('Seed ' + esc(String(v)));
|
|
271
|
+
return h;
|
|
272
|
+
}
|
|
273
|
+
|
|
233
274
|
// @VisualDNA / #Moodboard mentions are the tag syntax the server resolves into
|
|
234
275
|
// real reference assets — rendering them as flat prose hid the single most
|
|
235
276
|
// consequential part of the prompt. Escape FIRST, then wrap: the pattern only
|
|
@@ -340,6 +381,7 @@ function renderChips(sc) {
|
|
|
340
381
|
: ICONS.mic;
|
|
341
382
|
h += chip(face + ' ' + esc(voice));
|
|
342
383
|
}
|
|
384
|
+
h += speechChipsHTML(sc);
|
|
343
385
|
if (s.mode) h += chip(esc(editLabel(s.mode)));
|
|
344
386
|
if (Array.isArray(s.details)) s.details.forEach(function (d) { if (d) h += chip(esc(String(d))); });
|
|
345
387
|
if (many && !kind) h += chip(sc.count + ' items');
|
|
@@ -1358,7 +1400,7 @@ function preRefSc(toolName, a) {
|
|
|
1358
1400
|
reference_videos: vid,
|
|
1359
1401
|
reference_audio: aud,
|
|
1360
1402
|
local_references: local,
|
|
1361
|
-
settings: {
|
|
1403
|
+
settings: withSpeech({
|
|
1362
1404
|
duration: a.duration,
|
|
1363
1405
|
resolution: a.draft === true ? '480p-draft' : a.draft === false ? String(a.resolution || '').replace(/-draft$/i, '') : a.resolution,
|
|
1364
1406
|
aspect_ratio: a.aspect_ratio,
|
|
@@ -1369,7 +1411,7 @@ function preRefSc(toolName, a) {
|
|
|
1369
1411
|
moodboard_ids: a.moodboard_ids,
|
|
1370
1412
|
moodboard_id: a.moodboard_id,
|
|
1371
1413
|
preset_id: a.preset_id
|
|
1372
|
-
}
|
|
1414
|
+
}, a)
|
|
1373
1415
|
};
|
|
1374
1416
|
}
|
|
1375
1417
|
|
|
@@ -1427,7 +1469,7 @@ function liveFromTimedOut(sc) {
|
|
|
1427
1469
|
kind: kindFromTool(originTool, sc),
|
|
1428
1470
|
prompt: originArgs.prompt || originArgs.text || '',
|
|
1429
1471
|
model: sc.model || originArgs.model,
|
|
1430
|
-
settings: {
|
|
1472
|
+
settings: withSpeech({
|
|
1431
1473
|
duration: originArgs.duration,
|
|
1432
1474
|
is_draft: originArgs.draft,
|
|
1433
1475
|
resolution: originArgs.draft === true ? '480p-draft' : originArgs.draft === false ? String(originArgs.resolution || '').replace(/-draft$/i, '') : originArgs.resolution,
|
|
@@ -1436,7 +1478,7 @@ function liveFromTimedOut(sc) {
|
|
|
1436
1478
|
mode: originArgs.operation,
|
|
1437
1479
|
visual_dna_ids: originArgs.visual_dna_ids,
|
|
1438
1480
|
moodboard_id: originArgs.moodboard_id
|
|
1439
|
-
},
|
|
1481
|
+
}, originArgs),
|
|
1440
1482
|
count: ids ? ids.length : (originArgs.num_images || 1),
|
|
1441
1483
|
generation_id: sc.generation_id,
|
|
1442
1484
|
poll_tool: 'get_generation_status',
|
|
@@ -1457,14 +1499,14 @@ function completedFromPlain(sc) {
|
|
|
1457
1499
|
kind: kindFromTool(originTool, sc),
|
|
1458
1500
|
prompt: originArgs.prompt || originArgs.text || sc.prompt_used || '',
|
|
1459
1501
|
model: sc.model || originArgs.model,
|
|
1460
|
-
settings: {
|
|
1502
|
+
settings: withSpeech({
|
|
1461
1503
|
duration: sc.duration || originArgs.duration,
|
|
1462
1504
|
is_draft: originArgs.draft,
|
|
1463
1505
|
resolution: originArgs.draft === true ? '480p-draft' : originArgs.draft === false ? String(originArgs.resolution || '').replace(/-draft$/i, '') : originArgs.resolution,
|
|
1464
1506
|
aspect_ratio: originArgs.aspect_ratio,
|
|
1465
1507
|
quality: originArgs.quality,
|
|
1466
1508
|
mode: originArgs.operation
|
|
1467
|
-
},
|
|
1509
|
+
}, originArgs),
|
|
1468
1510
|
urls: sc.urls || [],
|
|
1469
1511
|
session_id: sc.session_id || originArgs.session_id,
|
|
1470
1512
|
project_id: sc.project_id || originArgs.project_id,
|
package/src/tools/_shared.js
CHANGED
|
@@ -1066,6 +1066,10 @@ async function uiCompleted(p, textPayload, extraContent) {
|
|
|
1066
1066
|
// voice's face. Exactly the "never show a raw id on a card" rule, broken on
|
|
1067
1067
|
// the one path the user actually ends up looking at.
|
|
1068
1068
|
...(p.voice ? { voice_name: p.voice.name, voice_thumbnail: p.voice.thumbnail } : {}),
|
|
1069
|
+
// Speech settings the API reports it applied (generate.js speechFromResult,
|
|
1070
|
+
// incl. eleven_model); passed through whole.
|
|
1071
|
+
// the card prefers them over the submitted `settings`.
|
|
1072
|
+
...(p.speech ? { speech: p.speech } : {}),
|
|
1069
1073
|
// The RAW generation state, when the caller has one. `phase` above is
|
|
1070
1074
|
// hardcoded 'completed' — it means "this tool call finished", not "the
|
|
1071
1075
|
// generation finished" — so a status check on a still-running job looked
|
package/src/tools/generate.js
CHANGED
|
@@ -151,6 +151,24 @@ function mediaKind(url) {
|
|
|
151
151
|
return 'image';
|
|
152
152
|
}
|
|
153
153
|
|
|
154
|
+
// The speech settings the API says it APPLIED (status result, kolbo-api
|
|
155
|
+
// sdk/controller.js extractResult). Keys are always present (null = not
|
|
156
|
+
// applied) so the card prefers these over what the caller asked for; only a
|
|
157
|
+
// speech result carries `enforce_language`, so every other result returns
|
|
158
|
+
// undefined and its card is untouched.
|
|
159
|
+
function speechFromResult(r) {
|
|
160
|
+
if (!r || typeof r !== 'object' || !Object.prototype.hasOwnProperty.call(r, 'enforce_language')) return undefined;
|
|
161
|
+
const vs = r.voice_settings || {};
|
|
162
|
+
const out = {
|
|
163
|
+
stability: vs.stability, similarity_boost: vs.similarity_boost, style: vs.style, use_speaker_boost: vs.use_speaker_boost,
|
|
164
|
+
speaking_speed: r.speaking_speed, enforce_language: r.enforce_language, output_format: r.output_format,
|
|
165
|
+
text_normalization: r.text_normalization, audio_effect: r.audio_effect,
|
|
166
|
+
audio_effect_strength: r.audio_effect_strength, seed: r.seed, eleven_model: r.eleven_model,
|
|
167
|
+
};
|
|
168
|
+
for (const k of Object.keys(out)) if (out[k] === undefined) out[k] = null;
|
|
169
|
+
return out;
|
|
170
|
+
}
|
|
171
|
+
|
|
154
172
|
function preferOwned(urls) {
|
|
155
173
|
const list = (urls || []).filter((item) => typeof item === 'string' && item);
|
|
156
174
|
const ours = list.filter(ownedUrl);
|
|
@@ -1082,8 +1100,9 @@ function registerGenerateTools(server, client, options = {}) {
|
|
|
1082
1100
|
{
|
|
1083
1101
|
text: z.string().describe('The text to convert to speech'),
|
|
1084
1102
|
voice: z.string().optional().describe('Voice ID or display name — MUST come from a `list_voices` result, never constructed. Google/Gemini ids in particular are not validated provider-side: an id that is not in the catalog is silently mapped to another voice (or a default one) and the audio comes back in a voice nobody asked for. Do not pattern-match a locale onto an id you saw for another language. Default: "Rachel"'),
|
|
1085
|
-
model: z.string().optional().describe('Model identifier. Use list_models type="text_to_speech" to see options. Default: eleven_v4 (ElevenLabs V4). ElevenLabs V4/V3 voices follow inline audio tags in the text: delivery ([whispers], [shouting], [sarcastic]), reactions ([laughs], [sighs], [clears throat]), pauses ([pause], [long pause]) and, on V4, free-form directions like [Low, steady voice, restrained urgency]. Tags are always English, even in Hebrew text. SSML such as <break> is NOT supported.'),
|
|
1103
|
+
model: z.string().optional().describe('Model identifier. Use list_models type="text_to_speech" to see options. Default: eleven_v4 (ElevenLabs V4). To choose which ElevenLabs model speaks a given ElevenLabs voice (stock or a cloned voice), use `eleven_model` instead. ElevenLabs V4/V3 voices follow inline audio tags in the text: delivery ([whispers], [shouting], [sarcastic]), reactions ([laughs], [sighs], [clears throat]), pauses ([pause], [long pause]) and, on V4, free-form directions like [Low, steady voice, restrained urgency]. Tags are always English, even in Hebrew text. SSML such as <break> is NOT supported.'),
|
|
1086
1104
|
turbo: z.boolean().optional().describe('ElevenLabs V4 voices ONLY. Turbo: faster generation at half the credits, slightly lower quality. Rejected (TURBO_UNSUPPORTED) for any voice not on ElevenLabs V4. Default false.'),
|
|
1105
|
+
eleven_model: z.enum(['eleven_v4', 'eleven_v3', 'eleven_multilingual_v2']).optional().describe("ElevenLabs voices ONLY (stock voices and the user's own cloned/character ElevenLabs voices). Which ElevenLabs model speaks: eleven_v4 (default for new voices, most expressive, audio tags, Stability/Similarity/Turbo), eleven_v3 (audio tags), eleven_multilingual_v2 (no audio tags; supports `style`). Omit = the voice's own default. Same price for all. Rejected with 400 ELEVEN_MODEL_UNSUPPORTED for non-ElevenLabs voices. `turbo` requires eleven_v4."),
|
|
1087
1106
|
language: z.string().optional().describe('Language / accent code (e.g., "en-US", "he-IL", "es-ES"). For Google/Gemini voices this is the Accent control (does not translate the text). Default: "en-US"'),
|
|
1088
1107
|
// ── Expressive style / emotion (provider-specific) ──
|
|
1089
1108
|
// Google/Gemini: prefer a named preset id from the Kolbo UI picker; free-form
|
|
@@ -1099,14 +1118,20 @@ function registerGenerateTools(server, client, options = {}) {
|
|
|
1099
1118
|
emotion: z.string().optional().describe('MiniMax / Cartesia voices. Emotion: happy, sad, angry, fearful, disgusted, surprised, calm, fluent, whisper. Prefer this OR selected_style (both map to the same delivery control).'),
|
|
1100
1119
|
speaking_speed: z.number().optional().describe('Speech speed 0.5 (slow) – 2.0 (fast); Cartesia clamped 0.6–1.5. Default 1.0. Applies to ElevenLabs / OpenAI / Google / MiniMax / Cartesia / DeepDub (as tempo when tempo omitted).'),
|
|
1101
1120
|
// ── ElevenLabs voice settings ──
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1121
|
+
stability: z.number().min(0).max(1).optional().describe('ElevenLabs Stability, 0–1. Default 0.5. Lower = more expressive and varied between takes (Creative); higher = steadier, more consistent delivery (Robust). Supported on V4.'),
|
|
1122
|
+
similarity_boost: z.number().optional().describe('ElevenLabs voice similarity, 0–1. Default 0.75. Higher hews closer to the original voice. Also applies to the user\'s own cloned/character ElevenLabs voices.'),
|
|
1123
|
+
style: z.number().optional().describe('ElevenLabs style exaggeration, 0–1. Default 0. Higher = more expressive/dramatic. V3/V2 voices only — ElevenLabs V4 ignores it (use stability or inline audio tags instead).'),
|
|
1124
|
+
use_speaker_boost: z.boolean().optional().describe('ElevenLabs speaker boost (presence/clarity). Default true.'),
|
|
1125
|
+
enforce_language: z.string().optional().describe('ElevenLabs voices ONLY. Force the spoken language with an ISO 639-1 code ("he", "en", "fr"; a locale like "he-IL" is also accepted). Omit (recommended) and ElevenLabs auto-detects the language from the text. Different from `language`, which stays the accent/locale control.'),
|
|
1126
|
+
output_format: z.enum(['mp3_44100_128', 'mp3_44100_192', 'wav_44100']).optional().describe('ElevenLabs voices ONLY. Audio file format: "mp3_44100_128" (default), "mp3_44100_192" (higher-bitrate MP3) or "wav_44100" (uncompressed; the result is a .wav file). ElevenLabs\' native render is delivered as is. Any other provider rejects it (OUTPUT_FORMAT_UNSUPPORTED).'),
|
|
1127
|
+
text_normalization: z.enum(['auto', 'on', 'off']).optional().describe('ElevenLabs voices. Spell out numbers, dates and abbreviations before speaking: "auto" (default), "on" (always), "off" (read as written).'),
|
|
1128
|
+
audio_effect: z.enum(['none', 'phone', 'radio', 'megaphone', 'small_room', 'hall', 'distant']).optional().describe('Kolbo post-processing effect applied to the finished voice: phone, radio, megaphone, small_room, hall, distant, or "none" (default). Works for ANY voice/provider, no extra credits.'),
|
|
1129
|
+
audio_effect_strength: z.number().min(0).max(1).optional().describe('Mix of audio_effect with the dry voice, 0–1. Default 1 (full effect). Ignored without audio_effect.'),
|
|
1105
1130
|
// ── DeepDub controls ──
|
|
1106
1131
|
variance: z.number().optional().describe('DeepDub voice variance, 0–1. Default 0.2. Higher = more takes/variation.'),
|
|
1107
1132
|
tempo: z.number().optional().describe('DeepDub tempo multiplier, 0–2. Default 1.0.'),
|
|
1108
1133
|
promptBoost: z.boolean().optional().describe('DeepDub prompt-fidelity boost. Default true.'),
|
|
1109
|
-
seed: z.number().optional().describe('Reproducibility seed (DeepDub / Zonos). Same seed + inputs → same output.'),
|
|
1134
|
+
seed: z.number().optional().describe('Reproducibility seed (ElevenLabs / DeepDub / Zonos). Same seed + inputs → same output. ElevenLabs: integer 0–4294967295, best-effort determinism (not guaranteed).'),
|
|
1110
1135
|
accentControl: z.object({
|
|
1111
1136
|
accentBaseLocale: z.string().describe('Base accent locale, e.g. "en-US".'),
|
|
1112
1137
|
accentLocale: z.string().describe('Target accent locale, e.g. "en-GB".'),
|
|
@@ -1121,7 +1146,7 @@ function registerGenerateTools(server, client, options = {}) {
|
|
|
1121
1146
|
project_id: projectIdField,
|
|
1122
1147
|
session_id: sessionIdField
|
|
1123
1148
|
},
|
|
1124
|
-
async ({ text, voice, model, turbo, language, style_instructions_preset_id, style_instructions, style_instructions_label, selected_style, emotion, speaking_speed, similarity_boost, style, use_speaker_boost, variance, tempo, promptBoost, seed, accentControl, voiceTitle, minimax_pitch, minimax_vol, minimax_intensity, minimax_timbre, project_id, session_id }) => {
|
|
1149
|
+
async ({ text, voice, model, eleven_model, turbo, language, style_instructions_preset_id, style_instructions, style_instructions_label, selected_style, emotion, speaking_speed, stability, similarity_boost, style, use_speaker_boost, enforce_language, output_format, text_normalization, audio_effect, audio_effect_strength, variance, tempo, promptBoost, seed, accentControl, voiceTitle, minimax_pitch, minimax_vol, minimax_intensity, minimax_timbre, project_id, session_id }) => {
|
|
1125
1150
|
model = await canonicalModelId(client, model, 'text_to_speech'); // lenient id resolution ("z-image" → "z-image/turbo")
|
|
1126
1151
|
// Resolve the requested voice against the REAL catalog (cached) so the card
|
|
1127
1152
|
// can show its display name + portrait instead of a raw id, and so an id
|
|
@@ -1133,11 +1158,14 @@ function registerGenerateTools(server, client, options = {}) {
|
|
|
1133
1158
|
const unknownVoice = voice && !voiceRecord && !/^custom_/i.test(voice)
|
|
1134
1159
|
? `Voice "${voice}" is not in the Kolbo voice catalog. Call list_voices and pass a voice_id it returns — an unrecognised id is NOT rejected, it is silently mapped to a different voice, so the audio will not be the voice you named.`
|
|
1135
1160
|
: null;
|
|
1161
|
+
// ElevenLabs / effect controls carried on the card (undefined keys drop out of the JSON).
|
|
1162
|
+
const ttsControls = { eleven_model, turbo, stability, similarity_boost, style, use_speaker_boost, enforce_language, output_format, text_normalization, audio_effect, audio_effect_strength, seed };
|
|
1136
1163
|
const gen = await client.post('/v1/generate/speech', {
|
|
1137
|
-
text, voice, model, turbo, language,
|
|
1164
|
+
text, voice, model, eleven_model, turbo, language,
|
|
1138
1165
|
style_instructions_preset_id, style_instructions, style_instructions_label,
|
|
1139
1166
|
selected_style, emotion, speaking_speed,
|
|
1140
|
-
similarity_boost, style, use_speaker_boost,
|
|
1167
|
+
stability, similarity_boost, style, use_speaker_boost,
|
|
1168
|
+
enforce_language, output_format, text_normalization, audio_effect, audio_effect_strength,
|
|
1141
1169
|
variance, tempo, promptBoost, seed, accentControl, voiceTitle,
|
|
1142
1170
|
minimax_pitch, minimax_vol, minimax_intensity, minimax_timbre,
|
|
1143
1171
|
project_id, session_id
|
|
@@ -1151,6 +1179,7 @@ function registerGenerateTools(server, client, options = {}) {
|
|
|
1151
1179
|
style: selected_style || emotion || style_instructions_preset_id || style_instructions,
|
|
1152
1180
|
speaking_speed,
|
|
1153
1181
|
language,
|
|
1182
|
+
...ttsControls,
|
|
1154
1183
|
},
|
|
1155
1184
|
warning: unknownVoice
|
|
1156
1185
|
});
|
|
@@ -1178,7 +1207,9 @@ function registerGenerateTools(server, client, options = {}) {
|
|
|
1178
1207
|
style: selected_style || emotion || style_instructions_preset_id || style_instructions,
|
|
1179
1208
|
speaking_speed,
|
|
1180
1209
|
language,
|
|
1210
|
+
...ttsControls,
|
|
1181
1211
|
},
|
|
1212
|
+
speech: speechFromResult(result.result),
|
|
1182
1213
|
urls: result.result.urls,
|
|
1183
1214
|
playback_urls: result.result.playback_urls,
|
|
1184
1215
|
duration: result.result.duration,
|
|
@@ -1420,6 +1451,7 @@ function registerGenerateTools(server, client, options = {}) {
|
|
|
1420
1451
|
txt_url: res.txt_url || undefined,
|
|
1421
1452
|
audio_url: res.audio_url || undefined,
|
|
1422
1453
|
prompt: res.prompt_used || res.prompt || undefined,
|
|
1454
|
+
speech: speechFromResult(res),
|
|
1423
1455
|
credits_used: creditFields(single).credits_used,
|
|
1424
1456
|
items: [{
|
|
1425
1457
|
id: single.generation_id,
|