173 lines
5.9 KiB
Python
173 lines
5.9 KiB
Python
|
|
from PySide6.QtWidgets import (
|
||
|
|
QMainWindow, QWidget, QVBoxLayout, QHBoxLayout,
|
||
|
|
QScrollArea, QPushButton, QMessageBox, QLabel, QScroller
|
||
|
|
)
|
||
|
|
from PySide6.QtCore import Qt, QTimer
|
||
|
|
from ui.inspection_card import InspectionCard
|
||
|
|
from ui.incoming_inspection_page import IncomingInspectionPage
|
||
|
|
from ui.manual_inspection_page import ManualInspectionPage
|
||
|
|
from src.db_manager import DatabaseManager
|
||
|
|
from src.session_manager import SessionManager
|
||
|
|
|
||
|
|
class InspectionWindow(QMainWindow):
|
||
|
|
def __init__(self):
|
||
|
|
super().__init__()
|
||
|
|
self.setWindowTitle("检验管理系统")
|
||
|
|
|
||
|
|
# 初始化数据库管理器和分页参数
|
||
|
|
self.db_manager = DatabaseManager()
|
||
|
|
self.session_manager = SessionManager()
|
||
|
|
self.current_page = 0
|
||
|
|
self.page_size = 10
|
||
|
|
self.is_loading = False
|
||
|
|
self.has_more_data = True
|
||
|
|
|
||
|
|
# Central Widget
|
||
|
|
central_widget = QWidget()
|
||
|
|
self.setCentralWidget(central_widget)
|
||
|
|
|
||
|
|
# Main Layout
|
||
|
|
main_layout = QVBoxLayout(central_widget)
|
||
|
|
main_layout.setContentsMargins(0, 0, 0, 0)
|
||
|
|
main_layout.setSpacing(0)
|
||
|
|
|
||
|
|
# Scroll Area for Cards
|
||
|
|
self.scroll_area = QScrollArea()
|
||
|
|
self.scroll_area.setWidgetResizable(True)
|
||
|
|
self.scroll_area.setStyleSheet("background-color: #f0f0f0; border: none;")
|
||
|
|
|
||
|
|
self.cards_container = QWidget()
|
||
|
|
self.cards_container.setStyleSheet("background-color: white;")
|
||
|
|
self.cards_layout = QVBoxLayout(self.cards_container)
|
||
|
|
self.cards_layout.setContentsMargins(10, 10, 10, 10)
|
||
|
|
self.cards_layout.setSpacing(15)
|
||
|
|
|
||
|
|
# 加载提示标签
|
||
|
|
self.loading_label = QLabel("加载中...")
|
||
|
|
self.loading_label.setAlignment(Qt.AlignCenter)
|
||
|
|
self.loading_label.setStyleSheet("color: #666; padding: 10px;")
|
||
|
|
self.loading_label.hide()
|
||
|
|
self.cards_layout.addWidget(self.loading_label)
|
||
|
|
|
||
|
|
self.cards_layout.addStretch() # Push items to top
|
||
|
|
|
||
|
|
self.scroll_area.setWidget(self.cards_container)
|
||
|
|
|
||
|
|
# 启用触摸滚动
|
||
|
|
QScroller.grabGesture(self.scroll_area.viewport(), QScroller.LeftMouseButtonGesture)
|
||
|
|
|
||
|
|
# 连接滚动条信号
|
||
|
|
self.scroll_area.verticalScrollBar().valueChanged.connect(self.on_scroll)
|
||
|
|
|
||
|
|
main_layout.addWidget(self.scroll_area)
|
||
|
|
|
||
|
|
button_bar = QWidget()
|
||
|
|
button_bar.setStyleSheet("background-color: #e0e0e0; border-top: 1px solid #999;")
|
||
|
|
button_layout = QHBoxLayout(button_bar)
|
||
|
|
button_layout.setContentsMargins(20, 15, 20, 15)
|
||
|
|
button_layout.setSpacing(20)
|
||
|
|
|
||
|
|
# 按钮样式
|
||
|
|
btn_style = """
|
||
|
|
QPushButton {
|
||
|
|
background-color: #0086fa;
|
||
|
|
color: white;
|
||
|
|
border-radius: 5px;
|
||
|
|
padding: 15px;
|
||
|
|
font-family: 'Microsoft YaHei';
|
||
|
|
font-size: 19px;
|
||
|
|
font-weight: bold;
|
||
|
|
}
|
||
|
|
QPushButton:pressed {
|
||
|
|
background-color: #006bbd;
|
||
|
|
}
|
||
|
|
"""
|
||
|
|
|
||
|
|
self.btn_incoming = QPushButton("入检")
|
||
|
|
self.btn_incoming.setStyleSheet(btn_style)
|
||
|
|
self.btn_incoming.clicked.connect(lambda: self.show_dialog("入检"))
|
||
|
|
|
||
|
|
self.btn_manual = QPushButton("手检")
|
||
|
|
self.btn_manual.setStyleSheet(btn_style)
|
||
|
|
self.btn_manual.clicked.connect(lambda: self.show_dialog("手检"))
|
||
|
|
|
||
|
|
button_layout.addWidget(self.btn_incoming)
|
||
|
|
button_layout.addWidget(self.btn_manual)
|
||
|
|
|
||
|
|
main_layout.addWidget(button_bar)
|
||
|
|
|
||
|
|
def add_card(self, data):
|
||
|
|
card = InspectionCard(data)
|
||
|
|
count = self.cards_layout.count()
|
||
|
|
# 插入到 loading_label 之前
|
||
|
|
self.cards_layout.insertWidget(count - 2, card)
|
||
|
|
|
||
|
|
def on_scroll(self, value):
|
||
|
|
"""滚动条事件处理"""
|
||
|
|
scrollbar = self.scroll_area.verticalScrollBar()
|
||
|
|
# 当滚动到底部附近时触发加载
|
||
|
|
if value >= scrollbar.maximum() - 50 and not self.is_loading and self.has_more_data:
|
||
|
|
self.load_more_data()
|
||
|
|
|
||
|
|
def load_more_data(self):
|
||
|
|
"""加载更多数据"""
|
||
|
|
if self.is_loading or not self.has_more_data:
|
||
|
|
return
|
||
|
|
|
||
|
|
self.is_loading = True
|
||
|
|
self.loading_label.show()
|
||
|
|
|
||
|
|
# 使用 QTimer 异步加载,避免阻塞 UI
|
||
|
|
QTimer.singleShot(100, self._fetch_data)
|
||
|
|
|
||
|
|
def _fetch_data(self):
|
||
|
|
"""从数据库获取数据"""
|
||
|
|
offset = self.current_page * self.page_size
|
||
|
|
user_id = self.session_manager.get_user_id() or ''
|
||
|
|
rows, error = self.db_manager.get_inspection_list(self.page_size, offset, user_id=user_id)
|
||
|
|
|
||
|
|
if error:
|
||
|
|
self.loading_label.setText(f"加载失败: {error}")
|
||
|
|
self.is_loading = False
|
||
|
|
QTimer.singleShot(2000, lambda: self.loading_label.hide())
|
||
|
|
return
|
||
|
|
|
||
|
|
if not rows or len(rows) == 0:
|
||
|
|
self.has_more_data = False
|
||
|
|
self.loading_label.setText("没有更多数据")
|
||
|
|
QTimer.singleShot(1000, lambda: self.loading_label.hide())
|
||
|
|
else:
|
||
|
|
for row in rows:
|
||
|
|
self.add_card(dict(row))
|
||
|
|
|
||
|
|
self.current_page += 1
|
||
|
|
|
||
|
|
if len(rows) < self.page_size:
|
||
|
|
self.has_more_data = False
|
||
|
|
|
||
|
|
self.loading_label.hide()
|
||
|
|
|
||
|
|
self.is_loading = False
|
||
|
|
|
||
|
|
def load_initial_data(self):
|
||
|
|
"""加载初始数据"""
|
||
|
|
self.current_page = 0
|
||
|
|
self.has_more_data = True
|
||
|
|
self.load_more_data()
|
||
|
|
|
||
|
|
def show_dialog(self, title):
|
||
|
|
if title == "入检":
|
||
|
|
page = IncomingInspectionPage(self)
|
||
|
|
page.showMaximized()
|
||
|
|
page.exec()
|
||
|
|
elif title == "手检":
|
||
|
|
page = ManualInspectionPage(self)
|
||
|
|
page.showMaximized()
|
||
|
|
page.exec()
|
||
|
|
else:
|
||
|
|
msg = QMessageBox(self)
|
||
|
|
msg.setWindowTitle(title)
|
||
|
|
msg.setText(f"{title} - 功能开发中")
|
||
|
|
msg.setStandardButtons(QMessageBox.Ok)
|
||
|
|
msg.exec()
|