using MaterialTraceability.Common; using MaterialTraceability.Entity.DTO; using MaterialTraceability.Plc; using System; using System.Collections.Generic; using System.Linq; using System.Reflection; using System.Text; using System.Threading; using System.Threading.Tasks; namespace MaterialTraceability.Business { /// /// PLC业务类 /// public class PlcBusiness { private static IPlc plcInstance = null; private static AppConfigDto appConfig = AppConfigDto.Instance; #region 定义间隔判断时间 private static DateTime lastReadTime_A_Begin; private static DateTime lastReadTime_A_End; private static DateTime lastReadTime_B_Begin; private static DateTime lastReadTime_B_End; private static DateTime lastReadTime_Force; private static DateTime lastReadTime_ForceSecond; //模切暂用 #endregion /// /// 信号刷新事件 /// /// public delegate void SignalReadRefresh(int status, int position); public event SignalReadRefresh SignalRefreshEvent; private static System.Timers.Timer timer = new System.Timers.Timer(appConfig.plcSingalReadTime); public void EndSignalInit(int status, int position) { SignalRefreshEvent?.Invoke(status, position); } /// /// 初始化PLC /// /// /// public IPlc InitPlc(string PLCType) { try { string str = System.Environment.CurrentDirectory; str = str + "\\MaterialTraceability.Plc.dll"; Assembly assembly = Assembly.LoadFile(str); // 加载程序集(EXE 或 DLL) string AssemName = "MaterialTraceability.Plc.Impl." + PLCType; var obj = assembly.CreateInstance(AssemName, true); plcInstance = obj as IPlc; if (plcInstance == null) { LogHelper.Info("PLC初始化失败!!!"); return null; } else { LogHelper.Info("PLC初始化成功"); #region 读取时间初始化 var initTime = DateTime.Now.AddMinutes(-1); lastReadTime_A_Begin = initTime; lastReadTime_A_End = initTime; lastReadTime_B_Begin = initTime; lastReadTime_B_End = initTime; lastReadTime_Force = initTime; lastReadTime_ForceSecond = initTime; #endregion return plcInstance; } } catch (Exception ex) { LogHelper.Error("PLC初始化异常", ex); return null; } } public bool Connect() { if (!plcInstance.IsConnected) { bool connectResult = plcInstance.Connect(appConfig.plcAddress, appConfig.plcPort); return connectResult; } return plcInstance.IsConnected; } /// /// 获取PLC连接状态 /// /// public bool IsConnected() { return plcInstance.IsConnected; } public bool ReConnect() { try { if (plcInstance.IsConnected) { if (plcInstance.DisConnect()) { LogHelper.PlcLog("PLC断开成功"); } } //断开后关闭定时器 if (timer.Enabled) { timer.Stop(); timer.Close(); timer.Dispose(); timer = new System.Timers.Timer(appConfig.plcSingalReadTime); } LogHelper.PlcLog("定时器关闭,等待2S后进行重连"); Thread.Sleep(1000 * 2); if (Connect()) { LogHelper.PlcLog("PLC连接成功,开启定时器"); LoopRead(""); } } catch(Exception ex) { LogHelper.Error("PLC重连异常",ex); } var result = plcInstance.IsConnected; return result; } /// /// 开启线程循环读取PLC地址 /// /// public void LoopRead(string address) { timer.Elapsed += new System.Timers.ElapsedEventHandler(readPlc); timer.AutoReset = true; timer.Enabled = true; timer.Start(); } /// /// 读取PLC信号 object source, System.Timers.ElapsedEventArgs e /// /// /// private void readPlc(object source, System.Timers.ElapsedEventArgs e) { try { //获取工序编号 TB-涂布、LY冷压预分切、MQ-模切、JR-卷绕 string processCode = appConfig.processId; #region 涂布 if (processCode.Equals("TB")) { lock (string.Empty) { //写入心跳 plcInstance.writeInt32ByAddress("D9628", 1); LogHelper.PlcLog("RFID系统写入心跳D9628"); Thread.Sleep(200); // A轴收卷涨紧 A轴position设为1 if (plcInstance.readInt32ByAddress("D9600") == 1) { LogHelper.PlcLog("A轴收卷涨紧"); plcInstance.writeInt32ByAddress("D9604", 1); plcInstance.writeInt32ByAddress("D9600", 0); if (isReadFlag(ref lastReadTime_A_Begin)) { SignalRefreshEvent?.Invoke(3, 1); } } // B轴收卷涨紧 B轴position设为2 if (plcInstance.readInt32ByAddress("D9620") == 1) { LogHelper.PlcLog("B轴收卷涨紧"); plcInstance.writeInt32ByAddress("D9604", 1); plcInstance.writeInt32ByAddress("D9620", 0); if (isReadFlag(ref lastReadTime_B_Begin)) { SignalRefreshEvent?.Invoke(3, 2); } } #region 收卷开始信号 Add By wenjy 2022-11-29 // A轴收卷开始信号 if (plcInstance.readInt32ByAddress("D9720") == 1) { LogHelper.PlcLog("A轴收卷开始信号 D9720==1 -> 0"); plcInstance.writeInt32ByAddress("D9720", 0); if (isReadFlag(ref lastReadTime_A_End)) { SignalRefreshEvent?.Invoke(7, 1); } } // B轴收卷开始信号 if (plcInstance.readInt32ByAddress("D9720") == 2) { LogHelper.PlcLog("B轴收卷开始信号 D9720==2 -> 0"); plcInstance.writeInt32ByAddress("D9720", 0); if (isReadFlag(ref lastReadTime_B_End)) { SignalRefreshEvent?.Invoke(7, 2); } } #endregion // A轴收卷完工信号 if (plcInstance.readInt32ByAddress("D9606") == 1) { LogHelper.PlcLog("A轴收卷完工信号"); plcInstance.writeInt32ByAddress("D9614", 1); plcInstance.writeInt32ByAddress("D9606", 0); if (isReadFlag(ref lastReadTime_A_End)) { SignalRefreshEvent?.Invoke(4, 1); } } // B轴收卷完工信号 if (plcInstance.readInt32ByAddress("D9626") == 1) { LogHelper.PlcLog("B轴收卷完工信号"); plcInstance.writeInt32ByAddress("D9614", 1); plcInstance.writeInt32ByAddress("D9626", 0); if (isReadFlag(ref lastReadTime_B_End)) { SignalRefreshEvent?.Invoke(4, 2); } } //A轴强制下料 if (plcInstance.readInt32ByAddress("D9618") == 1) { LogHelper.PlcLog("A轴强制下料"); plcInstance.writeInt32ByAddress("D9618", 0); if (isReadFlag(ref lastReadTime_Force)) { SignalRefreshEvent?.Invoke(5, 1); } } //B轴强制下料 if (plcInstance.readInt32ByAddress("D9618") == 2) { LogHelper.PlcLog("B轴强制下料"); plcInstance.writeInt32ByAddress("D9618", 0); if (isReadFlag(ref lastReadTime_Force)) { SignalRefreshEvent?.Invoke(5, 2); } } } } #endregion #region 冷压 //冷压工序、赢合厂家 if (processCode.Equals("LY_A")) { //if (plcInstance.readInt32ByAddress("D6125") == 1) //{ // plcInstance.writeInt32ByAddress("D6125", 0); // SignalRefreshEvent?.Invoke(8, 0); //} //放卷 涨紧信号 if (plcInstance.readInt32ByAddress("D6005") == 1) { plcInstance.writeInt32ByAddress("D6005", 0); SignalRefreshEvent?.Invoke(1, 0); } //放卷结束信号 if (plcInstance.readInt32ByAddress("D6000") == 1) { plcInstance.writeInt32ByAddress("D6000", 0); SignalRefreshEvent?.Invoke(2, 0); } //收卷涨紧信号-1A气胀轴 if (plcInstance.readInt32ByAddress("D6006") == 1) { plcInstance.writeInt32ByAddress("D6006", 0); SignalRefreshEvent?.Invoke(3, 1); } //收卷涨紧信号-1B气胀轴 if (plcInstance.readInt32ByAddress("D6007") == 1) { plcInstance.writeInt32ByAddress("D6007", 0); SignalRefreshEvent?.Invoke(3, 2); } //收卷涨紧信号-2A气胀轴 if (plcInstance.readInt32ByAddress("D6008") == 1) { plcInstance.writeInt32ByAddress("D6008", 0); SignalRefreshEvent?.Invoke(3, 3); } //收卷涨紧信号-2B气胀轴 if (plcInstance.readInt32ByAddress("D6009") == 1) { plcInstance.writeInt32ByAddress("D6009", 0); SignalRefreshEvent?.Invoke(3, 4); } //收卷结束信号-1A气胀轴 if (plcInstance.readInt32ByAddress("D6001") == 1) { lock (string.Empty) { plcInstance.writeInt32ByAddress("D6001", 0); SignalRefreshEvent?.Invoke(4, 1); } } //收卷结束信号-1B气胀轴 if (plcInstance.readInt32ByAddress("D6002") == 1) { lock (string.Empty) { plcInstance.writeInt32ByAddress("D6002", 0); SignalRefreshEvent?.Invoke(4, 2); } } //收卷结束信号-2A气胀轴 if (plcInstance.readInt32ByAddress("D6003") == 1) { lock (string.Empty) { plcInstance.writeInt32ByAddress("D6003", 0); SignalRefreshEvent?.Invoke(4, 3); } } //收卷结束信号-2B气胀轴 if (plcInstance.readInt32ByAddress("D6004") == 1) { lock (string.Empty) { plcInstance.writeInt32ByAddress("D6004", 0); SignalRefreshEvent?.Invoke(4, 4); } } //异常下料-1A if (plcInstance.readInt32ByAddress("D6116") == 1) { plcInstance.writeInt32ByAddress("D6116", 0); SignalRefreshEvent?.Invoke(5, 1); } //异常下料-1B if (plcInstance.readInt32ByAddress("D6117") == 1) { plcInstance.writeInt32ByAddress("D6117", 0); SignalRefreshEvent?.Invoke(5, 2); } //异常下料-2A if (plcInstance.readInt32ByAddress("D6118") == 1) { plcInstance.writeInt32ByAddress("D6118", 0); SignalRefreshEvent?.Invoke(5, 3); } //异常下料-2B if (plcInstance.readInt32ByAddress("D6119") == 1) { plcInstance.writeInt32ByAddress("D6119", 0); SignalRefreshEvent?.Invoke(5, 4); } } #endregion #region 模切 if (processCode.Equals("MQ_A")) { //开机启动信号 Add By WenJy 2022-10-12 if (plcInstance.readInt32ByAddress("MW25678") == 1) { plcInstance.writeInt32ByAddress("MW25678", 0); SignalRefreshEvent?.Invoke(8, 0); } //左放卷 涨紧信号 if (plcInstance.readInt32ByAddress("MW24800") == 1) { plcInstance.writeInt32ByAddress("MW24800", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(1, 6); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(1, 5); } } //右放卷 涨紧信号 if (plcInstance.readInt32ByAddress("MW24802") == 1) { plcInstance.writeInt32ByAddress("MW24802", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(1, 5); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(1, 6); } } //左放卷 开始信号 if (plcInstance.readBoolByAddress("MW1021.2")) { if (isReadFlag(ref lastReadTime_A_Begin)) { LogHelper.PlcLog("读到左放卷开始信号"); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(6, 6); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(6, 5); } } } //右放卷 开始信号 if (plcInstance.readBoolByAddress("MW1021.6")) { if (isReadFlag(ref lastReadTime_A_End)) { LogHelper.PlcLog("读到右放卷开始信号"); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(6, 5); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(6, 6); } } } //左放卷 结束信号 if (plcInstance.readInt32ByAddress("MW24844") == 1) { writePlc("MW24844", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(2, 6); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(2, 5); } } //右放卷 结束信号 if (plcInstance.readInt32ByAddress("MW24846") == 1) { if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(2, 5); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(2, 6); } writePlc("MW24846", 0); } //上收卷左侧涨紧 信号 if (plcInstance.readInt32ByAddress("MW24804") == 1) { plcInstance.writeInt32ByAddress("MW24804", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(3, 3); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(3, 1); } } //上收卷右侧涨紧 信号 if (plcInstance.readInt32ByAddress("MW24806") == 1) { plcInstance.writeInt32ByAddress("MW24806", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(3, 1); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(3, 3); } } //下收卷左侧涨紧 信号 if (plcInstance.readInt32ByAddress("MW24808") == 1) { plcInstance.writeInt32ByAddress("MW24808", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(3, 4); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(3, 2); } } //下收卷右侧涨紧 信号 if (plcInstance.readInt32ByAddress("MW24810") == 1) { plcInstance.writeInt32ByAddress("MW24810", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(3, 2); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(3, 4); } } //上收卷左侧开始信号 if (plcInstance.readBoolByAddress("MW1022.2")) { if (isReadFlag(ref lastReadTime_B_Begin)) { if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(7, 3); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(7, 1); } } } //上收卷右侧开始信号 if (plcInstance.readBoolByAddress("MW1022.6")) { if (isReadFlag(ref lastReadTime_B_End)) { if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(7, 1); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(7, 3); } } } //下收卷左侧开始信号 if (plcInstance.readBoolByAddress("MW1023.2")) { if (isReadFlag(ref lastReadTime_Force)) { if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(7, 4); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(7, 2); } } } //下收卷右侧开始信号 if (plcInstance.readBoolByAddress("MW1023.6")) { if (isReadFlag(ref lastReadTime_ForceSecond)) { if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(7, 2); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(7, 4); } } } //上左收卷结束信号 if (plcInstance.readInt32ByAddress("MW24848") == 1) { writePlc("MW24848", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(4, 3); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(4, 1); } } //上右收卷结束信号 if (plcInstance.readInt32ByAddress("MW24850") == 1) { writePlc("MW24850", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(4, 1); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(4, 3); } } //下左收卷结束 if (plcInstance.readInt32ByAddress("MW24852") == 1) { writePlc("MW24852", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(4, 4); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(4, 2); } } //下右收卷结束 if (plcInstance.readInt32ByAddress("MW24854") == 1) { writePlc("MW24854", 0); if (appConfig.machineId == 3) { SignalRefreshEvent?.Invoke(4, 2); } if (appConfig.machineId == 4) { SignalRefreshEvent?.Invoke(4, 4); } } } #endregion } catch (Exception ex) { LogHelper.Error("读取PLC信号异常",ex); } } /// /// 根据时间差判断信号是否处理 /// /// /// public static bool isReadFlag(ref DateTime lastReadTime) { DateTime nowReadTime = DateTime.Now; TimeSpan info = nowReadTime - lastReadTime; int elapsedTime = Convert.ToInt32(info.TotalSeconds); LogHelper.PlcLog("开始时间:" + lastReadTime.ToString("G") + ";结束时间:" + nowReadTime.ToString("G") + ";时间差:" + elapsedTime); if (elapsedTime < 30) { LogHelper.PlcLog("距离上次读取时间小于30S,不触发逻辑处理"); return false; } else { //上次读取时间 lastReadTime = nowReadTime; return true; } } /// /// PLC地址写入 /// /// /// public void writePlc(string address,int value) { plcInstance.writeInt32ByAddress(address, value); } /// /// 写入String类型数据 /// /// /// public static void writeStrPlc(string address, string value) { plcInstance.writeStringByAddress(address, value); } /// /// 写入double类型 /// /// /// public void writeDoublePlc(string address, int value) { plcInstance.writeDoubleByAddress(address, value); } /// /// 读取String类型数据 /// /// /// public static string readStrPlc(string address,ushort length) { return plcInstance.readStringByAddress(address, length); } /// /// PLC地址读取 /// /// /// public static int readPlc(string address) { var info = plcInstance.readInt32ByAddress(address); return info; } /// /// PLC地址读取-bool /// /// /// public static bool readBoolPlc(string address) { var info = plcInstance.readBoolByAddress(address); return info; } } }