feat(voice): bracketed emotion tags, [잡음] for noise, spoken emotion, concise replies
- Brain persona now prefixes every reply with one bracketed emotion tag (e.g. [반가움], [궁금]) and keeps replies to one or two short sentences. - Empty/unrecognised audio (silence/noise) is reported as reply "[잡음]" with no TTS playback instead of an empty reply. - TTS speaks the bracketed emotion too: "[힘차게] 안녕!" is synthesised as "힘차게, 안녕!" via a leading-tag -> spoken-word transform. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
@@ -18,6 +18,7 @@ from __future__ import annotations
|
||||
import json
|
||||
import logging
|
||||
import queue
|
||||
import re
|
||||
import threading
|
||||
from http.server import BaseHTTPRequestHandler, ThreadingHTTPServer
|
||||
|
||||
@@ -25,6 +26,21 @@ from .monitor import Monitor
|
||||
|
||||
log = logging.getLogger("wsai.dashboard")
|
||||
|
||||
_EMOTION_RE = re.compile(r"^\s*\[([^\]]+)\]\s*(.*)", re.S)
|
||||
|
||||
|
||||
def _speech_text(reply: str) -> str:
|
||||
"""Turn a reply like ``[힘차게] 안녕!`` into what the TTS should actually say.
|
||||
|
||||
The bracketed emotion is spoken too (per user request), so the leading tag
|
||||
becomes a natural spoken word: ``[힘차게] 안녕!`` -> ``힘차게, 안녕!``. Replies
|
||||
without a tag are spoken as-is."""
|
||||
m = _EMOTION_RE.match(reply or "")
|
||||
if not m:
|
||||
return reply
|
||||
emotion, rest = m.group(1).strip(), m.group(2).strip()
|
||||
return f"{emotion}, {rest}" if rest else emotion
|
||||
|
||||
|
||||
def _make_handler(dash: "Dashboard"):
|
||||
monitor = dash.monitor
|
||||
@@ -259,12 +275,14 @@ class Dashboard:
|
||||
heard = (self._submit(self.stt.transcribe(wav)) or "").strip()
|
||||
turn.heard(heard or "(빈 결과)")
|
||||
if not heard:
|
||||
# Nothing recognised (silence/noise): skip the turn, tell the bot.
|
||||
# Nothing recognised (silence/noise): mark it as [잡음] and skip
|
||||
# the brain/TTS so the bot plays nothing back.
|
||||
turn.replied("[잡음]")
|
||||
turn.finish()
|
||||
return {"heard": heard, "reply": "", "wav": b""}
|
||||
return {"heard": heard, "reply": "[잡음]", "wav": b""}
|
||||
reply_text = self._think(heard)
|
||||
turn.replied(reply_text)
|
||||
out_path = self._submit(self.tts.synth(reply_text))
|
||||
out_path = self._submit(self.tts.synth(_speech_text(reply_text)))
|
||||
with open(out_path, "rb") as f:
|
||||
reply_wav = f.read()
|
||||
ms = int((time.monotonic() - t0) * 1000)
|
||||
|
||||
Reference in New Issue
Block a user