182 lines
5.6 KiB
Python
182 lines
5.6 KiB
Python
|
|
"""
|
|||
|
|
PCM_Report 看板查看器按钮模块
|
|||
|
|
使用方法:在 ui_main.py 中导入并调用 add_dashboard_button()
|
|||
|
|
"""
|
|||
|
|
|
|||
|
|
import subprocess
|
|||
|
|
import sys
|
|||
|
|
import os
|
|||
|
|
from pathlib import Path
|
|||
|
|
from PySide6.QtWidgets import (
|
|||
|
|
QPushButton, QFileDialog, QMessageBox, QHBoxLayout, QWidget
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
|
|||
|
|
def get_viewer_executable():
|
|||
|
|
"""
|
|||
|
|
获取看板查看器的可执行文件路径
|
|||
|
|
优先查找打包后的 exe,否则使用 Python 源文件
|
|||
|
|
"""
|
|||
|
|
# 获取当前程序所在目录
|
|||
|
|
if getattr(sys, 'frozen', False):
|
|||
|
|
# 打包后的环境
|
|||
|
|
current_dir = Path(sys.executable).parent
|
|||
|
|
else:
|
|||
|
|
# 开发环境
|
|||
|
|
current_dir = Path(__file__).parent
|
|||
|
|
|
|||
|
|
# 1. 首先查找打包后的 exe(与当前程序同级目录)
|
|||
|
|
exe_path = current_dir / "PCM_Viewer.exe"
|
|||
|
|
if exe_path.exists():
|
|||
|
|
return str(exe_path), True # True 表示是 exe
|
|||
|
|
|
|||
|
|
# 2. 查找开发环境的 Python 源文件
|
|||
|
|
dev_path = Path(r"F:\PyPro\PCM_Viewer\main.py")
|
|||
|
|
if dev_path.exists():
|
|||
|
|
return str(dev_path), False # False 表示是 py 文件
|
|||
|
|
|
|||
|
|
# 3. 尝试相对路径(假设两个项目在同一目录下)
|
|||
|
|
relative_path = current_dir.parent / "PCM_Viewer" / "main.py"
|
|||
|
|
if relative_path.exists():
|
|||
|
|
return str(relative_path), False
|
|||
|
|
|
|||
|
|
return None, False
|
|||
|
|
|
|||
|
|
|
|||
|
|
def add_dashboard_button(window, toolbar_layout: QHBoxLayout):
|
|||
|
|
"""
|
|||
|
|
在工具栏添加"打开看板"按钮
|
|||
|
|
|
|||
|
|
Args:
|
|||
|
|
window: MainWindow 实例 (用于日志记录和消息框)
|
|||
|
|
toolbar_layout: 工具栏布局
|
|||
|
|
"""
|
|||
|
|
# 创建按钮
|
|||
|
|
open_viewer_btn = QPushButton("打开看板")
|
|||
|
|
open_viewer_btn.setToolTip("打开看板查看器 (全屏模式)")
|
|||
|
|
|
|||
|
|
# 绑定点击事件
|
|||
|
|
def on_open_viewer():
|
|||
|
|
"""打开 PCM_Viewer 全屏展示"""
|
|||
|
|
# 选择布局文件
|
|||
|
|
file_path, _ = QFileDialog.getOpenFileName(
|
|||
|
|
window,
|
|||
|
|
"选择看板布局文件",
|
|||
|
|
"",
|
|||
|
|
"JSON文件 (*.json)"
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
if not file_path:
|
|||
|
|
return
|
|||
|
|
|
|||
|
|
# 检查文件是否存在
|
|||
|
|
if not Path(file_path).exists():
|
|||
|
|
QMessageBox.warning(window, "警告", "选择的文件不存在!")
|
|||
|
|
return
|
|||
|
|
|
|||
|
|
# 获取查看器可执行文件
|
|||
|
|
viewer_path, is_exe = get_viewer_executable()
|
|||
|
|
|
|||
|
|
if not viewer_path:
|
|||
|
|
QMessageBox.critical(
|
|||
|
|
window,
|
|||
|
|
"错误",
|
|||
|
|
"未找到看板查看器程序!\n"
|
|||
|
|
"请确保 PCM_Viewer.exe 或 main.py 存在。"
|
|||
|
|
)
|
|||
|
|
return
|
|||
|
|
|
|||
|
|
# 启动 PCM_Viewer 子进程
|
|||
|
|
try:
|
|||
|
|
if is_exe:
|
|||
|
|
# 打包后的 exe,直接运行
|
|||
|
|
cmd = [viewer_path, file_path, "--fullscreen"]
|
|||
|
|
else:
|
|||
|
|
# Python 源文件,使用 python 解释器运行
|
|||
|
|
cmd = ["python", viewer_path, file_path, "--fullscreen"]
|
|||
|
|
|
|||
|
|
# 使用 subprocess.Popen 启动独立进程
|
|||
|
|
subprocess.Popen(
|
|||
|
|
cmd,
|
|||
|
|
shell=False, # 不使用 shell,更安全
|
|||
|
|
stdout=subprocess.DEVNULL,
|
|||
|
|
stderr=subprocess.DEVNULL,
|
|||
|
|
# 设置工作目录为查看器所在目录
|
|||
|
|
cwd=os.path.dirname(viewer_path) if is_exe else None
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
# 记录日志
|
|||
|
|
if hasattr(window, 'logger'):
|
|||
|
|
window.logger.info(f"已启动看板查看器: {viewer_path} {file_path}")
|
|||
|
|
|
|||
|
|
except Exception as e:
|
|||
|
|
QMessageBox.critical(window, "错误", f"启动看板失败: {str(e)}")
|
|||
|
|
if hasattr(window, 'logger'):
|
|||
|
|
window.logger.error(f"启动看板失败: {e}")
|
|||
|
|
|
|||
|
|
open_viewer_btn.clicked.connect(on_open_viewer)
|
|||
|
|
|
|||
|
|
# 添加到工具栏
|
|||
|
|
toolbar_layout.addWidget(open_viewer_btn)
|
|||
|
|
|
|||
|
|
return open_viewer_btn
|
|||
|
|
|
|||
|
|
|
|||
|
|
# 兼容直接复制到 ui_main.py 的函数形式
|
|||
|
|
def open_dashboard_viewer(window):
|
|||
|
|
"""
|
|||
|
|
打开 PCM_Viewer 全屏展示(可直接复制到 ui_main.py 使用)
|
|||
|
|
"""
|
|||
|
|
# 选择布局文件
|
|||
|
|
file_path, _ = QFileDialog.getOpenFileName(
|
|||
|
|
window,
|
|||
|
|
"选择看板布局文件",
|
|||
|
|
"",
|
|||
|
|
"JSON文件 (*.json)"
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
if not file_path:
|
|||
|
|
return
|
|||
|
|
|
|||
|
|
# 检查文件是否存在
|
|||
|
|
if not Path(file_path).exists():
|
|||
|
|
QMessageBox.warning(window, "警告", "选择的文件不存在!")
|
|||
|
|
return
|
|||
|
|
|
|||
|
|
# 获取查看器可执行文件
|
|||
|
|
viewer_path, is_exe = get_viewer_executable()
|
|||
|
|
|
|||
|
|
if not viewer_path:
|
|||
|
|
QMessageBox.critical(
|
|||
|
|
window,
|
|||
|
|
"错误",
|
|||
|
|
"未找到看板查看器程序!\n"
|
|||
|
|
"请确保 PCM_Viewer.exe 或 main.py 存在。"
|
|||
|
|
)
|
|||
|
|
return
|
|||
|
|
|
|||
|
|
# 启动 PCM_Viewer 子进程
|
|||
|
|
try:
|
|||
|
|
if is_exe:
|
|||
|
|
# 打包后的 exe,直接运行
|
|||
|
|
cmd = [viewer_path, file_path, "--fullscreen"]
|
|||
|
|
else:
|
|||
|
|
# Python 源文件,使用 python 解释器运行
|
|||
|
|
cmd = ["python", viewer_path, file_path, "--fullscreen"]
|
|||
|
|
|
|||
|
|
subprocess.Popen(
|
|||
|
|
cmd,
|
|||
|
|
shell=False,
|
|||
|
|
stdout=subprocess.DEVNULL,
|
|||
|
|
stderr=subprocess.DEVNULL,
|
|||
|
|
cwd=os.path.dirname(viewer_path) if is_exe else None
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
if hasattr(window, 'logger'):
|
|||
|
|
window.logger.info(f"已启动看板查看器: {viewer_path} {file_path}")
|
|||
|
|
|
|||
|
|
except Exception as e:
|
|||
|
|
QMessageBox.critical(window, "错误", f"启动看板失败: {str(e)}")
|
|||
|
|
if hasattr(window, 'logger'):
|
|||
|
|
window.logger.error(f"启动看板失败: {e}")
|