mirror of
https://github.com/harry0703/MoneyPrinterTurbo.git
synced 2026-02-21 16:37:21 +08:00
1173 lines
23 KiB
Python
1173 lines
23 KiB
Python
import asyncio
|
||
import os
|
||
import re
|
||
from xml.sax.saxutils import unescape
|
||
from edge_tts.submaker import mktimestamp
|
||
from loguru import logger
|
||
from edge_tts import submaker, SubMaker
|
||
import edge_tts
|
||
from moviepy.video.tools import subtitles
|
||
|
||
from app.utils import utils
|
||
|
||
|
||
def get_all_voices(filter_locals=None) -> list[str]:
|
||
if filter_locals is None:
|
||
filter_locals = ["zh-CN", "en-US", "zh-HK", "zh-TW"]
|
||
voices_str = """
|
||
Name: af-ZA-AdriNeural
|
||
Gender: Female
|
||
|
||
Name: af-ZA-WillemNeural
|
||
Gender: Male
|
||
|
||
Name: am-ET-AmehaNeural
|
||
Gender: Male
|
||
|
||
Name: am-ET-MekdesNeural
|
||
Gender: Female
|
||
|
||
Name: ar-AE-FatimaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-AE-HamdanNeural
|
||
Gender: Male
|
||
|
||
Name: ar-BH-AliNeural
|
||
Gender: Male
|
||
|
||
Name: ar-BH-LailaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-DZ-AminaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-DZ-IsmaelNeural
|
||
Gender: Male
|
||
|
||
Name: ar-EG-SalmaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-EG-ShakirNeural
|
||
Gender: Male
|
||
|
||
Name: ar-IQ-BasselNeural
|
||
Gender: Male
|
||
|
||
Name: ar-IQ-RanaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-JO-SanaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-JO-TaimNeural
|
||
Gender: Male
|
||
|
||
Name: ar-KW-FahedNeural
|
||
Gender: Male
|
||
|
||
Name: ar-KW-NouraNeural
|
||
Gender: Female
|
||
|
||
Name: ar-LB-LaylaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-LB-RamiNeural
|
||
Gender: Male
|
||
|
||
Name: ar-LY-ImanNeural
|
||
Gender: Female
|
||
|
||
Name: ar-LY-OmarNeural
|
||
Gender: Male
|
||
|
||
Name: ar-MA-JamalNeural
|
||
Gender: Male
|
||
|
||
Name: ar-MA-MounaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-OM-AbdullahNeural
|
||
Gender: Male
|
||
|
||
Name: ar-OM-AyshaNeural
|
||
Gender: Female
|
||
|
||
Name: ar-QA-AmalNeural
|
||
Gender: Female
|
||
|
||
Name: ar-QA-MoazNeural
|
||
Gender: Male
|
||
|
||
Name: ar-SA-HamedNeural
|
||
Gender: Male
|
||
|
||
Name: ar-SA-ZariyahNeural
|
||
Gender: Female
|
||
|
||
Name: ar-SY-AmanyNeural
|
||
Gender: Female
|
||
|
||
Name: ar-SY-LaithNeural
|
||
Gender: Male
|
||
|
||
Name: ar-TN-HediNeural
|
||
Gender: Male
|
||
|
||
Name: ar-TN-ReemNeural
|
||
Gender: Female
|
||
|
||
Name: ar-YE-MaryamNeural
|
||
Gender: Female
|
||
|
||
Name: ar-YE-SalehNeural
|
||
Gender: Male
|
||
|
||
Name: az-AZ-BabekNeural
|
||
Gender: Male
|
||
|
||
Name: az-AZ-BanuNeural
|
||
Gender: Female
|
||
|
||
Name: bg-BG-BorislavNeural
|
||
Gender: Male
|
||
|
||
Name: bg-BG-KalinaNeural
|
||
Gender: Female
|
||
|
||
Name: bn-BD-NabanitaNeural
|
||
Gender: Female
|
||
|
||
Name: bn-BD-PradeepNeural
|
||
Gender: Male
|
||
|
||
Name: bn-IN-BashkarNeural
|
||
Gender: Male
|
||
|
||
Name: bn-IN-TanishaaNeural
|
||
Gender: Female
|
||
|
||
Name: bs-BA-GoranNeural
|
||
Gender: Male
|
||
|
||
Name: bs-BA-VesnaNeural
|
||
Gender: Female
|
||
|
||
Name: ca-ES-EnricNeural
|
||
Gender: Male
|
||
|
||
Name: ca-ES-JoanaNeural
|
||
Gender: Female
|
||
|
||
Name: cs-CZ-AntoninNeural
|
||
Gender: Male
|
||
|
||
Name: cs-CZ-VlastaNeural
|
||
Gender: Female
|
||
|
||
Name: cy-GB-AledNeural
|
||
Gender: Male
|
||
|
||
Name: cy-GB-NiaNeural
|
||
Gender: Female
|
||
|
||
Name: da-DK-ChristelNeural
|
||
Gender: Female
|
||
|
||
Name: da-DK-JeppeNeural
|
||
Gender: Male
|
||
|
||
Name: de-AT-IngridNeural
|
||
Gender: Female
|
||
|
||
Name: de-AT-JonasNeural
|
||
Gender: Male
|
||
|
||
Name: de-CH-JanNeural
|
||
Gender: Male
|
||
|
||
Name: de-CH-LeniNeural
|
||
Gender: Female
|
||
|
||
Name: de-DE-AmalaNeural
|
||
Gender: Female
|
||
|
||
Name: de-DE-ConradNeural
|
||
Gender: Male
|
||
|
||
Name: de-DE-FlorianMultilingualNeural
|
||
Gender: Male
|
||
|
||
Name: de-DE-KatjaNeural
|
||
Gender: Female
|
||
|
||
Name: de-DE-KillianNeural
|
||
Gender: Male
|
||
|
||
Name: de-DE-SeraphinaMultilingualNeural
|
||
Gender: Female
|
||
|
||
Name: el-GR-AthinaNeural
|
||
Gender: Female
|
||
|
||
Name: el-GR-NestorasNeural
|
||
Gender: Male
|
||
|
||
Name: en-AU-NatashaNeural
|
||
Gender: Female
|
||
|
||
Name: en-AU-WilliamNeural
|
||
Gender: Male
|
||
|
||
Name: en-CA-ClaraNeural
|
||
Gender: Female
|
||
|
||
Name: en-CA-LiamNeural
|
||
Gender: Male
|
||
|
||
Name: en-GB-LibbyNeural
|
||
Gender: Female
|
||
|
||
Name: en-GB-MaisieNeural
|
||
Gender: Female
|
||
|
||
Name: en-GB-RyanNeural
|
||
Gender: Male
|
||
|
||
Name: en-GB-SoniaNeural
|
||
Gender: Female
|
||
|
||
Name: en-GB-ThomasNeural
|
||
Gender: Male
|
||
|
||
Name: en-HK-SamNeural
|
||
Gender: Male
|
||
|
||
Name: en-HK-YanNeural
|
||
Gender: Female
|
||
|
||
Name: en-IE-ConnorNeural
|
||
Gender: Male
|
||
|
||
Name: en-IE-EmilyNeural
|
||
Gender: Female
|
||
|
||
Name: en-IN-NeerjaExpressiveNeural
|
||
Gender: Female
|
||
|
||
Name: en-IN-NeerjaNeural
|
||
Gender: Female
|
||
|
||
Name: en-IN-PrabhatNeural
|
||
Gender: Male
|
||
|
||
Name: en-KE-AsiliaNeural
|
||
Gender: Female
|
||
|
||
Name: en-KE-ChilembaNeural
|
||
Gender: Male
|
||
|
||
Name: en-NG-AbeoNeural
|
||
Gender: Male
|
||
|
||
Name: en-NG-EzinneNeural
|
||
Gender: Female
|
||
|
||
Name: en-NZ-MitchellNeural
|
||
Gender: Male
|
||
|
||
Name: en-NZ-MollyNeural
|
||
Gender: Female
|
||
|
||
Name: en-PH-JamesNeural
|
||
Gender: Male
|
||
|
||
Name: en-PH-RosaNeural
|
||
Gender: Female
|
||
|
||
Name: en-SG-LunaNeural
|
||
Gender: Female
|
||
|
||
Name: en-SG-WayneNeural
|
||
Gender: Male
|
||
|
||
Name: en-TZ-ElimuNeural
|
||
Gender: Male
|
||
|
||
Name: en-TZ-ImaniNeural
|
||
Gender: Female
|
||
|
||
Name: en-US-AnaNeural
|
||
Gender: Female
|
||
|
||
Name: en-US-AndrewNeural
|
||
Gender: Male
|
||
|
||
Name: en-US-AriaNeural
|
||
Gender: Female
|
||
|
||
Name: en-US-AvaNeural
|
||
Gender: Female
|
||
|
||
Name: en-US-BrianNeural
|
||
Gender: Male
|
||
|
||
Name: en-US-ChristopherNeural
|
||
Gender: Male
|
||
|
||
Name: en-US-EmmaNeural
|
||
Gender: Female
|
||
|
||
Name: en-US-EricNeural
|
||
Gender: Male
|
||
|
||
Name: en-US-GuyNeural
|
||
Gender: Male
|
||
|
||
Name: en-US-JennyNeural
|
||
Gender: Female
|
||
|
||
Name: en-US-MichelleNeural
|
||
Gender: Female
|
||
|
||
Name: en-US-RogerNeural
|
||
Gender: Male
|
||
|
||
Name: en-US-SteffanNeural
|
||
Gender: Male
|
||
|
||
Name: en-ZA-LeahNeural
|
||
Gender: Female
|
||
|
||
Name: en-ZA-LukeNeural
|
||
Gender: Male
|
||
|
||
Name: es-AR-ElenaNeural
|
||
Gender: Female
|
||
|
||
Name: es-AR-TomasNeural
|
||
Gender: Male
|
||
|
||
Name: es-BO-MarceloNeural
|
||
Gender: Male
|
||
|
||
Name: es-BO-SofiaNeural
|
||
Gender: Female
|
||
|
||
Name: es-CL-CatalinaNeural
|
||
Gender: Female
|
||
|
||
Name: es-CL-LorenzoNeural
|
||
Gender: Male
|
||
|
||
Name: es-CO-GonzaloNeural
|
||
Gender: Male
|
||
|
||
Name: es-CO-SalomeNeural
|
||
Gender: Female
|
||
|
||
Name: es-CR-JuanNeural
|
||
Gender: Male
|
||
|
||
Name: es-CR-MariaNeural
|
||
Gender: Female
|
||
|
||
Name: es-CU-BelkysNeural
|
||
Gender: Female
|
||
|
||
Name: es-CU-ManuelNeural
|
||
Gender: Male
|
||
|
||
Name: es-DO-EmilioNeural
|
||
Gender: Male
|
||
|
||
Name: es-DO-RamonaNeural
|
||
Gender: Female
|
||
|
||
Name: es-EC-AndreaNeural
|
||
Gender: Female
|
||
|
||
Name: es-EC-LuisNeural
|
||
Gender: Male
|
||
|
||
Name: es-ES-AlvaroNeural
|
||
Gender: Male
|
||
|
||
Name: es-ES-ElviraNeural
|
||
Gender: Female
|
||
|
||
Name: es-ES-XimenaNeural
|
||
Gender: Female
|
||
|
||
Name: es-GQ-JavierNeural
|
||
Gender: Male
|
||
|
||
Name: es-GQ-TeresaNeural
|
||
Gender: Female
|
||
|
||
Name: es-GT-AndresNeural
|
||
Gender: Male
|
||
|
||
Name: es-GT-MartaNeural
|
||
Gender: Female
|
||
|
||
Name: es-HN-CarlosNeural
|
||
Gender: Male
|
||
|
||
Name: es-HN-KarlaNeural
|
||
Gender: Female
|
||
|
||
Name: es-MX-DaliaNeural
|
||
Gender: Female
|
||
|
||
Name: es-MX-JorgeNeural
|
||
Gender: Male
|
||
|
||
Name: es-NI-FedericoNeural
|
||
Gender: Male
|
||
|
||
Name: es-NI-YolandaNeural
|
||
Gender: Female
|
||
|
||
Name: es-PA-MargaritaNeural
|
||
Gender: Female
|
||
|
||
Name: es-PA-RobertoNeural
|
||
Gender: Male
|
||
|
||
Name: es-PE-AlexNeural
|
||
Gender: Male
|
||
|
||
Name: es-PE-CamilaNeural
|
||
Gender: Female
|
||
|
||
Name: es-PR-KarinaNeural
|
||
Gender: Female
|
||
|
||
Name: es-PR-VictorNeural
|
||
Gender: Male
|
||
|
||
Name: es-PY-MarioNeural
|
||
Gender: Male
|
||
|
||
Name: es-PY-TaniaNeural
|
||
Gender: Female
|
||
|
||
Name: es-SV-LorenaNeural
|
||
Gender: Female
|
||
|
||
Name: es-SV-RodrigoNeural
|
||
Gender: Male
|
||
|
||
Name: es-US-AlonsoNeural
|
||
Gender: Male
|
||
|
||
Name: es-US-PalomaNeural
|
||
Gender: Female
|
||
|
||
Name: es-UY-MateoNeural
|
||
Gender: Male
|
||
|
||
Name: es-UY-ValentinaNeural
|
||
Gender: Female
|
||
|
||
Name: es-VE-PaolaNeural
|
||
Gender: Female
|
||
|
||
Name: es-VE-SebastianNeural
|
||
Gender: Male
|
||
|
||
Name: et-EE-AnuNeural
|
||
Gender: Female
|
||
|
||
Name: et-EE-KertNeural
|
||
Gender: Male
|
||
|
||
Name: fa-IR-DilaraNeural
|
||
Gender: Female
|
||
|
||
Name: fa-IR-FaridNeural
|
||
Gender: Male
|
||
|
||
Name: fi-FI-HarriNeural
|
||
Gender: Male
|
||
|
||
Name: fi-FI-NooraNeural
|
||
Gender: Female
|
||
|
||
Name: fil-PH-AngeloNeural
|
||
Gender: Male
|
||
|
||
Name: fil-PH-BlessicaNeural
|
||
Gender: Female
|
||
|
||
Name: fr-BE-CharlineNeural
|
||
Gender: Female
|
||
|
||
Name: fr-BE-GerardNeural
|
||
Gender: Male
|
||
|
||
Name: fr-CA-AntoineNeural
|
||
Gender: Male
|
||
|
||
Name: fr-CA-JeanNeural
|
||
Gender: Male
|
||
|
||
Name: fr-CA-SylvieNeural
|
||
Gender: Female
|
||
|
||
Name: fr-CA-ThierryNeural
|
||
Gender: Male
|
||
|
||
Name: fr-CH-ArianeNeural
|
||
Gender: Female
|
||
|
||
Name: fr-CH-FabriceNeural
|
||
Gender: Male
|
||
|
||
Name: fr-FR-DeniseNeural
|
||
Gender: Female
|
||
|
||
Name: fr-FR-EloiseNeural
|
||
Gender: Female
|
||
|
||
Name: fr-FR-HenriNeural
|
||
Gender: Male
|
||
|
||
Name: fr-FR-RemyMultilingualNeural
|
||
Gender: Male
|
||
|
||
Name: fr-FR-VivienneMultilingualNeural
|
||
Gender: Female
|
||
|
||
Name: ga-IE-ColmNeural
|
||
Gender: Male
|
||
|
||
Name: ga-IE-OrlaNeural
|
||
Gender: Female
|
||
|
||
Name: gl-ES-RoiNeural
|
||
Gender: Male
|
||
|
||
Name: gl-ES-SabelaNeural
|
||
Gender: Female
|
||
|
||
Name: gu-IN-DhwaniNeural
|
||
Gender: Female
|
||
|
||
Name: gu-IN-NiranjanNeural
|
||
Gender: Male
|
||
|
||
Name: he-IL-AvriNeural
|
||
Gender: Male
|
||
|
||
Name: he-IL-HilaNeural
|
||
Gender: Female
|
||
|
||
Name: hi-IN-MadhurNeural
|
||
Gender: Male
|
||
|
||
Name: hi-IN-SwaraNeural
|
||
Gender: Female
|
||
|
||
Name: hr-HR-GabrijelaNeural
|
||
Gender: Female
|
||
|
||
Name: hr-HR-SreckoNeural
|
||
Gender: Male
|
||
|
||
Name: hu-HU-NoemiNeural
|
||
Gender: Female
|
||
|
||
Name: hu-HU-TamasNeural
|
||
Gender: Male
|
||
|
||
Name: id-ID-ArdiNeural
|
||
Gender: Male
|
||
|
||
Name: id-ID-GadisNeural
|
||
Gender: Female
|
||
|
||
Name: is-IS-GudrunNeural
|
||
Gender: Female
|
||
|
||
Name: is-IS-GunnarNeural
|
||
Gender: Male
|
||
|
||
Name: it-IT-DiegoNeural
|
||
Gender: Male
|
||
|
||
Name: it-IT-ElsaNeural
|
||
Gender: Female
|
||
|
||
Name: it-IT-GiuseppeNeural
|
||
Gender: Male
|
||
|
||
Name: it-IT-IsabellaNeural
|
||
Gender: Female
|
||
|
||
Name: ja-JP-KeitaNeural
|
||
Gender: Male
|
||
|
||
Name: ja-JP-NanamiNeural
|
||
Gender: Female
|
||
|
||
Name: jv-ID-DimasNeural
|
||
Gender: Male
|
||
|
||
Name: jv-ID-SitiNeural
|
||
Gender: Female
|
||
|
||
Name: ka-GE-EkaNeural
|
||
Gender: Female
|
||
|
||
Name: ka-GE-GiorgiNeural
|
||
Gender: Male
|
||
|
||
Name: kk-KZ-AigulNeural
|
||
Gender: Female
|
||
|
||
Name: kk-KZ-DauletNeural
|
||
Gender: Male
|
||
|
||
Name: km-KH-PisethNeural
|
||
Gender: Male
|
||
|
||
Name: km-KH-SreymomNeural
|
||
Gender: Female
|
||
|
||
Name: kn-IN-GaganNeural
|
||
Gender: Male
|
||
|
||
Name: kn-IN-SapnaNeural
|
||
Gender: Female
|
||
|
||
Name: ko-KR-HyunsuNeural
|
||
Gender: Male
|
||
|
||
Name: ko-KR-InJoonNeural
|
||
Gender: Male
|
||
|
||
Name: ko-KR-SunHiNeural
|
||
Gender: Female
|
||
|
||
Name: lo-LA-ChanthavongNeural
|
||
Gender: Male
|
||
|
||
Name: lo-LA-KeomanyNeural
|
||
Gender: Female
|
||
|
||
Name: lt-LT-LeonasNeural
|
||
Gender: Male
|
||
|
||
Name: lt-LT-OnaNeural
|
||
Gender: Female
|
||
|
||
Name: lv-LV-EveritaNeural
|
||
Gender: Female
|
||
|
||
Name: lv-LV-NilsNeural
|
||
Gender: Male
|
||
|
||
Name: mk-MK-AleksandarNeural
|
||
Gender: Male
|
||
|
||
Name: mk-MK-MarijaNeural
|
||
Gender: Female
|
||
|
||
Name: ml-IN-MidhunNeural
|
||
Gender: Male
|
||
|
||
Name: ml-IN-SobhanaNeural
|
||
Gender: Female
|
||
|
||
Name: mn-MN-BataaNeural
|
||
Gender: Male
|
||
|
||
Name: mn-MN-YesuiNeural
|
||
Gender: Female
|
||
|
||
Name: mr-IN-AarohiNeural
|
||
Gender: Female
|
||
|
||
Name: mr-IN-ManoharNeural
|
||
Gender: Male
|
||
|
||
Name: ms-MY-OsmanNeural
|
||
Gender: Male
|
||
|
||
Name: ms-MY-YasminNeural
|
||
Gender: Female
|
||
|
||
Name: mt-MT-GraceNeural
|
||
Gender: Female
|
||
|
||
Name: mt-MT-JosephNeural
|
||
Gender: Male
|
||
|
||
Name: my-MM-NilarNeural
|
||
Gender: Female
|
||
|
||
Name: my-MM-ThihaNeural
|
||
Gender: Male
|
||
|
||
Name: nb-NO-FinnNeural
|
||
Gender: Male
|
||
|
||
Name: nb-NO-PernilleNeural
|
||
Gender: Female
|
||
|
||
Name: ne-NP-HemkalaNeural
|
||
Gender: Female
|
||
|
||
Name: ne-NP-SagarNeural
|
||
Gender: Male
|
||
|
||
Name: nl-BE-ArnaudNeural
|
||
Gender: Male
|
||
|
||
Name: nl-BE-DenaNeural
|
||
Gender: Female
|
||
|
||
Name: nl-NL-ColetteNeural
|
||
Gender: Female
|
||
|
||
Name: nl-NL-FennaNeural
|
||
Gender: Female
|
||
|
||
Name: nl-NL-MaartenNeural
|
||
Gender: Male
|
||
|
||
Name: pl-PL-MarekNeural
|
||
Gender: Male
|
||
|
||
Name: pl-PL-ZofiaNeural
|
||
Gender: Female
|
||
|
||
Name: ps-AF-GulNawazNeural
|
||
Gender: Male
|
||
|
||
Name: ps-AF-LatifaNeural
|
||
Gender: Female
|
||
|
||
Name: pt-BR-AntonioNeural
|
||
Gender: Male
|
||
|
||
Name: pt-BR-FranciscaNeural
|
||
Gender: Female
|
||
|
||
Name: pt-BR-ThalitaNeural
|
||
Gender: Female
|
||
|
||
Name: pt-PT-DuarteNeural
|
||
Gender: Male
|
||
|
||
Name: pt-PT-RaquelNeural
|
||
Gender: Female
|
||
|
||
Name: ro-RO-AlinaNeural
|
||
Gender: Female
|
||
|
||
Name: ro-RO-EmilNeural
|
||
Gender: Male
|
||
|
||
Name: ru-RU-DmitryNeural
|
||
Gender: Male
|
||
|
||
Name: ru-RU-SvetlanaNeural
|
||
Gender: Female
|
||
|
||
Name: si-LK-SameeraNeural
|
||
Gender: Male
|
||
|
||
Name: si-LK-ThiliniNeural
|
||
Gender: Female
|
||
|
||
Name: sk-SK-LukasNeural
|
||
Gender: Male
|
||
|
||
Name: sk-SK-ViktoriaNeural
|
||
Gender: Female
|
||
|
||
Name: sl-SI-PetraNeural
|
||
Gender: Female
|
||
|
||
Name: sl-SI-RokNeural
|
||
Gender: Male
|
||
|
||
Name: so-SO-MuuseNeural
|
||
Gender: Male
|
||
|
||
Name: so-SO-UbaxNeural
|
||
Gender: Female
|
||
|
||
Name: sq-AL-AnilaNeural
|
||
Gender: Female
|
||
|
||
Name: sq-AL-IlirNeural
|
||
Gender: Male
|
||
|
||
Name: sr-RS-NicholasNeural
|
||
Gender: Male
|
||
|
||
Name: sr-RS-SophieNeural
|
||
Gender: Female
|
||
|
||
Name: su-ID-JajangNeural
|
||
Gender: Male
|
||
|
||
Name: su-ID-TutiNeural
|
||
Gender: Female
|
||
|
||
Name: sv-SE-MattiasNeural
|
||
Gender: Male
|
||
|
||
Name: sv-SE-SofieNeural
|
||
Gender: Female
|
||
|
||
Name: sw-KE-RafikiNeural
|
||
Gender: Male
|
||
|
||
Name: sw-KE-ZuriNeural
|
||
Gender: Female
|
||
|
||
Name: sw-TZ-DaudiNeural
|
||
Gender: Male
|
||
|
||
Name: sw-TZ-RehemaNeural
|
||
Gender: Female
|
||
|
||
Name: ta-IN-PallaviNeural
|
||
Gender: Female
|
||
|
||
Name: ta-IN-ValluvarNeural
|
||
Gender: Male
|
||
|
||
Name: ta-LK-KumarNeural
|
||
Gender: Male
|
||
|
||
Name: ta-LK-SaranyaNeural
|
||
Gender: Female
|
||
|
||
Name: ta-MY-KaniNeural
|
||
Gender: Female
|
||
|
||
Name: ta-MY-SuryaNeural
|
||
Gender: Male
|
||
|
||
Name: ta-SG-AnbuNeural
|
||
Gender: Male
|
||
|
||
Name: ta-SG-VenbaNeural
|
||
Gender: Female
|
||
|
||
Name: te-IN-MohanNeural
|
||
Gender: Male
|
||
|
||
Name: te-IN-ShrutiNeural
|
||
Gender: Female
|
||
|
||
Name: th-TH-NiwatNeural
|
||
Gender: Male
|
||
|
||
Name: th-TH-PremwadeeNeural
|
||
Gender: Female
|
||
|
||
Name: tr-TR-AhmetNeural
|
||
Gender: Male
|
||
|
||
Name: tr-TR-EmelNeural
|
||
Gender: Female
|
||
|
||
Name: uk-UA-OstapNeural
|
||
Gender: Male
|
||
|
||
Name: uk-UA-PolinaNeural
|
||
Gender: Female
|
||
|
||
Name: ur-IN-GulNeural
|
||
Gender: Female
|
||
|
||
Name: ur-IN-SalmanNeural
|
||
Gender: Male
|
||
|
||
Name: ur-PK-AsadNeural
|
||
Gender: Male
|
||
|
||
Name: ur-PK-UzmaNeural
|
||
Gender: Female
|
||
|
||
Name: uz-UZ-MadinaNeural
|
||
Gender: Female
|
||
|
||
Name: uz-UZ-SardorNeural
|
||
Gender: Male
|
||
|
||
Name: vi-VN-HoaiMyNeural
|
||
Gender: Female
|
||
|
||
Name: vi-VN-NamMinhNeural
|
||
Gender: Male
|
||
|
||
Name: zh-CN-XiaoxiaoNeural
|
||
Gender: Female
|
||
|
||
Name: zh-CN-XiaoyiNeural
|
||
Gender: Female
|
||
|
||
Name: zh-CN-YunjianNeural
|
||
Gender: Male
|
||
|
||
Name: zh-CN-YunxiNeural
|
||
Gender: Male
|
||
|
||
Name: zh-CN-YunxiaNeural
|
||
Gender: Male
|
||
|
||
Name: zh-CN-YunyangNeural
|
||
Gender: Male
|
||
|
||
Name: zh-CN-liaoning-XiaobeiNeural
|
||
Gender: Female
|
||
|
||
Name: zh-CN-shaanxi-XiaoniNeural
|
||
Gender: Female
|
||
|
||
Name: zh-HK-HiuGaaiNeural
|
||
Gender: Female
|
||
|
||
Name: zh-HK-HiuMaanNeural
|
||
Gender: Female
|
||
|
||
Name: zh-HK-WanLungNeural
|
||
Gender: Male
|
||
|
||
Name: zh-TW-HsiaoChenNeural
|
||
Gender: Female
|
||
|
||
Name: zh-TW-HsiaoYuNeural
|
||
Gender: Female
|
||
|
||
Name: zh-TW-YunJheNeural
|
||
Gender: Male
|
||
|
||
Name: zu-ZA-ThandoNeural
|
||
Gender: Female
|
||
|
||
Name: zu-ZA-ThembaNeural
|
||
Gender: Male
|
||
""".strip()
|
||
voices = []
|
||
name = ''
|
||
for line in voices_str.split("\n"):
|
||
line = line.strip()
|
||
if not line:
|
||
continue
|
||
if line.startswith("Name: "):
|
||
name = line[6:].strip()
|
||
if line.startswith("Gender: "):
|
||
gender = line[8:].strip()
|
||
if name and gender:
|
||
# voices.append({
|
||
# "name": name,
|
||
# "gender": gender,
|
||
# })
|
||
if filter_locals:
|
||
for filter_local in filter_locals:
|
||
if name.lower().startswith(filter_local.lower()):
|
||
voices.append(f"{name}-{gender}")
|
||
else:
|
||
voices.append(f"{name}-{gender}")
|
||
name = ''
|
||
voices.sort()
|
||
return voices
|
||
|
||
|
||
def parse_voice_name(name: str):
|
||
# zh-CN-XiaoyiNeural-Female
|
||
# zh-CN-YunxiNeural-Male
|
||
name = name.replace("-Female", "").replace("-Male", "").strip()
|
||
return name
|
||
|
||
|
||
def tts(text: str, voice_name: str, voice_file: str) -> [SubMaker, None]:
|
||
text = text.strip()
|
||
for i in range(3):
|
||
try:
|
||
logger.info(f"start, voice name: {voice_name}, try: {i + 1}")
|
||
|
||
async def _do() -> SubMaker:
|
||
communicate = edge_tts.Communicate(text, voice_name)
|
||
sub_maker = edge_tts.SubMaker()
|
||
with open(voice_file, "wb") as file:
|
||
async for chunk in communicate.stream():
|
||
if chunk["type"] == "audio":
|
||
file.write(chunk["data"])
|
||
elif chunk["type"] == "WordBoundary":
|
||
sub_maker.create_sub((chunk["offset"], chunk["duration"]), chunk["text"])
|
||
return sub_maker
|
||
|
||
sub_maker = asyncio.run(_do())
|
||
if not sub_maker or not sub_maker.subs:
|
||
logger.warning(f"failed, sub_maker is None or sub_maker.subs is None")
|
||
continue
|
||
|
||
logger.info(f"completed, output file: {voice_file}")
|
||
return sub_maker
|
||
except Exception as e:
|
||
logger.error(f"failed, error: {str(e)}")
|
||
return None
|
||
|
||
|
||
def create_subtitle(sub_maker: submaker.SubMaker, text: str, subtitle_file: str):
|
||
"""
|
||
优化字幕文件
|
||
1. 将字幕文件按照标点符号分割成多行
|
||
2. 逐行匹配字幕文件中的文本
|
||
3. 生成新的字幕文件
|
||
"""
|
||
text = text.replace("\n", " ")
|
||
text = text.replace("[", " ")
|
||
text = text.replace("]", " ")
|
||
text = text.replace("(", " ")
|
||
text = text.replace(")", " ")
|
||
text = text.replace("{", " ")
|
||
text = text.replace("}", " ")
|
||
text = text.strip()
|
||
|
||
def formatter(idx: int, start_time: float, end_time: float, sub_text: str) -> str:
|
||
"""
|
||
1
|
||
00:00:00,000 --> 00:00:02,360
|
||
跑步是一项简单易行的运动
|
||
"""
|
||
start_t = mktimestamp(start_time).replace(".", ",")
|
||
end_t = mktimestamp(end_time).replace(".", ",")
|
||
return (
|
||
f"{idx}\n"
|
||
f"{start_t} --> {end_t}\n"
|
||
f"{sub_text}\n"
|
||
)
|
||
|
||
start_time = -1.0
|
||
sub_items = []
|
||
sub_index = 0
|
||
|
||
script_lines = utils.split_string_by_punctuations(text)
|
||
|
||
def match_line(_sub_line: str, _sub_index: int):
|
||
if len(script_lines) <= _sub_index:
|
||
return ""
|
||
|
||
_line = script_lines[_sub_index]
|
||
if _sub_line == _line:
|
||
return script_lines[_sub_index].strip()
|
||
|
||
_sub_line_ = re.sub(r"[^\w\s]", "", _sub_line)
|
||
_line_ = re.sub(r"[^\w\s]", "", _line)
|
||
if _sub_line_ == _line_:
|
||
return _line_.strip()
|
||
|
||
_sub_line_ = re.sub(r"\W+", "", _sub_line)
|
||
_line_ = re.sub(r"\W+", "", _line)
|
||
if _sub_line_ == _line_:
|
||
return _line.strip()
|
||
|
||
return ""
|
||
|
||
sub_line = ""
|
||
|
||
try:
|
||
for _, (offset, sub) in enumerate(zip(sub_maker.offset, sub_maker.subs)):
|
||
_start_time, end_time = offset
|
||
if start_time < 0:
|
||
start_time = _start_time
|
||
|
||
sub = unescape(sub)
|
||
sub_line += sub
|
||
sub_text = match_line(sub_line, sub_index)
|
||
if sub_text:
|
||
sub_index += 1
|
||
line = formatter(
|
||
idx=sub_index,
|
||
start_time=start_time,
|
||
end_time=end_time,
|
||
sub_text=sub_text,
|
||
)
|
||
sub_items.append(line)
|
||
start_time = -1.0
|
||
sub_line = ""
|
||
|
||
if len(sub_items) == len(script_lines):
|
||
with open(subtitle_file, "w", encoding="utf-8") as file:
|
||
file.write("\n".join(sub_items) + "\n")
|
||
try:
|
||
sbs = subtitles.file_to_subtitles(subtitle_file)
|
||
duration = max([tb for ((ta, tb), txt) in sbs])
|
||
logger.info(f"completed, subtitle file created: {subtitle_file}, duration: {duration}")
|
||
except Exception as e:
|
||
logger.error(f"failed, error: {str(e)}")
|
||
os.remove(subtitle_file)
|
||
else:
|
||
logger.warning(f"failed, sub_items len: {len(sub_items)}, script_lines len: {len(script_lines)}")
|
||
|
||
except Exception as e:
|
||
logger.error(f"failed, error: {str(e)}")
|
||
|
||
|
||
def get_audio_duration(sub_maker: submaker.SubMaker):
|
||
"""
|
||
获取音频时长
|
||
"""
|
||
if not sub_maker.offset:
|
||
return 0.0
|
||
return sub_maker.offset[-1][1] / 10000000
|
||
|
||
|
||
if __name__ == "__main__":
|
||
voices = get_all_voices()
|
||
print(voices)
|
||
print(len(voices))
|
||
|
||
|
||
async def _do():
|
||
temp_dir = utils.storage_dir("temp")
|
||
|
||
voice_names = [
|
||
# 女性
|
||
"zh-CN-XiaoxiaoNeural",
|
||
"zh-CN-XiaoyiNeural",
|
||
# 男性
|
||
"zh-CN-YunyangNeural",
|
||
"zh-CN-YunxiNeural",
|
||
]
|
||
text = """
|
||
静夜思是唐代诗人李白创作的一首五言古诗。这首诗描绘了诗人在寂静的夜晚,看到窗前的明月,不禁想起远方的家乡和亲人,表达了他对家乡和亲人的深深思念之情。全诗内容是:“床前明月光,疑是地上霜。举头望明月,低头思故乡。”在这短短的四句诗中,诗人通过“明月”和“思故乡”的意象,巧妙地表达了离乡背井人的孤独与哀愁。首句“床前明月光”设景立意,通过明亮的月光引出诗人的遐想;“疑是地上霜”增添了夜晚的寒冷感,加深了诗人的孤寂之情;“举头望明月”和“低头思故乡”则是情感的升华,展现了诗人内心深处的乡愁和对家的渴望。这首诗简洁明快,情感真挚,是中国古典诗歌中非常著名的一首,也深受后人喜爱和推崇。
|
||
"""
|
||
|
||
text = """
|
||
What is the meaning of life? This question has puzzled philosophers, scientists, and thinkers of all kinds for centuries. Throughout history, various cultures and individuals have come up with their interpretations and beliefs around the purpose of life. Some say it's to seek happiness and self-fulfillment, while others believe it's about contributing to the welfare of others and making a positive impact in the world. Despite the myriad of perspectives, one thing remains clear: the meaning of life is a deeply personal concept that varies from one person to another. It's an existential inquiry that encourages us to reflect on our values, desires, and the essence of our existence.
|
||
"""
|
||
|
||
text = """
|
||
预计未来3天深圳冷空气活动频繁,未来两天持续阴天有小雨,出门带好雨具;
|
||
10-11日持续阴天有小雨,日温差小,气温在13-17℃之间,体感阴凉;
|
||
12日天气短暂好转,早晚清凉;
|
||
"""
|
||
|
||
text = "[Opening scene: A sunny day in a suburban neighborhood. A young boy named Alex, around 8 years old, is playing in his front yard with his loyal dog, Buddy.]\n\n[Camera zooms in on Alex as he throws a ball for Buddy to fetch. Buddy excitedly runs after it and brings it back to Alex.]\n\nAlex: Good boy, Buddy! You're the best dog ever!\n\n[Buddy barks happily and wags his tail.]\n\n[As Alex and Buddy continue playing, a series of potential dangers loom nearby, such as a stray dog approaching, a ball rolling towards the street, and a suspicious-looking stranger walking by.]\n\nAlex: Uh oh, Buddy, look out!\n\n[Buddy senses the danger and immediately springs into action. He barks loudly at the stray dog, scaring it away. Then, he rushes to retrieve the ball before it reaches the street and gently nudges it back towards Alex. Finally, he stands protectively between Alex and the stranger, growling softly to warn them away.]\n\nAlex: Wow, Buddy, you're like my superhero!\n\n[Just as Alex and Buddy are about to head inside, they hear a loud crash from a nearby construction site. They rush over to investigate and find a pile of rubble blocking the path of a kitten trapped underneath.]\n\nAlex: Oh no, Buddy, we have to help!\n\n[Buddy barks in agreement and together they work to carefully move the rubble aside, allowing the kitten to escape unharmed. The kitten gratefully nuzzles against Buddy, who responds with a friendly lick.]\n\nAlex: We did it, Buddy! We saved the day again!\n\n[As Alex and Buddy walk home together, the sun begins to set, casting a warm glow over the neighborhood.]\n\nAlex: Thanks for always being there to watch over me, Buddy. You're not just my dog, you're my best friend.\n\n[Buddy barks happily and nuzzles against Alex as they disappear into the sunset, ready to face whatever adventures tomorrow may bring.]\n\n[End scene.]"
|
||
for voice_name in voice_names:
|
||
voice_file = f"{temp_dir}/tts-{voice_name}.mp3"
|
||
subtitle_file = f"{temp_dir}/tts.mp3.srt"
|
||
sub_maker = tts(text=text, voice_name=voice_name, voice_file=voice_file)
|
||
create_subtitle(sub_maker=sub_maker, text=text, subtitle_file=subtitle_file)
|
||
audio_duration = get_audio_duration(sub_maker)
|
||
print(f"voice: {voice_name}, audio duration: {audio_duration}s")
|
||
|
||
|
||
loop = asyncio.get_event_loop_policy().get_event_loop()
|
||
try:
|
||
loop.run_until_complete(_do())
|
||
finally:
|
||
loop.close()
|