package com.mes.plc; import com.alibaba.fastjson2.JSONObject; import com.mes.component.StationPanel; import com.mes.ui.DataUtil; import com.mes.ui.MesClient; import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** * 氦检单工位流程: * M205 上升沿 → 读条码 → 复位 M205 → 校验 → 写 M206 * M207 上升沿 → 清 M206 → 检测中 * M208 上升沿 → 读泄露 → 显示结果 * * 开始/结束信号是保持电平,只在 0→1 时触发 */ public class HeliumFlow { private static final Logger log = LoggerFactory.getLogger(HeliumFlow.class); private final int station; private final McPlcClient plc; private final StationPanel ui; private final String scanAddr; private final String allowAddr; private final String startAddr; private final String endAddr; private final String leakAddr; private final String codeAddr; private boolean initialized = false; private boolean lastScan = false; // 启动时若已扫码,也要处理 private boolean lastStart; private boolean lastEnd; private String currentSn = ""; public HeliumFlow(int station, McPlcClient plc, StationPanel ui, String scanAddr, String allowAddr, String startAddr, String endAddr, String leakAddr, String codeAddr) { this.station = station; this.plc = plc; this.ui = ui; this.scanAddr = scanAddr; this.allowAddr = allowAddr; this.startAddr = startAddr; this.endAddr = endAddr; this.leakAddr = leakAddr; this.codeAddr = codeAddr; } private String name() { return station == 2 ? "B" : "A"; } /** 启动时同步开始/结束信号的当前电平,避免误触发 */ private void init() { Boolean start = plc.tryReadBit(startAddr); Boolean end = plc.tryReadBit(endAddr); if (start == null || end == null) { return; // 通信未就绪,下轮再同步 } lastStart = start; lastEnd = end; initialized = true; log.info(name() + " 工位流程初始化: start=" + start + " end=" + end); } public void poll() { if (!initialized) { init(); return; } if (!plc.isConnected()) { initialized = false; return; } Boolean scan = plc.tryReadBit(scanAddr); Boolean start = plc.tryReadBit(startAddr); Boolean end = plc.tryReadBit(endAddr); if (scan == null || start == null || end == null) { return; // 本轮通信异常,跳过 } if (scan && !lastScan) { onScan(); } lastScan = scan; if (start && !lastStart) { onStart(); } lastStart = start; if (end && !lastEnd) { onEnd(); } lastEnd = end; } /** 扫码:读码 → 复位扫码信号 → 查质量 → 写允许位 */ private void onScan() { String code = plc.readString(codeAddr, MesClient.plc_code_len); if (code == null || code.isEmpty()) { MesClient.addLog(name() + " 扫码信号已到,但条码为空,等待重试"); return; } currentSn = code; ui.setCode(code); ui.setSignal(StationPanel.SIG_SCAN, true); ui.setSignal(StationPanel.SIG_CODE, true); ui.setState("校验中", StationPanel.STATE_BUSY); MesClient.addLog(name() + " 读到条码 " + code); // 读码成功后复位扫码成功信号 plc.writeBit(scanAddr, false); MesClient.getUser(); JSONObject ret = DataUtil.checkQuality(code, MesClient.user20); boolean allow = ret != null && "true".equalsIgnoreCase(String.valueOf(ret.get("result"))); plc.writeBit(allowAddr, allow); ui.setSignal(StationPanel.SIG_ALLOW, allow); if (allow) { ui.setState("允许运行", StationPanel.STATE_OK); MesClient.addLog(name() + " 校验通过,允许运行"); } else { currentSn = ""; // 禁止运行,不参与后续提交 ui.setState("禁止运行", StationPanel.STATE_NG); String msg = ret == null ? "请求失败" : ret.getString("message"); MesClient.addLog(name() + " 禁止运行:" + msg); } } /** 检测开始:清允许位,界面进入检测中 */ private void onStart() { plc.writeBit(allowAddr, false); ui.setSignal(StationPanel.SIG_ALLOW, false); ui.setSignal(StationPanel.SIG_START, true); ui.setState("检测中", StationPanel.STATE_RUN); MesClient.addLog(name() + " 检测开始"); } /** 检测结束:读泄露,提交结果 */ private void onEnd() { String leak = plc.readString(leakAddr, 8); ui.setData(null, leak); ui.setSignal(StationPanel.SIG_LEAK, !leak.isEmpty()); ui.setSignal(StationPanel.SIG_END, true); MesClient.addLog(name() + " 检测结束,泄露=" + leak); if (currentSn.isEmpty()) { MesClient.addLog(name() + " 无当前条码,跳过提交"); return; } // 设备判定结果点位待补,当前按 OK 提交 String result = "OK"; ui.setState("上传中", StationPanel.STATE_BUSY); MesClient.getUser(); JSONObject ret = DataUtil.sendQuality(currentSn, result, MesClient.user20); boolean ok = ret != null && "true".equalsIgnoreCase(String.valueOf(ret.get("result"))); if (ok) { ui.setResult(result); ui.setState("检测完成", StationPanel.STATE_OK); MesClient.addLog(name() + " 结果已提交 " + currentSn + " " + result); } else { ui.setState("提交失败", StationPanel.STATE_NG); MesClient.addLog(name() + " 结果提交失败:" + (ret == null ? "请求失败" : ret.getString("message"))); } } }