# connection_manager.py """连接管理器:负责 MT2-AM8 模块 (Modbus TCP) 的连接/断开。 纯业务逻辑,无 UI 依赖。通过回调与 UI 层通信。 """ import time from PcControl import MT2AM8Client class ConnectionManager: """管理 MT2-AM8 模块连接的生命周期""" def __init__(self): self.modbus_client = None # MT2AM8Client (TCP 读压力/流量,控电机) self._pressure_addr = 0 # 压力传感器模拟量通道地址 self._flowmeter_addr = None # 流量计模拟量通道地址(None=使用手动输入) self._motor_addr = 0 # 电机模拟量输出通道地址 self._on_log = None # 日志回调 self._on_status_change = None # 状态变化回调 def set_log_callback(self, callback): """设置日志回调: callback(message: str)""" self._on_log = callback def set_status_callback(self, callback): """设置状态变化回调: callback(connected: bool, status_text: str)""" self._on_status_change = callback def log(self, message): """内部日志输出""" if self._on_log: self._on_log(message) def is_connected(self) -> bool: """检查是否已连接""" return self.modbus_client is not None and self.modbus_client.connected def connect(self, tcp_ip: str, tcp_port: int, pressure_addr: int, motor_addr: int, flowmeter_addr: int, pressure_range: float = 400, flow_range: float = 100) -> bool: """连接到 MT2-AM8 模块 Args: tcp_ip: 模块 IP 地址 tcp_port: TCP 端口 pressure_addr: 压力传感器模拟量通道地址 motor_addr: 电机模拟量输出通道地址 flowmeter_addr: 流量计模拟量通道地址 pressure_range: 压力表量程上限 flow_range: 流量计量程上限 Returns: 是否连接成功 """ try: self.log("正在连接设备...") # 保存地址配置 self._pressure_addr = pressure_addr self._motor_addr = motor_addr self._flowmeter_addr = flowmeter_addr # 创建 MT2-AM8 客户端 self.modbus_client = MT2AM8Client( host=tcp_ip, port=tcp_port, pressure_range=pressure_range, flow_range=flow_range, ) if not self.modbus_client.connect(): self.log(f"连接 MT2-AM8 模块失败: {tcp_ip}:{tcp_port}") return False self.log(f"成功连接到 MT2-AM8 模块: {tcp_ip}:{tcp_port}") self.log(f"压力地址: {pressure_addr}, 电机地址: {motor_addr}, 流量计地址: {flowmeter_addr}") if self._on_status_change: self._on_status_change(True, "已连接") return True except Exception as e: self.log(f"连接异常: {str(e)}") return False def disconnect(self): """断开连接""" if self.modbus_client: self.modbus_client.disconnect() self.modbus_client = None self.log("已断开连接") if self._on_status_change: self._on_status_change(False, "未连接") def read_pressure(self): """读取当前压力值(转换为实际物理量) Returns: 实际压力值 (kPa), 读取失败返回 None """ if not self.is_connected(): return None return self.modbus_client.get_pressure(self._pressure_addr) def read_flow(self): """读取当前流量值(转换为实际物理量) 若未配置流量计地址,直接返回 None,由调用方使用控制栏手动输入值。 Returns: 实际流量值 (L/min), 未配置地址或读取失败返回 None """ if not self.is_connected() or self._flowmeter_addr is None: return None return self.modbus_client.get_flow(self._flowmeter_addr) def set_motor_position(self, xa: float) -> bool: """设置电机位置(通过模拟量输出控制阀门开度) Args: xa: 目标行程 (0~x_max) Returns: 是否设置成功 """ if not self.is_connected(): return False return self.modbus_client.set_motor_position(xa, channel=self._motor_addr)