Files
Blind/assets/earcons/generate_cues.py
T
2026-09-11 19:47:15 +03:00

62 lines
2.7 KiB
Python

"""Генерация голосовых куи-файлов (готовые записи для мгновенного проигрыша).
Запускается ОДИН РАЗ при настройке (и при смене голоса/скорости в .env):
.venv/bin/python assets/earcons/generate_cues.py
Файлы — статичные wav: ассистент играет их мгновенно (без синтеза в реальном
времени), что даёт немедленное подтверждение «аудио-тракт жив». Если хочется
свои записи — просто положи свои wav с этими именами (генератор не перезапишет
существующие без флага --force).
"""
from __future__ import annotations
import asyncio
import sys
from pathlib import Path
import numpy as np
try:
from modules.tts import make_tts
from modules.brain.config import get_secret
except ImportError:
sys.path.insert(0, str(Path(__file__).resolve().parents[2]))
from modules.tts import make_tts
from modules.brain.config import get_secret
CUES_DIR = Path(__file__).resolve().parent
CUES = {
"dialog_start.wav": "Ассистент готов к диалогу.",
"dialog_end.wav": "Спасибо. До новых встреч!",
"error_network.wav": "Ошибка. Связь отсутствует. Проверьте интернет.",
"error_limit.wav": "Превышен лимит ответа. Попробуйте позже.",
"error_general.wav": "Произошла ошибка. Попробуйте ещё раз.",
"unclear_question.wav": "Ваш вопрос неразборчив. Повторите, пожалуйста, чуть громче и ближе к микрофону.",
}
def main() -> int:
force = "--force" in sys.argv
voice = get_secret("TTS_VOICE") or "ru-RU-SvetlanaNeural"
rate = get_secret("TTS_RATE") or "+15"
print(f"Голос: {voice}, темп: {rate}")
tts = make_tts() # edge (или текущий провайдер из .env)
for filename, text in CUES.items():
path = CUES_DIR / filename
if path.exists() and not force:
print(f" {filename}: уже есть, пропускаю (--force для перегенерации)")
continue
result = tts.synthesize(text)
import soundfile as sf
sf.write(str(path), result.audio, result.samplerate)
print(f" {filename}: готов ({result.duration_sec:.1f} c)")
print(f"\nФайлы в {CUES_DIR}")
return 0
if __name__ == "__main__":
sys.exit(main())