# -*- coding: utf-8 -*- """ IO 模块完整演示 ───────────────────────────────────────────────────────────────── 运行: python main.py 依赖: pip install PyQt5 SpeechRecognition pyaudio pyttsx3 ───────────────────────────────────────────────────────────────── """ import logging import sys from PyQt5.QtCore import Qt, QTimer, pyqtSlot from PyQt5.QtWidgets import ( QApplication, QMainWindow, QWidget, QVBoxLayout, QSplitter, QTabWidget, QStatusBar ) # ── 处理器 ──────────────────────────────────────────────────────── from processors.text_processor import PIPELINE_PRESETS from uas.io.base_io import IOType from uas.io.dispatcher import IODispatcher # ── 核心模块 ────────────────────────────────────────────────────── from uas.io.signals import io_signals from inputs.speech_input import SpeechInputWidget # ── 输入模块 ────────────────────────────────────────────────────── from inputs.text_input import TextInputWidget, ConsoleTextInput from outputs.speech_output import SpeechOutputWidget # ── 输出模块 ────────────────────────────────────────────────────── from outputs.text_output import TextOutputWidget # ── 日志 ────────────────────────────────────────────────────────── logging.basicConfig( level = logging.DEBUG, format = "%(asctime)s [%(levelname)-8s] %(name)s - %(message)s", ) logger = logging.getLogger("main") # ───────────────────────────────────────────────────────────────── # 主窗口 # ───────────────────────────────────────────────────────────────── class MainWindow(QMainWindow): def __init__(self): super().__init__() self.setWindowTitle("🛰️ IO 通信模块 — PyQt5 信号槽演示") self.resize(1100, 700) self._setup_dispatcher() self._setup_ui() self._connect_signals() self._auto_demo() # ── 分发器初始化 ────────────────────────────────────────────── def _setup_dispatcher(self): self.dispatcher = IODispatcher(max_threads=4, parent=self) # 注册文本处理链(full 预设) for proc in PIPELINE_PRESETS["full"]: self.dispatcher.register_processor(IOType.TEXT, proc) # 注册语音处理链 for proc in PIPELINE_PRESETS["speech"]: self.dispatcher.register_processor(IOType.SPEECH, proc) self.dispatcher.start() logger.info("✅ 分发器已启动") # ── UI 构建 ─────────────────────────────────────────────────── def _setup_ui(self): central = QWidget() self.setCentralWidget(central) main_layout = QVBoxLayout(central) main_layout.setContentsMargins(6, 6, 6, 6) # 水平分割:左=输入,右=输出 splitter = QSplitter(Qt.Horizontal) # ── 左侧:输入 Tab ──────────────────────────────────────── input_tabs = QTabWidget() self.text_input = TextInputWidget() self.speech_input = SpeechInputWidget() input_tabs.addTab(self.text_input, "📝 文本输入") input_tabs.addTab(self.speech_input, "🎤 语音输入") splitter.addWidget(input_tabs) # ── 右侧:输出 Tab ──────────────────────────────────────── output_tabs = QTabWidget() self.text_output = TextOutputWidget() self.speech_output = SpeechOutputWidget() output_tabs.addTab(self.text_output, "📄 文本输出") output_tabs.addTab(self.speech_output, "🔊 语音输出") splitter.addWidget(output_tabs) splitter.setSizes([420, 660]) main_layout.addWidget(splitter) # ── 状态栏 ──────────────────────────────────────────────── self._status = QStatusBar() self.setStatusBar(self._status) self._status.showMessage("就绪 | IODispatcher 运行中") # ── 信号连接 ────────────────────────────────────────────────── def _connect_signals(self): # 全局信号监听(用于状态栏更新) io_signals.input_received.connect(self._on_input_received) io_signals.input_processed.connect(self._on_processed) io_signals.error_occurred.connect(self._on_error) io_signals.speech_recognized.connect(self._on_speech_recognized) @pyqtSlot(str, str, object) def _on_input_received(self, data_id: str, io_type: str, data): self._status.showMessage( f"📥 收到输入 [{io_type}] id={data_id[:8]} 正在处理..." ) @pyqtSlot(str, str, object) def _on_processed(self, data_id: str, io_type: str, data): self._status.showMessage( f"✅ 处理完成 [{io_type}] id={data_id[:8]}" ) @pyqtSlot(str, str, str) def _on_error(self, data_id: str, source: str, msg: str): self._status.showMessage(f"❌ 错误 [{source}]: {msg}") @pyqtSlot(str) def _on_speech_recognized(self, text: str): self._status.showMessage(f"🎤 语音识别: {text}") # ── 自动演示 ────────────────────────────────────────────────── def _auto_demo(self): """启动后自动注入几条测试消息""" demo_texts = [ "Hello World!这是第一条测试消息。", "PyQt5 信号与槽机制实现异步IO分发?", "支持文本、语音、文件等多种输入输出类型!", ] console_input = ConsoleTextInput(self) def inject_next(idx=0): if idx < len(demo_texts): console_input.inject(demo_texts[idx]) QTimer.singleShot(800, lambda: inject_next(idx + 1)) QTimer.singleShot(500, inject_next) def closeEvent(self, event): self.dispatcher.stop() self.speech_input.stop() event.accept() # ───────────────────────────────────────────────────────────────── # 入口 # ───────────────────────────────────────────────────────────────── def main(): app = QApplication(sys.argv) app.setStyle("Fusion") win = MainWindow() win.show() sys.exit(app.exec_()) if __name__ == "__main__": main()