# connection_tab.py """页面1:Modbus TCP 连接参数设置""" import os from PySide6.QtWidgets import ( QWidget, QVBoxLayout, QHBoxLayout, QGridLayout, QLabel, QLineEdit, QPushButton, QFrame, QSizePolicy, QGraphicsDropShadowEffect ) from PySide6.QtCore import Qt, QSize from PySide6.QtGui import QColor, QIcon _SRC_DIR = os.path.normpath(os.path.join(os.path.dirname(__file__), "..", "src")) # ========================================== # 工具函数:创建带左侧蓝色竖线的 Section 卡片 # ========================================== def _make_section_card(parent, title_text: str, colors: dict): card = QFrame(parent) card.setProperty("cssClass", "sectionCard") card.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Preferred) # 添加微弱的模糊阴影效果 shadow = QGraphicsDropShadowEffect(card) shadow.setColor(QColor(0, 0, 0, 12)) shadow.setBlurRadius(16) shadow.setOffset(0, 4) card.setGraphicsEffect(shadow) outer = QVBoxLayout(card) outer.setContentsMargins(0, 0, 0, 0) outer.setSpacing(0) # ---- 标题行(蓝色左竖线 + 标题文字) ---- title_row = QHBoxLayout() title_row.setContentsMargins(20, 16, 20, 0) title_row.setSpacing(10) accent = QWidget() accent.setProperty("cssClass", "sectionAccent") accent.setFixedSize(4, 16) title_row.addWidget(accent) title_lbl = QLabel(title_text) title_lbl.setProperty("cssClass", "sectionTitle") title_row.addWidget(title_lbl) title_row.addStretch() outer.addLayout(title_row) # ---- 内容区 ---- content_widget = QWidget() content_widget.setStyleSheet("background-color: transparent;") content_layout = QGridLayout(content_widget) content_layout.setContentsMargins(20, 14, 20, 18) content_layout.setHorizontalSpacing(0) content_layout.setVerticalSpacing(10) # 列0(标签)固定宽度,列1(输入框)拉伸 content_layout.setColumnMinimumWidth(0, 148) content_layout.setColumnStretch(1, 1) outer.addWidget(content_widget) return card, content_layout # ========================================== # 工具函数:创建表单标签(左对齐) # ========================================== def _form_label(text: str, parent=None): lbl = QLabel(text, parent) lbl.setProperty("cssClass", "formLabel") lbl.setAlignment(Qt.AlignLeft | Qt.AlignVCenter) return lbl class ConnectionTab(QWidget): """连接设置页面""" def __init__(self, colors: dict, parent=None): super().__init__(parent) self.setProperty("cssClass", "tabPage") self.colors = colors main_layout = QVBoxLayout(self) main_layout.setContentsMargins(20, 16, 20, 16) main_layout.setSpacing(14) # ========================================== # Section: Modbus TCP # ========================================== tcp_card, tcp_layout = _make_section_card(self, "Modbus TCP", colors) self._build_tcp_section(tcp_layout) main_layout.addWidget(tcp_card) # ========================================== # 按钮组 # ========================================== btn_row = QHBoxLayout() btn_row.setContentsMargins(0, 4, 0, 0) btn_row.setSpacing(12) # 连接设备按钮 self.connect_btn = QPushButton(" 连接设备") self.connect_btn.setObjectName("connect_btn") self.connect_btn.setIcon(QIcon(os.path.join(_SRC_DIR, "connect_device.svg"))) self.connect_btn.setIconSize(QSize(18, 18)) self.connect_btn.setCursor(Qt.PointingHandCursor) # 保存按钮引用(connect/disconnect 切换文字时使用) self._connect_text_lbl = self.connect_btn btn_row.addWidget(self.connect_btn) btn_row.addStretch() main_layout.addLayout(btn_row) main_layout.addStretch() # ========================================== # Modbus TCP 表单 # ========================================== def _build_tcp_section(self, grid: QGridLayout): row = 0 grid.addWidget(_form_label("模块地址:", self), row, 0) self.tcp_ip_entry = QLineEdit("192.168.1.12") self.tcp_ip_entry.setPlaceholderText("输入模块 IP地址") grid.addWidget(self.tcp_ip_entry, row, 1) row += 1 grid.addWidget(_form_label("端口:", self), row, 0) self.tcp_port_entry = QLineEdit("502") self.tcp_port_entry.setPlaceholderText("默认502") grid.addWidget(self.tcp_port_entry, row, 1) row += 1 grid.addWidget(_form_label("读取压力寄存器地址:", self), row, 0) self.pressure_addr_entry = QLineEdit("0") self.pressure_addr_entry.setPlaceholderText("寄存器地址") grid.addWidget(self.pressure_addr_entry, row, 1) row += 1 grid.addWidget(_form_label("电机地址:", self), row, 0) self.motor_addr_entry = QLineEdit("0") self.motor_addr_entry.setPlaceholderText("电机模拟量通道地址") grid.addWidget(self.motor_addr_entry, row, 1) row += 1 grid.addWidget(_form_label("流量计地址:", self), row, 0) self.flowmeter_addr_entry = QLineEdit("1") self.flowmeter_addr_entry.setPlaceholderText("留空则使用手动输入流量") grid.addWidget(self.flowmeter_addr_entry, row, 1) row += 1 grid.addWidget(_form_label("压力表量程:", self), row, 0) self.pressure_range_entry = QLineEdit("400") self.pressure_range_entry.setPlaceholderText("压力传感器量程上限") grid.addWidget(self.pressure_range_entry, row, 1) row += 1 grid.addWidget(_form_label("流量计量程:", self), row, 0) self.flow_range_entry = QLineEdit("300") self.flow_range_entry.setPlaceholderText("流量计量程上限") grid.addWidget(self.flow_range_entry, row, 1) # ---- 公开方法 ---- def get_connection_params(self) -> dict: flow_str = self.flowmeter_addr_entry.text().strip() return { "tcp_ip": self.tcp_ip_entry.text().strip(), "tcp_port": int(self.tcp_port_entry.text() or "502"), "pressure_addr": int(self.pressure_addr_entry.text() or "504"), "motor_addr": int(self.motor_addr_entry.text() or "0"), "flowmeter_addr": int(flow_str) if flow_str else None, "pressure_range": float(self.pressure_range_entry.text() or "400"), "flow_range": float(self.flow_range_entry.text() or "300"), }