# coding:utf-8 """ 启动入口 — 默认使用 Flet2 UI。 使用 --tk 参数切换到 Tkinter UI。 """ import sys import os import subprocess import ssl import traceback # 修复 Windows 上 flet_desktop 子进程弹出控制台窗口的问题 # 原始 Popen 不带 CREATE_NO_WINDOW 标志,会为每个子进程创建控制台窗口 _original_popen = subprocess.Popen class Popen(_original_popen): def __init__(self, *args, **kwargs): if sys.platform == "win32" and "creationflags" not in kwargs: kwargs["creationflags"] = subprocess.CREATE_NO_WINDOW super().__init__(*args, **kwargs) subprocess.Popen = Popen # PyInstaller 打包后,设置 FLET_VIEW_PATH 指向打包内的 Flet 客户端 # 避免从 GitHub 下载 if getattr(sys, 'frozen', False): # 运行在打包后的 exe 中 base_path = sys._MEIPASS # PyInstaller 解压到的临时目录 flet_client_path = os.path.join(base_path, '.flet', 'client', 'flet-desktop-full-0.85.3') flet_exe = os.path.join(flet_client_path, 'flet', 'flet.exe') # 写入日志便于调试 log_file = os.path.join(os.path.dirname(sys.executable), 'startup_log.txt') with open(log_file, 'w') as f: f.write(f'base_path: {base_path}\n') f.write(f'flet_client_path: {flet_client_path}\n') f.write(f'flet_exe: {flet_exe}\n') f.write(f'exists: {os.path.exists(flet_exe)}\n') if os.path.exists(flet_exe): f.write('Setting FLET_VIEW_PATH\n') os.environ['FLET_VIEW_PATH'] = flet_client_path f.write(f'FLET_VIEW_PATH: {os.environ.get("FLET_VIEW_PATH")}\n') # 禁用 SSL 验证,避免证书问题 if hasattr(ssl, '_create_unverified_context'): ssl._create_default_https_context = ssl._create_unverified_context def excepthook(type, value, tb): """捕获未处理的异常,写入日志""" log_file = os.path.join(os.path.dirname(sys.executable), 'error_log.txt') with open(log_file, 'w') as f: f.write(''.join(traceback.format_exception(type, value, tb))) sys.__excepthook__(type, value, tb) sys.excepthook = excepthook if __name__ == '__main__': if '--tk' in sys.argv: from core.ui.tkinter.splash import SplashWindow from tkinter import messagebox try: window = SplashWindow().run() if window: window.run() except Exception as e: messagebox.showerror("错误", f"系统初始化失败: {str(e)}") else: from core.ui.flet.app_v2 import run run()