项目文件夹

文件
2026-07-13 12:28:27 +08:00

165 行
4.6 KiB
Python

# coding: utf-8
"""
上下文菜单处理模块
提供托盘菜单"编辑上下文"的回调处理逻辑。
"""
import queue
import threading
import tkinter as tk
from typing import Optional
from config_client import ClientConfig as Config
from core.client.state import console
from . import logger
# 全局对话框管理器
_dialog_manager: Optional['_ContextDialogManager'] = None
_manager_lock = threading.Lock()
def get_dialog_manager() -> Optional['_ContextDialogManager']:
"""获取对话框管理器单例"""
global _dialog_manager
with _manager_lock:
if _dialog_manager is None:
_dialog_manager = _ContextDialogManager()
return _dialog_manager
def on_edit_context():
"""
处理"编辑上下文"菜单点击
"""
try:
# 获取对话框管理器并显示对话框
manager = get_dialog_manager()
# 传递当前的上下文配置作为默认值
result = manager.show_dialog(default_text=Config.context)
if not result or not result.confirmed:
logger.info("用户取消编辑上下文")
return
context_text = result.data.get('context', '').strip()
# 更新配置
Config.context = context_text
# 显示成功提示
console.print(f'[green]✓[/] 上下文已更新: {context_text}')
if context_text:
logger.info(f"用户更新了上下文: {context_text}")
else:
logger.info("用户清空了上下文")
except Exception as e:
logger.error(f"处理'编辑上下文'时发生错误: {e}", exc_info=True)
console.print(f'[red]编辑上下文失败: {e}[/]')
class _ContextDialogManager:
"""
上下文对话框管理器
"""
def __init__(self):
self.request_queue: queue.Queue = queue.Queue()
self.result_queue: queue.Queue = queue.Queue()
self.root: Optional[tk.Tk] = None
self.is_running = False
# 在独立线程中启动 Tkinter
self.tk_thread = threading.Thread(
target=self._run_tkinter,
daemon=True,
name="ContextDialogThread"
)
self.tk_thread.start()
# 等待 Tkinter 初始化完成
self._wait_for_ready()
def _wait_for_ready(self, timeout=5.0):
"""等待 Tkinter 线程准备就绪"""
import time
start = time.time()
while not self.is_running and (time.time() - start) < timeout:
time.sleep(0.05)
if not self.is_running:
raise RuntimeError("Context Tkinter 线程启动超时")
def _run_tkinter(self):
"""在独立线程中运行 Tkinter 主循环"""
self.root = tk.Tk()
self.root.withdraw()
# 设置窗口关闭时的行为
self.root.protocol("WM_DELETE_WINDOW", self._on_close)
# 标记为运行中
self.is_running = True
# 开始处理请求队列
self._process_requests()
# 启动 Tkinter 主循环
self.root.mainloop()
def _on_close(self):
"""关闭窗口并退出"""
self.is_running = False
if self.root:
self.root.quit()
def _process_requests(self):
"""处理队列中的对话框请求"""
if not self.is_running:
return
try:
while not self.request_queue.empty():
try:
req_data = self.request_queue.get_nowait()
self._show_dialog_impl(req_data)
except queue.Empty:
break
except Exception as e:
logger.error(f"处理上下文对话框请求时发生错误: {e}", exc_info=True)
if self.root:
self.root.after(100, self._process_requests)
def _show_dialog_impl(self, default_text):
"""实际显示对话框"""
try:
from core.ui.context_dialog import show_context_dialog
result = show_context_dialog(
default_text=default_text,
parent=self.root,
title="编辑上下文"
)
self.result_queue.put(result)
except Exception as e:
logger.error(f"显示上下文对话框时发生错误: {e}", exc_info=True)
self.result_queue.put(None)
def show_dialog(self, default_text: str = "") -> Optional[object]:
"""显示对话框"""
self.request_queue.put(default_text)
try:
result = self.result_queue.get(timeout=300)
return result
except queue.Empty:
logger.error("上下文对话框操作超时")
return None