#!/usr/bin/env python3 # Afinado de XTTS: combina varias referencias (promedia el timbre) y prueba # distintos ajustes de velocidad/temperatura para acercarse al Jarvis original. # Genera variantes en ref/afinar/ para comparar de oido y elegir la buena. import os, sys, time os.environ.setdefault("COQUI_TOS_AGREED", "1") DISP = sys.argv[1] if len(sys.argv) > 1 else "cuda" BASE = os.path.dirname(os.path.abspath(__file__)) OUT = os.path.join(BASE, "ref", "afinar") os.makedirs(OUT, exist_ok=True) # varias referencias: XTTS calcula el latent del hablante promediandolas REFS = [os.path.join(BASE, "ref", n) for n in ("jarvis_lento_b.wav", "jarvis_lento_a.wav", "jarvis_ref.wav")] REFS = [r for r in REFS if os.path.exists(r)] FRASES = { "saludo": "Buenas noches, señor. Todo está listo.", "pregunta": "He encontrado tres ficheros que coinciden. ¿Cuál abro?", } # (etiqueta, kwargs de inferencia) VARIANTES = [ ("v1_natural", dict(speed=1.0, temperature=0.65, repetition_penalty=2.0)), ("v2_sereno", dict(speed=0.92, temperature=0.60, repetition_penalty=3.0)), ("v3_grave", dict(speed=0.88, temperature=0.55, repetition_penalty=5.0)), ] print(f"referencias ({len(REFS)}): {[os.path.basename(r) for r in REFS]}", flush=True) t0 = time.time() from TTS.api import TTS tts = TTS("tts_models/multilingual/multi-dataset/xtts_v2").to(DISP) print(f"modelo cargado en {time.time()-t0:.1f}s", flush=True) for fid, frase in FRASES.items(): for etiqueta, kw in VARIANTES: dst = os.path.join(OUT, f"{fid}_{etiqueta}.wav") t0 = time.time() try: tts.tts_to_file(text=frase, speaker_wav=REFS, language="es", file_path=dst, **kw) print(f" {fid}/{etiqueta}: {time.time()-t0:4.1f}s {kw}", flush=True) except TypeError as e: # algun kwarg no soportado: reintenta solo con speed+temperature kw2 = {k: kw[k] for k in ("speed", "temperature") if k in kw} tts.tts_to_file(text=frase, speaker_wav=REFS, language="es", file_path=dst, **kw2) print(f" {fid}/{etiqueta}: (sin rep_penalty) {kw2}", flush=True) print("listo.", flush=True)