using iWareSda.Common; using iWareModel; using System; using System.Collections.Generic; using System.Threading; using iWareCommon.Utils; using iWareCommon.Common.Globle; using iWareCommon; using iWareSda.Model; namespace iWareSda { /// /// 每台堆垛机的实时信息 /// public class SrmEntity : IDevice { public SrmEntity() { this.View = new SrmView(); } #region OPC相关 /// /// 写的DB块 /// public SrmDBForWrite DBBlockForWrite { get; set; } /// /// 读的DB块 /// public SrmDBForRead DBBlockForRead { get; set; } /// /// 读取PLC实例 /// public PLCService plcService { get; set; } /// /// 视图对象 /// public SrmView View { get; set; } #endregion /// /// 初始化数据 /// public void InitData() { } public SrmEntity(string srmName, int deviceId, SrmDBForWrite _dbBlockForWrite, SrmDBForRead _dbBlockForRead, PLCService _plcService) { this.View = new SrmView(); this.View.DeviceName = srmName; this.View.DeviceId = deviceId; plcService = _plcService; DBBlockForWrite = _dbBlockForWrite; DBBlockForRead = _dbBlockForRead; } #region 个性化方法 /// /// 是否允许给堆垛机发送新任务 /// /// /// public bool IsAllowSendNewTaskToSrm() { Thread.Sleep(2000);//等待一秒钟 【EditBy shaocx,2022-03-26】 if (this.View.ModeName == "自动" && this.View.R_AlarmCode == 0 && (this.View.R_WarningDBList == null || this.View.R_WarningDBList.Count == 0) && this.View.StateName == "空闲") { return true; } return false; } /// /// 重新格式化处理站点号 /// /// /// public void ReSubStringPlace(ref string sourcePlace, ref string toPlace) {//1-01-03-04 转换为 01-03-04 sourcePlace = sourcePlace.Substring(2, sourcePlace.Length - 2); toPlace = toPlace.Substring(2, toPlace.Length - 2); } /// /// 给堆垛机发送指令 /// /// 堆垛机设备号 /// 任务号 /// 起始位 /// 目标位 /// 任务类型 /// 错误消息 /// public bool SendTask(ESrmCmd srmCmd, int deviceId, int taskId, string sourcePlace, string toPlace, out string msg) { try { msg = ""; if (!CanDoTask(deviceId, out msg)) { return false; } //Z 排 X 列 Y层 //01-02-03 int sourceZ = 0, sourceX = 0, sourceY = 0; if (srmCmd == ESrmCmd.库内搬运 || srmCmd == ESrmCmd.入库 || srmCmd == ESrmCmd.出库) { var arr_source = sourcePlace.Split('-'); //int sourceZ = int.Parse(sourcePlace.Substring(0, 2)); //int sourceX = int.Parse(sourcePlace.Substring(2, 4)); //int sourceY = int.Parse(sourcePlace.Substring(3, 2)); sourceZ = int.Parse(arr_source[0]); sourceX = int.Parse(arr_source[1]); sourceY = int.Parse(arr_source[2]); ConvertPlaceToSrm(deviceId, ref srmCmd, true, sourcePlace, ref sourceZ, ref sourceX, ref sourceY); } var arr_to = toPlace.Split('-'); //int toZ = int.Parse(toPlace.Substring(0, 1)); //int toX = int.Parse(toPlace.Substring(1, 2)); //int toY = int.Parse(toPlace.Substring(3, 2)); int toZ = int.Parse(arr_to[0]); int toX = int.Parse(arr_to[1]); int toY = int.Parse(arr_to[2]); ConvertPlaceToSrm(deviceId, ref srmCmd, false, toPlace, ref toZ, ref toX, ref toY); //发送指令 var ss = this.plcService; ////只有一台堆垛机,不需要写 //var constValue = 1; //MessageModel b1 = this.plcService.WriteValuePoint( this.DBBlockForWrite.W_SrmNo, constValue, this.View.W_SrmNo); //if (!b1.result) //{ // msg = string.Format("向堆垛机{0}发送任务{1},写入设备编号" + constValue + "失败,返回结果:" + b1.resMsg, this.View.DeviceName, taskId); // return false; //} MessageModel b2 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_TaskNo, taskId, this.View.W_TaskNo); if (!b2.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入任务号" + taskId + "失败,返回结果:" + b2.resMsg, this.View.DeviceName, taskId); return false; } //MessageModel b60 = this.plcService.WriteValuePoint( this.DBBlockForWrite.W_PalletType, constValue, this.View.W_PalletType); //if (!b60.result) //{ // msg = string.Format("向堆垛机{0}发送任务{1},写入托盘类型" + constValue + "失败,返回结果:" + b60.resMsg, this.View.DeviceName, taskId); // return false; //} if (srmCmd == ESrmCmd.库内搬运 || srmCmd == ESrmCmd.入库 || srmCmd == ESrmCmd.出库) { MessageModel b5 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_SourcePosZ, sourceZ, this.View.W_SourcePosZ); if (!b5.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入sourceZ失败,返回结果:" + b5.resMsg, this.View.DeviceName, taskId); return false; } MessageModel b4 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_SourcePosX, sourceX, this.View.W_SourcePosX); if (!b4.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入sourceX失败,返回结果:" + b4.resMsg, this.View.DeviceName, taskId); return false; } MessageModel b3 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_SourcePosY, sourceY, this.View.W_SourcePosY); if (!b3.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入sourceY失败,返回结果:" + b3.resMsg, this.View.DeviceName, taskId); return false; } } MessageModel b8 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_DestinationPosZ, toZ, this.View.W_DestinationPosZ); if (!b8.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入toZ失败,返回结果:" + b8.resMsg, this.View.DeviceName, taskId); return false; } MessageModel b7 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_DestinationPosX, toX, this.View.W_DestinationPosX); if (!b7.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入toX失败,返回结果:" + b7.resMsg, this.View.DeviceName, taskId); return false; } MessageModel b6 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_DestinationPosY, toY, this.View.W_DestinationPosY); if (!b6.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入toY失败,返回结果:" + b6.resMsg, this.View.DeviceName, taskId); return false; } short command = (short)srmCmd; MessageModel b10 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_Command, command, this.View.W_Command); if (!b10.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入command失败,返回结果:" + b10.resMsg, this.View.DeviceName, taskId); return false; } MessageModel b9 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_Stb, 1, this.View.W_Stb); if (!b9.result) { msg = string.Format("向堆垛机{0}发送任务{1},写入W_Stb失败,返回结果:" + b9.resMsg, this.View.DeviceName, taskId); return false; } //重置如下状态 //不需要重置 【EditBy shaocx,2022-04-09】 //this.plcService.WriteValuePoint( this.DBBlockForWrite.W_EmergencyStop, 0, this.View.W_EmergencyStop); //this.plcService.WriteValuePoint( this.DBBlockForWrite.W_CancleAlarm, 0, this.View.W_CancleAlarm); //this.plcService.WriteValuePoint( this.DBBlockForWrite.W_TaskFinishConfirm, 0, this.View.W_TaskFinishConfirm); //this.plcService.WriteValuePoint( this.DBBlockForWrite.W_Ack, 0, this.View.W_Ack); return true; } catch (Exception ex) { msg = ex.Message; Log4NetHelper.WriteErrorLog(Srm_CacheEntity.curLogType, "发送任务出现异常:" + ex.Message, ex); return false; } } /// /// 堆垛机上的站点转换 /// /// /// /// /// /// private void ConvertPlaceToSrm(int deviceId, ref ESrmCmd srmCmd, bool isSource, string place, ref int z, ref int x, ref int y) { if (deviceId == (int)EDevice.四号堆垛机) { if (place == "02-01-01") {//入口 x = 801; y = 0; z = 0; if (isSource && srmCmd == ESrmCmd.库内搬运) {//如果是起点是入库口 srmCmd = ESrmCmd.入库; } } else if (place == "01-01-01") {//出口 x = 901; y = 0; z = 0; if (isSource == false && srmCmd == ESrmCmd.库内搬运) {//如果是目标点是出口 srmCmd = ESrmCmd.出库; } } } else { if (place == "01-01-01") {//入口 x = 801; y = 0; z = 0; if (isSource && srmCmd == ESrmCmd.库内搬运) {//如果是起点是入库口 srmCmd = ESrmCmd.入库; } } else if (place == "02-01-01") {//出口 x = 901; y = 0; z = 0; if (isSource == false && srmCmd == ESrmCmd.库内搬运) {//如果是目标点是出口 srmCmd = ESrmCmd.出库; } } } } /// /// 任务删除 /// /// /// /// /// public bool SendDelTask(int deviceId, out string msg) { try { msg = ""; if (!CanDeleteTask(deviceId, out msg)) { return false; } MessageModel b3 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_Command, (int)ESrmCmd.任务删除, this.View.W_Command); if (!(b3.result)) { msg = string.Format("向堆垛机{0}发送删除任务失败,返回结果:" + b3.resMsg, this.View.DeviceName); return false; } return true; } catch (Exception ex) { Log4NetHelper.WriteErrorLog(Srm_CacheEntity.curLogType, "任务删除出现异常:" + ex.Message, ex); throw ex; } } /// /// 堆垛机解警 /// /// /// public bool ReleaseAlert(out string msg) { try { msg = ""; MessageModel b1 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_CancleAlarm, 1, this.View.W_CancleAlarm); if (!(b1.result)) { msg = string.Format("向堆垛机{0}发送解警指令失败,返回结果:" + b1.resMsg, this.View.DeviceName); return false; } return true; } catch (Exception ex) { Log4NetHelper.WriteErrorLog(Srm_CacheEntity.curLogType, "发送解警指令异常:" + ex.Message, ex); throw ex; } } /// /// 堆垛机急停 /// /// /// public bool SendEStop(out string msg) { try { msg = ""; MessageModel b1 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_EmergencyStop, 1, this.View.W_EmergencyStop); if (!(b1.result)) { msg = string.Format("向堆垛机{0}发送急停指令失败,返回结果:" + b1.resMsg, this.View.DeviceName); return false; } return true; } catch (Exception ex) { Log4NetHelper.WriteErrorLog(Srm_CacheEntity.curLogType, "发送急停指令异常:" + ex.Message, ex); throw ex; } } /// /// 堆垛机任务确认 /// /// /// public bool ConfirmTaskFinish(out string msg) { try { msg = ""; MessageModel b1 = this.plcService.WriteValuePoint(this.DBBlockForWrite.W_TaskFinishConfirm, 1, this.View.W_TaskFinishConfirm); if (!(b1.result)) { msg = string.Format("向堆垛机{0}发送任务确认指令失败,返回结果:" + b1.resMsg, this.View.DeviceName); return false; } return true; } catch (Exception ex) { Log4NetHelper.WriteErrorLog(Srm_CacheEntity.curLogType, "发送任务确认指令异常:" + ex.Message, ex); throw ex; } } /// /// 堆垛机继续任务 /// /// /// public bool ContinueTask(out string msg) { try { msg = ""; //var dbNumber = Srm_CacheEntity.W_DBHeader; //FunctionReturnEntity b1 = this.S7.WriteValuePoint( this.DBBlock.con, 1); //if (!(b1.result)) //{ // msg = string.Format("向堆垛机{0}发送解警指令失败,返回结果:" + b1.resMsg, this.DeviceName); // return false; //} return true; } catch (Exception ex) { Log4NetHelper.WriteErrorLog(Srm_CacheEntity.curLogType, "堆垛机继续任务异常:" + ex.Message, ex); throw ex; } } /// /// 是否可以下发任务 /// /// /// /// public bool CanDoTask(int deviceId, out string msg) { msg = ""; //在不在线不需要校验,不在线的话 if (this.View.R_Mode != 1) { msg = string.Format("堆垛机{0}非自动模式", this.View.DeviceName); return false; } if (this.View.R_Alarm == 1) { msg = string.Format("堆垛机{0}报警中", this.View.DeviceName); return false; } if (this.View.R_LiftFull == 1) { msg = string.Format("堆垛机{0}叉齿有货", this.View.DeviceName); return false; } if (this.View.R_PosZ != 0) { msg = string.Format("堆垛机{0}叉齿不在原点", this.View.DeviceName); return false; } //*/ if (this.View.R_State != (int)ESrmState.空闲) { msg = string.Format("堆垛机{0}非空闲", this.View.DeviceName); return false; } return true; } /// /// 是否可以删除任务 /// /// /// /// private bool CanDeleteTask(int deviceId, out string msg) { msg = ""; //在不在线不需要校验,不在线的话 if (this.View.R_Mode != 1) { msg = string.Format("堆垛机{0}非自动模式", this.View.DeviceName); return false; } return true; } #endregion public void SetPropertyValueForRead() { var r_dbBlock = this.DBBlockForRead; SdaHelper.SetPropertyValueForDB(r_dbBlock, this.View, this.plcService, ""); } public void SetPropertyValueForWrite() { var w_dbBlock = this.DBBlockForWrite; SdaHelper.SetPropertyValueForDB(w_dbBlock, this.View, this.plcService, ""); } /// /// 是否有心跳 /// /// public bool IsHaveHeatBeat() { try { var r_dbBlock = this.DBBlockForRead; short value = Convert.ToInt16(this.plcService.ReadValuePoint(r_dbBlock.R_HandShake, typeof(short))); //约定 等待2秒 Thread.Sleep(2000); short value_next = Convert.ToInt16(this.plcService.ReadValuePoint(r_dbBlock.R_HandShake, typeof(short))); if (value == value_next) {//没有心跳 return false; } else {//有心跳 return true; } } catch (Exception ex) { throw ex; } } /// /// 组合 起始点 /// /// public string GetSrmSourcePlace() { if (this.View.W_SourcePosZ != 0) { return this.View.W_SourcePosZ.ToString("00") + "-" + this.View.W_SourcePosX.ToString("00") + "-" + this.View.W_SourcePosY.ToString("00"); } return GetPlaceForInOutStation(this.View.W_SourcePosX); } /// /// 组合 目标点 /// /// public string GetSrmToPlace() { if (this.View.W_DestinationPosZ != 0) { return this.View.W_DestinationPosZ.ToString("00") + "-" + this.View.W_DestinationPosX.ToString("00") + "-" + this.View.W_DestinationPosY.ToString("00"); } return GetPlaceForInOutStation(this.View.W_DestinationPosX); } /// /// 单独获取出入口站点名 /// /// /// private string GetPlaceForInOutStation(short xVaue) { if (xVaue == 801) { if (this.View.DeviceId == (int)EDevice.四号堆垛机) { return "02-01-01"; } else { return "01-01-01"; } } else if (xVaue == 901) { if (this.View.DeviceId == (int)EDevice.四号堆垛机) { return "01-01-01"; } else { return "02-01-01"; } } return ""; } #region 获取当前报警信息 #endregion } }