添加chunk处理
This commit is contained in:
parent
9569009f32
commit
b0753a5220
40
Human.py
40
Human.py
@ -1,14 +1,50 @@
|
|||||||
#encoding = utf8
|
#encoding = utf8
|
||||||
|
import logging
|
||||||
|
import queue
|
||||||
from queue import Queue
|
from queue import Queue
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
|
||||||
|
from tts.Chunk2Mal import Chunk2Mal
|
||||||
|
|
||||||
|
logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
class Human:
|
class Human:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self._tts = None
|
self._tts = None
|
||||||
self._audio_chunk_queue = Queue()
|
self._fps = 25 # 20 ms per frame
|
||||||
|
self._sample_rate = 16000
|
||||||
|
self._chunk = self._sample_rate // self._fps # 320 samples per chunk (20ms * 16000 / 1000)
|
||||||
|
self._chunk_2_mal = Chunk2Mal()
|
||||||
|
|
||||||
|
def on_destroy(self):
|
||||||
|
if self._tts is not None:
|
||||||
|
self._tts.stop()
|
||||||
|
logger.info('human destroy')
|
||||||
|
|
||||||
def set_tts(self, tts):
|
def set_tts(self, tts):
|
||||||
|
if self._tts == tts:
|
||||||
|
return
|
||||||
|
|
||||||
self._tts = tts
|
self._tts = tts
|
||||||
|
self._tts.start()
|
||||||
|
|
||||||
|
def read(self, txt):
|
||||||
|
if self._tts is None:
|
||||||
|
logger.warning('tts is none')
|
||||||
|
return
|
||||||
|
|
||||||
|
self._tts.push_txt(txt)
|
||||||
|
|
||||||
def push_audio_chunk(self, chunk):
|
def push_audio_chunk(self, chunk):
|
||||||
pass
|
self._chunk_2_mal.push_chunk(chunk)
|
||||||
|
self._audio_chunk_queue.put(chunk)
|
||||||
|
|
||||||
|
def pull_audio_chunk(self):
|
||||||
|
try:
|
||||||
|
chunk = self._audio_chunk_queue.get(block=True, timeout=1.0)
|
||||||
|
type = 1
|
||||||
|
except queue.Empty:
|
||||||
|
chunk = np.zeros(self._chunk, dtype=np.float32)
|
||||||
|
type = 0
|
||||||
|
return chunk, type
|
@ -2,7 +2,7 @@ librosa~=0.10.2.post1
|
|||||||
numpy~=1.26.3
|
numpy~=1.26.3
|
||||||
opencv-contrib-python
|
opencv-contrib-python
|
||||||
opencv-python~=4.10.0.84
|
opencv-python~=4.10.0.84
|
||||||
torch~=2.4.0+cu118
|
torch
|
||||||
torchvision
|
torchvision
|
||||||
tqdm~=4.66.5
|
tqdm~=4.66.5
|
||||||
numba
|
numba
|
||||||
|
11
tts/Chunk2Mal.py
Normal file
11
tts/Chunk2Mal.py
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
#encoding = utf8
|
||||||
|
from queue import Queue
|
||||||
|
|
||||||
|
|
||||||
|
class Chunk2Mal:
|
||||||
|
def __init__(self):
|
||||||
|
self._audio_chunk_queue = Queue()
|
||||||
|
|
||||||
|
def push_chunk(self, chunk):
|
||||||
|
self._audio_chunk_queue.put(chunk)
|
||||||
|
|
@ -1,4 +1,5 @@
|
|||||||
#encoding = utf8
|
#encoding = utf8
|
||||||
|
import logging
|
||||||
import queue
|
import queue
|
||||||
from io import BytesIO
|
from io import BytesIO
|
||||||
from queue import Queue
|
from queue import Queue
|
||||||
@ -17,12 +18,14 @@ class TTSBase:
|
|||||||
self._chunk = self._sample_rate // self._fps
|
self._chunk = self._sample_rate // self._fps
|
||||||
|
|
||||||
def _on_run(self):
|
def _on_run(self):
|
||||||
|
logging.info('tts run')
|
||||||
while not self._exit_event.is_set():
|
while not self._exit_event.is_set():
|
||||||
try:
|
try:
|
||||||
txt = self._queue.get(block=True, timeout=1)
|
txt = self._queue.get(block=True, timeout=1)
|
||||||
except queue.Empty:
|
except queue.Empty:
|
||||||
continue
|
continue
|
||||||
self._request(txt)
|
self._request(txt)
|
||||||
|
logging.info('tts exit')
|
||||||
|
|
||||||
def _request(self, txt):
|
def _request(self, txt):
|
||||||
pass
|
pass
|
||||||
@ -33,6 +36,7 @@ class TTSBase:
|
|||||||
self._exit_event = Event()
|
self._exit_event = Event()
|
||||||
self._thread = Thread(target=self._on_run)
|
self._thread = Thread(target=self._on_run)
|
||||||
self._thread.start()
|
self._thread.start()
|
||||||
|
logging.info('tts start')
|
||||||
|
|
||||||
def stop(self):
|
def stop(self):
|
||||||
if self._exit_event is None:
|
if self._exit_event is None:
|
||||||
@ -40,6 +44,7 @@ class TTSBase:
|
|||||||
|
|
||||||
self._exit_event.set()
|
self._exit_event.set()
|
||||||
self._thread.join()
|
self._thread.join()
|
||||||
|
logging.info('tts stop')
|
||||||
|
|
||||||
def clear(self):
|
def clear(self):
|
||||||
self._queue.queue.clear()
|
self._queue.queue.clear()
|
||||||
|
73
ui.py
73
ui.py
@ -1,6 +1,7 @@
|
|||||||
#encoding = utf8
|
#encoding = utf8
|
||||||
import json
|
import json
|
||||||
import logging
|
import logging
|
||||||
|
from logging import handlers
|
||||||
import tkinter
|
import tkinter
|
||||||
import tkinter.messagebox
|
import tkinter.messagebox
|
||||||
import customtkinter
|
import customtkinter
|
||||||
@ -52,6 +53,10 @@ class App(customtkinter.CTk):
|
|||||||
tts = EdgeTTS(self._human)
|
tts = EdgeTTS(self._human)
|
||||||
self._human.set_tts(tts)
|
self._human.set_tts(tts)
|
||||||
|
|
||||||
|
def on_destroy(self):
|
||||||
|
logger.info('------------App destroy------------')
|
||||||
|
self._human.on_destroy()
|
||||||
|
|
||||||
def _init_image_canvas(self):
|
def _init_image_canvas(self):
|
||||||
self._canvas = customtkinter.CTkCanvas(self.image_frame)
|
self._canvas = customtkinter.CTkCanvas(self.image_frame)
|
||||||
self._canvas.pack(fill=customtkinter.BOTH, expand=customtkinter.YES)
|
self._canvas.pack(fill=customtkinter.BOTH, expand=customtkinter.YES)
|
||||||
@ -60,20 +65,21 @@ class App(customtkinter.CTk):
|
|||||||
content = self.entry.get()
|
content = self.entry.get()
|
||||||
print('content:', content)
|
print('content:', content)
|
||||||
self.entry.delete(0, customtkinter.END)
|
self.entry.delete(0, customtkinter.END)
|
||||||
payload = {
|
self._human.read(content)
|
||||||
'text': content,
|
# payload = {
|
||||||
'voice': 'zh-CN-XiaoyiNeural'
|
# 'text': content,
|
||||||
}
|
# 'voice': 'zh-CN-XiaoyiNeural'
|
||||||
resp = requests.get(self._tts_url + '/tts', params=urlencode(payload))
|
# }
|
||||||
if resp.status_code != 200:
|
# resp = requests.get(self._tts_url + '/tts', params=urlencode(payload))
|
||||||
print('tts error', resp.status_code)
|
# if resp.status_code != 200:
|
||||||
return
|
# print('tts error', resp.status_code)
|
||||||
|
# return
|
||||||
print(resp.content)
|
#
|
||||||
|
# print(resp.content)
|
||||||
resJson = json.loads(resp.text)
|
#
|
||||||
url = resJson.get('url')
|
# resJson = json.loads(resp.text)
|
||||||
self.download_tts(url)
|
# url = resJson.get('url')
|
||||||
|
# self.download_tts(url)
|
||||||
|
|
||||||
def download_tts(self, url):
|
def download_tts(self, url):
|
||||||
file_name = url[3:]
|
file_name = url[3:]
|
||||||
@ -91,8 +97,43 @@ class App(customtkinter.CTk):
|
|||||||
# open('./audio/', 'wb') with
|
# open('./audio/', 'wb') with
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
def config_logging(file_name: str, console_level: int=logging.INFO, file_level: int=logging.DEBUG):
|
||||||
logging.basicConfig(filename='./logs/info.log', level=logging.INFO)
|
file_handler = logging.FileHandler(file_name, mode='a', encoding="utf8")
|
||||||
|
file_handler.setFormatter(logging.Formatter(
|
||||||
|
'%(asctime)s [%(levelname)s] %(module)s.%(lineno)d %(name)s:\t%(message)s'
|
||||||
|
))
|
||||||
|
file_handler.setLevel(file_level)
|
||||||
|
|
||||||
|
console_handler = logging.StreamHandler()
|
||||||
|
console_handler.setFormatter(logging.Formatter(
|
||||||
|
'[%(asctime)s %(levelname)s] %(message)s',
|
||||||
|
datefmt="%Y/%m/%d %H:%M:%S"
|
||||||
|
))
|
||||||
|
console_handler.setLevel(console_level)
|
||||||
|
|
||||||
|
logging.basicConfig(
|
||||||
|
level=min(console_level, file_level),
|
||||||
|
handlers=[file_handler, console_handler],
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
# logging.basicConfig(filename='./logs/info.log', level=logging.INFO)
|
||||||
|
config_logging('./logs/info.log', logging.INFO, logging.INFO)
|
||||||
|
# logger = logging.getLogger('manager')
|
||||||
|
# # 输出到控制台, 级别为DEBUG
|
||||||
|
# console = logging.StreamHandler()
|
||||||
|
# console.setLevel(logging.DEBUG)
|
||||||
|
# logger.addHandler(console)
|
||||||
|
#
|
||||||
|
# # 输出到文件, 级别为INFO, 文件按大小切分
|
||||||
|
# filelog = logging.handlers.RotatingFileHandler(filename='./logs/info.log', level=logging.INFO,
|
||||||
|
# maxBytes=1024 * 1024, backupCount=5)
|
||||||
|
# filelog.setFormatter(logging.Formatter('%(asctime)s - %(levelname)s - %(message)s'))
|
||||||
|
# logger.setLevel(logging.INFO)
|
||||||
|
# logger.addHandler(filelog)
|
||||||
|
logger.info('------------start------------')
|
||||||
app = App()
|
app = App()
|
||||||
app.mainloop()
|
app.mainloop()
|
||||||
|
app.on_destroy()
|
||||||
|
# logger.info('------------exit------------')
|
||||||
|
Loading…
Reference in New Issue
Block a user