import os import sys import traceback from loguru import logger from nicegui import ui, app, run, native from screeninfo import get_monitors from config.config import load_config # 导入我们的模块 from ui.core.logger import setup_logger from ui.views.config_page import create_config_page from ui.views.home_page import create_home_page from ui.views.data_page import create_data_page from ui.views.signature_page import create_signature_page from utils.font_utils import install_fonts_from_directory sys.stdout.reconfigure(encoding="utf-8") sys.stderr.reconfigure(encoding="utf-8") # 1. 初始化配置 config = load_config("config.toml") setup_logger() # === 关键修改:定义一个获取路径的通用函数 === def get_path(relative_path): """ 获取资源的绝对路径。 兼容:开发环境(直接运行) 和 生产环境(打包成exe后解压的临时目录) """ if hasattr(sys, "_MEIPASS"): base_path = sys._MEIPASS else: # 开发环境当前目录 base_path = os.path.dirname(os.path.abspath(__file__)) return os.path.join(base_path, relative_path) def calculate_window_size(): """ 获取主屏幕分辨率,并计算一个基于百分比的 NiceGUI 窗口大小。 """ try: # 尝试获取所有显示器信息 monitors = get_monitors() if monitors: # 假设第一个是主显示器 m = monitors[0] screen_width = m.width screen_height = m.height # 设置窗口宽度为屏幕宽度的 30% target_width = int(screen_width * 0.30) # 设置窗口高度为屏幕高度的 60% target_height = int(screen_height * 0.60) # 确保窗口有一个合理的最小值 (例如 800x600) min_width = 800 min_height = 700 target_width = max(target_width, min_width) target_height = max(target_height, min_height) logger.info(f"屏幕分辨率: {screen_width}x{screen_height}") logger.info(f"设置窗口大小为: {target_width}x{target_height}") return target_width, target_height except Exception as e: logger.warning(f"无法获取屏幕分辨率 ({e}),使用默认大小 (900, 900)") return 900, 900 # 失败时的默认值 # 1. 挂载静态资源 (CSS/图片) # 注意:这里使用 get_path 确保打包后能找到 static_dir = get_path(os.path.join("ui", "assets")) app.add_static_files("/assets", static_dir) # 3. 页面路由 @ui.page("/") def index_page(): create_home_page() @ui.page("/config") def config_page(): create_config_page() @ui.page("/data") def data_page(): create_data_page() @ui.page("/signature") def signature_page(folder: str = ""): create_signature_page(folder) # 4. 启动时钩子 async def startup_check(): try: logger.info("系统启动: 初始化资源...") await run.io_bound(install_fonts_from_directory, config["fonts_dir"]) os.makedirs(config["output_folder"], exist_ok=True) logger.success("资源初始化完成") except Exception as e: logger.error(f"初始化失败: {e}") logger.error(traceback.format_exc()) app.on_startup(startup_check) if __name__ in {"__main__", "__mp_main__"}: calculated_size = calculate_window_size() ui.run( title="尚城幼儿园成长报告助手", native=True, window_size=calculated_size, port=native.find_open_port(), # 自动寻找端口 reload=True, )