Spaces:
Running
Running
Add multilingual TTS voices: Thalita (pt-BR), Andrew, Jenny, Ela, Denise, Katja + _detect_voice_emotion for auto voice selection
Browse files
ai_ext.py
CHANGED
|
@@ -81,3 +81,62 @@ HEADERS = {
|
|
| 81 |
"Accept-Language": "vi-VN,vi;q=0.9,en;q=0.8"
|
| 82 |
}
|
| 83 |
LAST_QWEN_ERROR = ""
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 81 |
"Accept-Language": "vi-VN,vi;q=0.9,en;q=0.8"
|
| 82 |
}
|
| 83 |
LAST_QWEN_ERROR = ""
|
| 84 |
+
|
| 85 |
+
# ===== MULTILINGUAL VOICES FOR TTS =====
|
| 86 |
+
MULTILINGUAL_VOICES = {
|
| 87 |
+
# Vietnamese
|
| 88 |
+
"vi_female": "vi-VN-HoaMyNeural",
|
| 89 |
+
"vi_male": "vi-VN-NamMinhNeural",
|
| 90 |
+
"hoaimy": "vi-VN-HoaMyNeural",
|
| 91 |
+
"namminh": "vi-VN-NamMinhNeural",
|
| 92 |
+
# Multilingual - Andrew (hỗ trợ tiếng Việt)
|
| 93 |
+
"en_andrew": "en-US-AndrewNeural",
|
| 94 |
+
"andrew": "en-US-AndrewNeural",
|
| 95 |
+
# Multilingual - Jenny
|
| 96 |
+
"en_jenny": "en-US-JennyNeural",
|
| 97 |
+
"jenny": "en-US-JennyNeural",
|
| 98 |
+
# Portuguese - Thalita Multilingual
|
| 99 |
+
"pt_thalita": "pt-BR-ThalitaMultilingualNeural",
|
| 100 |
+
"thalita": "pt-BR-ThalitaMultilingualNeural",
|
| 101 |
+
"pt_francisco": "pt-BR-FranciscoNeural",
|
| 102 |
+
# Spanish
|
| 103 |
+
"es_ela": "es-ES-ElaNeural",
|
| 104 |
+
"ela": "es-ES-ElaNeural",
|
| 105 |
+
"es_carlos": "es-ES-CarlosNeural",
|
| 106 |
+
# French
|
| 107 |
+
"fr_denise": "fr-FR-DeniseNeural",
|
| 108 |
+
"denise": "fr-FR-DeniseNeural",
|
| 109 |
+
# German
|
| 110 |
+
"de_katja": "de-DE-KatjaNeural",
|
| 111 |
+
"katja": "de-DE-KatjaNeural",
|
| 112 |
+
# Japanese
|
| 113 |
+
"ja_nanami": "ja-JP-NanamiNeural",
|
| 114 |
+
"nanami": "ja-JP-NanamiNeural",
|
| 115 |
+
# Korean
|
| 116 |
+
"ko_sunhee": "ko-KR-SunHeeNeural",
|
| 117 |
+
"sunhee": "ko-KR-SunHeeNeural",
|
| 118 |
+
# Chinese
|
| 119 |
+
"zh_xiaochen": "zh-CN-XiaochenNeural",
|
| 120 |
+
"xiaochen": "zh-CN-XiaochenNeural",
|
| 121 |
+
}
|
| 122 |
+
|
| 123 |
+
def _detect_voice_emotion(title, text):
|
| 124 |
+
"""Detect appropriate voice and emotion based on content for multilingual TTS."""
|
| 125 |
+
content = ((title or "") + " " + (text or "")).lower()
|
| 126 |
+
|
| 127 |
+
# World Cup / Football content - use Andrew multilingual
|
| 128 |
+
if any(kw in content for kw in ["world cup", "wc 2026", "fifa", "bóng đá", "trận đấu", "bóng bóng", "đội tuyển", "cầu thủ"]):
|
| 129 |
+
return ("andrew", "excited") # Andrew multilingual hỗ trợ tiếng Việt
|
| 130 |
+
|
| 131 |
+
# News categories - choose appropriate voice
|
| 132 |
+
if any(kw in content for kw in ["kinh tế", "tài chính", "thị trường", "economics", "finance"]):
|
| 133 |
+
return ("jenny", "calm")
|
| 134 |
+
if any(kw in content for kw in ["thiên tai", "bão", "lũ lụt", "cháy nổ", "tai nạn", "disaster", "accident"]):
|
| 135 |
+
return ("thalita", "serious") # Portuguese multilingual
|
| 136 |
+
if any(kw in content for kw in ["giải trí", "showbiz", "entertainment", "hài hước"]):
|
| 137 |
+
return ("ela", "happy")
|
| 138 |
+
if any(kw in content for kw in ["công nghệ", "tech", "technology", "ai", "trí tuệ nhân tạo"]):
|
| 139 |
+
return ("katja", "excited")
|
| 140 |
+
|
| 141 |
+
# Default Vietnamese
|
| 142 |
+
return ("hoaimy", "trung_tinh")
|