using HH.WCS.QingXigongchang.process; using HH.WCS.QingXigongchang.util; using Newtonsoft.Json; using SqlSugar; using System; using System.Collections.Generic; using System.Linq; using System.Linq.Expressions; namespace HH.WCS.QingXigongchang.wms { public static class ClassExtends { //public static void Add(this Dictionary dict, TKey key, TValue value) //{ //} } internal class LocationHelper { private static Dictionary locations = null; private static Dictionary locationExts = null; private static Dictionary> FreeLineInfos = null; public static object _lock = new object();//锁定空托筛选流程。。0 防止多方进入导致筛选相同空托。 static LocationHelper() { //初始化location加入到字典缓存 //return; try { locations = new Dictionary(); var list = GetAllLocList(); if (list.Count > 0) { list.ForEach(a => { locations.Add(a.S_LOC_CODE.Trim(), a); }); } //初始化locationExt加入到集合缓存 locationExts = new Dictionary(); var exts = GetAllLocExtList(); if (exts.Count > 0) { exts.ForEach(a => { locationExts.Add($"{a.S_LOC_CODE.Trim()}_{a.S_PICKUP_POINT.Trim()}", a); }); } var freelist = GetFreeLineLists(); FreeLineInfos = new Dictionary>(); foreach (var item in freelist.GroupBy(x => x.area)) { FreeLineInfos.Add(item.Key, item.ToList()); } } catch (Exception ex) { Console.WriteLine("111111111" + ex.Message + "===" + ex.StackTrace); } } internal static bool CheckExist(string loc) { return locations.Keys.Contains(loc); } internal static Location GetLocation(string loc) { if (CheckExist(loc.Trim())) { return locations[loc.Trim()]; } return null; } internal static List GetFreeLineList(string area) { List lflis = new List(); if (FreeLineInfos.Keys.Contains(area.Trim())) { lflis = FreeLineInfos[area.Trim()]; } else { lflis = GetFreeLineLists(area.Trim()); if (lflis.Any()) { FreeLineInfos.Add(area.Trim(), lflis); } } return lflis; //var locinfo = GetLoc(loc); //return lflis.Find(x => x.row == locinfo.N_ROW && x.minCol <= locinfo.N_COL && locinfo.N_COL <= x.maxCol); } /// /// 获取货位站点信息 /// /// /// internal static int GetAgvSite(string loc) { var site = 0; if (locations.Keys.Contains(loc.Trim())) { var location = locations[loc.Trim()]; site = location.N_AGV_CODE; } else { var location = GetLoc(loc.Trim()); if (location != null) { if (location.N_AGV_CODE != 0) locations.Add(loc.Trim(), location); site = location.N_AGV_CODE; } } return site; } internal static int GetAgvSite(string loc, string actionType) { var site = 0; var key = $"{loc.Trim()}_{actionType.Trim()}"; if (locationExts.Keys.Contains(key)) { var location = locationExts[key]; site = int.Parse(location.S_AGV_SITE); } return site; } /// /// 获取所有货位信息 /// /// internal static List GetAllLocList() { var db = new SqlHelper().GetInstance(); return db.Queryable().ToList(); } internal static List GetLocList(Expression> expression) { var db = new SqlHelper().GetInstance(); return db.Queryable().Where(expression).ToList(); } public static List GetAreaNormalLocList(string areeacode, bool normal = true, bool isrow = true) { var locs = LocationHelper.GetLocList(x => x.S_AREA_CODE == areeacode && x.S_LOCK_STATE != "报废"); if (normal) { if (isrow) { IEnumerable lockcols = (from x in locs.FindAll((Location x) => x.S_LOCK_STATE.Trim() != "无" && x.S_LOCK_STATE.Trim() != "报废") select x.N_ROW).Distinct(); if (lockcols.Any()) { locs.RemoveAll((Location x) => lockcols.Contains(x.N_ROW)); } } else { IEnumerable lockcols = (from x in locs.FindAll((Location x) => x.S_LOCK_STATE.Trim() != "无" && x.S_LOCK_STATE.Trim() != "报废") select x.N_COL).Distinct(); if (lockcols.Any()) { locs.RemoveAll((Location x) => lockcols.Contains(x.N_COL)); } } } return locs; } public static List GetAreaNormalLocListAll(string areeacode) { var locs = LocationHelper.GetLocList(x => x.S_AREA_CODE == areeacode && x.S_LOCK_STATE.Trim() == "无" && x.N_CURRENT_NUM == 0); return locs; } internal static List GetAllLocListByAreaCode(string _areacode, int minRow, int maxRow) { var db = new SqlHelper().GetInstance(); if (minRow != 0 && maxRow != 0) { return db.Queryable().Where(l => l.S_AREA_CODE == _areacode && l.N_ROW >= minRow && l.N_ROW <= maxRow).ToList(); } return db.Queryable().Where(l => l.S_AREA_CODE == _areacode).ToList(); } internal static Location GetLoc(string coded) { var code = coded?.Trim(); var db = new SqlHelper().GetInstance(); return db.Queryable().Where(a => a.S_LOC_CODE.Trim() == code).First(); } /// ///获取所有货位扩展信息 /// /// internal static List GetAllLocExtList() { var db = new SqlHelper().GetInstance(); return db.Queryable().ToList(); } /// /// 自由线段 /// /// internal static List GetFreeLineLists(string area = "") { var db = new SqlHelper().GetInstance(); if (string.IsNullOrEmpty(area)) return db.Queryable().ToList(); else return db.Queryable().Where(x => x.area.Trim() == area).ToList(); } /// /// 判断没有入库锁和出库锁 /// /// /// internal static bool CheckLocFree(string code) { var result = false; var loc = GetLoc(code); if (loc != null) { result = loc.S_LOCK_STATE.Trim() == "无"; } return result; } internal static string CheckLocState(string code) { var result = ""; var loc = GetLoc(code); if (loc != null) { result = loc.S_LOCK_STATE.Trim(); } return result; } internal static List GetLocCntr(string loc) { var result = new List(); //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var list = db.Queryable().Where(a => a.S_LOC_CODE == loc.Trim()).OrderBy(a => a.T_CREATE).ToList(); if (list.Count > 0) { list.ForEach(a => { //获取容器信息 var cntr = db.Queryable().Where(b => b.S_CNTR_CODE == a.S_CNTR_CODE).First(); if (cntr != null) { a.Container = cntr; result.Add(a); } }); } return result; } internal static List GetLocCntrRel(string loc) { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var result = db.Queryable().Where(a => a.S_LOC_CODE == loc.Trim()).ToList(); return result; } internal static List GetLocCntrRel() { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var result = db.Queryable().ToList(); return result; } /// /// 根据货位集合获取有容器的货位 /// /// /// internal static List GetLocList(List loc) { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var list = db.Queryable().Where(a => loc.Contains(a.S_LOC_CODE) && a.N_CURRENT_NUM > 0).ToList(); return list; } /// /// 根据货位编码获取货位信息,不管有没有容器 /// /// /// internal static List GetLocListAny(List loc) { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var list = db.Queryable().Where(a => loc.Contains(a.S_LOC_CODE)).ToList(); return list; } /// /// 根据货位集合获取有容器 没有锁的货位 /// /// /// internal static List GetLocListFree(List loc) { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var list = db.Queryable().Where(a => loc.Contains(a.S_LOC_CODE) && a.N_CURRENT_NUM > 0 && a.S_LOCK_STATE.Trim() == "无").ToList(); return list; } /// /// 获取固定数量容器 没有锁的货位 /// /// /// /// internal static List GetLocListFree(List loc, int current) { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var list = db.Queryable().Where(a => loc.Contains(a.S_LOC_CODE) && a.N_CURRENT_NUM == current && a.S_LOCK_STATE.Trim() == "无").ToList(); return list; } /// /// 获取数量大于等于固定数量容器 没有锁的货位 /// /// /// /// internal static List GetLocList(List loc, int current) { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var list = db.Queryable().Where(a => loc.Contains(a.S_LOC_CODE) && a.N_CURRENT_NUM >= current && a.S_LOCK_STATE.Trim() == "无").ToList(); return list; } /// /// 根据货位集合获取 没有容器 没有锁的货位 /// /// /// internal static List GetLocListEmptyFree(List loc) { //1.0 查货位容器表 var db = new SqlHelper().GetInstance(); var list = db.Queryable().Where(a => loc.Contains(a.S_LOC_CODE) && a.N_CURRENT_NUM == 0 && a.S_LOCK_STATE.Trim() == "无").ToList(); return list; } /// /// 入库锁定终点,出库锁定起点 /// /// /// 1:入库锁、2:出库锁、2:其它锁 /// public static bool LockLoc(string loc, string lockState, SqlSugarClient db = null) { LogHelper.Info("LockLoc:" + loc); var res = false; if (db == null) db = new SqlHelper().GetInstance(); var model = db.Queryable().Where(a => a.S_LOC_CODE == loc).First(); if (model != null && model.S_LOCK_STATE.Trim() == "无") { model.S_LOCK_STATE = lockState; res = db.Updateable(model).UpdateColumns(it => new { it.S_LOCK_STATE }).ExecuteCommand() > 0; LogHelper.Info("LockLoc:锁结果" + res); } else { LogHelper.Info("LockLoc 失败"); } return res; } /// /// 取货完解锁起点,卸货完解锁终点,可检验锁的来源,也可以不校验 /// /// /// public static bool UnLockLoc(string loc) { LogHelper.Info("UnLockLoc:" + loc); var res = false; var db = new SqlHelper().GetInstance(); var model = db.Queryable().Where(a => a.S_LOC_CODE == loc).First(); if (model != null) { model.S_LOCK_STATE = "无"; res = db.Updateable(model).UpdateColumns(it => new { it.S_LOCK_STATE }).ExecuteCommand() > 0; LogHelper.Info("UnLockLoc:解锁结果" + res); } else { LogHelper.Info("UnLockLoc 失败"); } return res; } /// /// agv_site 用作 标识 瓶坯机 /// 本来用S_WH_CODE 的,谁知是仓库。 改用agv_site /// /// /// public static bool SetLocWH(string loc, string WH) { LogHelper.Info("SetLocWH:" + loc + "-" + WH); var res = false; var db = new SqlHelper().GetInstance(); var model = db.Queryable().Where(a => a.S_LOC_CODE == loc).First(); if (model != null) { model.S_AGV_SITE = WH; //model.S_LOCK_STATE = "无"; res = db.Updateable(model).UpdateColumns(it => new { it.S_AGV_SITE }).ExecuteCommand() > 0; LogHelper.Info("SetLocWH:结果" + res); } else { LogHelper.Info("SetLocWH 失败"); } return res; } public static bool lOCReSetValue(Expression> exQ, Action exu, Action, SqlSugar.SqlSugarClient> action = null) { //LogHelper.Info("SetLocExp:" + JsonConvert.SerializeObject(exQ)); var res = false; var db = new SqlHelper().GetInstance(); var models = db.Queryable().Where(exQ).ToList(); if (models != null && models.Count > 0) { res = db.Updateable(models).ReSetValue(exu).ExecuteCommand() > 0; //LogHelper.Info("SetLocExp:结果" + res); if (action != null) { action(models, db); } } else { LogHelper.Info("SetLocExp 失败,没有找到数据 "); } return res; } /// /// 瓶坯机用的。 记录托盘。 /// /// /// /// public static bool SetT_FULL_TIME(string loc, DateTime? dateTime, Action action = null) { LogHelper.Info("SetT_FULL_TIME:" + loc + "-" + dateTime); if (action != null) { var plc = Settings.GetDeviceInfoList().Where(a => a.location.Contains(loc.Trim()) && a.enable == 1).FirstOrDefault(); if (plc != null) { if (plc.deviceType == 8 || plc.deviceType == 2 || plc.deviceType == 3) for (var i = 0; i < plc.location.Length; i++) { if (loc.Trim() == plc.location[i]) { action(plc, "3F00" + (i + 1) + "0" + "0d0a"); break; } } } } var res = false; var db = new SqlHelper().GetInstance(); var model = db.Queryable().Where(a => a.S_LOC_CODE == loc).First(); if (model != null) { //if (model.T_FULL_TIME != null) //{ model.T_FULL_TIME = dateTime; //if(BBBB) //model.S_LOCK_STATE = "无"; res = db.Updateable(model).UpdateColumns(it => new { it.T_FULL_TIME }).ExecuteCommand() > 0; LogHelper.Info("SetT_FULL_TIME:结果" + res); res = true; //} } else { LogHelper.Info("SetT_FULL_TIME 失败"); } return res; } public static DateTime? GetT_FULL_TIME(string loc) { //LogHelper.Info("GetT_FULL_TIME:货位:" + loc); var db = new SqlHelper().GetInstance(); var model = db.Queryable().Where(a => a.S_LOC_CODE == loc).First(); if (model != null) { return model.T_FULL_TIME; } else { LogHelper.Info("GetT_FULL_TIME 失败。没有数据。 "); } return null; } /// /// 进入是true , 没进是false /// public static Dictionary GetT_FULL_ready = new Dictionary(); public static Dictionary Turn_ready = new Dictionary(); /// /// 胚盖 取空, /// 翻斗上满 /// /// /// public static bool TakeEmptyToBottleBoyd(WMSTask mst) { var startbit = mst.S_START_LOC.Trim(); bool res = false; var hasin = false; GetT_FULL_ready.TryGetValue(startbit, out hasin); if (hasin) { LogHelper.Info($"{startbit} 胚盖送空 / 翻斗机取满 流程 已在筛选中。"); return true; } else { if (GetT_FULL_ready.ContainsKey(startbit)) GetT_FULL_ready[startbit] = true; else GetT_FULL_ready.Add(startbit, true); } var plc = Settings.GetDeviceInfoList().Where(a => a.location.Contains(startbit) && a.enable == 1).FirstOrDefault(); LogHelper.Info($"{startbit} 开始 胚盖送空 / 翻斗机取满 流程"); if (plc != null) { var workOrder = WCSHelper.GetWorkOrder(plc.deviceName); if (workOrder == null) { LogHelper.Info($"工单没有执行,送空流程取消", "PEM机"); goto ______label____end; } if (/*plc.deviceType <= 3 || */plc.deviceType == 4 || plc.deviceType == 6 || plc.deviceType == 10) { var ret = false; LocationHelper.DoAction(db => { var tasks = db.Queryable().Where(x => x.S_START_LOC == startbit && "取货完成,开始卸货,卸货完成".Contains(x.S_B_STATE)).ToList(); if (tasks.Any()) { LogHelper.Info($"{startbit} 的下线任务还没完成。 等待完成后 在呼叫任务。-- 2024年6月5日 14:30:57 现场要求"); ret = true; } return true; }); if (ret) goto ______label____end; ; } LogHelper.Info($"工单{workOrder.SQL_WorkNo},胚盖送空 / 翻斗机取满 {plc.deviceType}"); var isusing = workOrder.SQL_UsingNow.Trim() == "Y"; Location endBit = null; int endLayer = 1;//起点。 字段名估计的。 if (plc.deviceType == 8) { //List loc_list_PEM = new List(); var loc_list_PEM = new List(); //lock (_lock) if (workOrder.SQL_UsingNow.Trim() == "Y") { //工单的满终点是 空起点 //var jlist = LocationHelper.GetLocList(x => x.S_AREA_CODE == workOrder.SQL_Area.Trim()); //var _le = LocationHelper.GetLocCntrRel().Select(x => x.S_LOC_CODE); List lp_ = new List(); //即产即用时 必填的。 var _l = LocationHelper.GetAllLocListByAreaCode(workOrder.SQL_Area, 0, 0).FindAll(x => x.S_LOCK_STATE != "入库锁" && x.S_LOCK_STATE != "报废"); var UsingEnough = _l.FindAll(x => x.S_LOCK_STATE.Trim() == "出库锁").Count + _l.FindAll(x => x.S_LOCK_STATE == "无" && x.N_CURRENT_NUM < x.N_CAPACITY).Count; if (UsingEnough > 0) { foreach (var _oloc in plc.location) { if (_oloc != startbit) { var _ctrl = LocationHelper.GetLocCntrRel(_oloc); if (_ctrl.Count > 0 && _ctrl.FirstOrDefault().S_CNTR_CODE.Contains("J")) UsingEnough--; } } } else {//if (!UsingEnough) LogHelper.Info($"{workOrder.SQL_WorkNo} 链接的即产满框区{workOrder.SQL_Area}位置不足。叫筐切筐。"); } if (UsingEnough > 0) lp_ = LocationHelper.GetAllLocListByAreaCode("JCJYKK", 0, 0).FindAll(x => x.S_LOCK_STATE == "无" && x.N_CURRENT_NUM > 0);//FindAll(x => x.T_FULL_TIME != null); if (lp_.Count > 0) { foreach (var item1 in lp_.OrderBy(x => x.N_ROW).ThenByDescending(x => x.N_COL)) { var _ctrl = LocationHelper.GetLocCntrRel(item1.S_LOC_CODE); if (_ctrl.Count > 0 && _ctrl.FirstOrDefault().S_CNTR_CODE.Contains("J")) { loc_list_PEM = _ctrl; break; } } } if (loc_list_PEM.Count > 0) { var location_ = loc_list_PEM.FirstOrDefault(); //var _ctrl = LocationHelper.GetLocCntrRel(location_.S_LOC_CODE); endLayer = 1; var carryCntrs = new List { location_.S_CNTR_CODE };//DateTime.Now.ToString("yyMMddHHmmss") }; var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, location_.S_LOC_CODE.Trim(), startbit, "J空瓶坯-出库", carryCntrs, loc_list_PEM.Count, endLayer, carryCntrs.Count, plc.taskPri + 2); if (re) { LogHelper.Info($"{plc.deviceName}-{startbit}正在执行送空"); } res = re; goto ______label____end; } else { // 转筐 //时间分钟 DateTime dateTime = DateTime.Now; if (Turn_ready.TryGetValue(startbit, out dateTime)) { if (DateTime.Now.Subtract(dateTime).TotalMinutes > plc.EmptyWait) { Turn_ready.Remove(startbit); goto labelUsingNo; } else { if (UsingEnough > 0) LogHelper.Info($"{workOrder.SQL_WorkNo} 即产空框不足。。叫筐切筐等待时间不足{plc.EmptyWait}分钟。"); else LogHelper.Info($"{workOrder.SQL_WorkNo} 链接的即产满框区{workOrder.SQL_Area}位置不足,叫筐切筐等待时间不足{plc.EmptyWait}分钟。"); } } else { Turn_ready.Add(startbit, DateTime.Now); } LogHelper.Info(plc.deviceName + "[" + startbit + "]送空托 失败,没有空托了"); goto ______label____end; } } labelUsingNo: { List areasssss = new List { "PPKK", "PPLASTKK" }; if (plc.deviceName.Trim() != "注塑机") { if ("注塑机3".Contains(plc.deviceName)) areasssss = new List { "PPTKK", "PPFKK", "PPLASTKK", "PPKK" }; if ("注塑机4".Contains(plc.deviceName)) areasssss = new List { "PPFKK", "PPTKK", "PPLASTKK", "PPKK" }; } LogHelper.Info(plc.deviceName + $"寻空框,库区顺序是{JsonConvert.SerializeObject(areasssss)}"); balellll: var _areaCode = areasssss.FirstOrDefault(); areasssss.Remove(_areaCode); //Location endBit = null; //var _l = LocationHelper.GetAllLocListByAreaCode("PPKKCK", 0, 0); var _l = LocationHelper.GetLocList(x => x.S_AREA_CODE == _areaCode && x.S_LOCK_STATE != "报废"); IEnumerable lockcols = (from x in _l.FindAll((Location x) => x.S_LOCK_STATE.Trim() != "无") select x.N_ROW).Distinct(); if (lockcols.Any()) { _l.RemoveAll((Location x) => lockcols.Contains(x.N_ROW)); } endBit = _l?.OrderBy(x => x.N_ROW).ThenByDescending(x => x.N_COL).ToList().Find(x => x.N_CURRENT_NUM > 0); //if (endBit == null) // //foreach (IGrouping item in from x in _l // // orderby x.N_COL, x.N_ROW // // group x by x.N_COL) // foreach (IGrouping item in _l.OrderBy(x => x.N_ROW).GroupBy(x => x.N_ROW)) // { // List _cols = item.OrderByDescending(x => x.N_COL).ToList(); // Location e = _cols.Find((Location x) => x.N_CURRENT_NUM > 0);//从右往左,第一个有筐位。 // if (e != null)// && e.N_CURRENT_NUM == e.N_CAPACITY) // { // endBit = e; // } // if (endBit != null) // break; // } if (endBit != null) { var location_ = LocationHelper.GetLocCntrRel(endBit.S_LOC_CODE); endLayer = 1; var carryCntrs = new List { location_.FirstOrDefault().S_CNTR_CODE };//DateTime.Now.ToString("yyMMddHHmmss") }; var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, "F空瓶坯-出库", carryCntrs, location_.Count, endLayer, carryCntrs.Count, plc.taskPri + 2); if (re) { LogHelper.Info($"{plc.deviceName}-{startbit}正在执行送空"); } res = re; goto ______label____end; } else { LogHelper.Info(_areaCode + "没有可搬运的空框"); if (areasssss.Count > 0) goto balellll; } } } else if (plc.deviceType <= 3) //1 是门。 门肯定不会叫的。所以就是2、3 { LocCntrRel cntrRel = null; List bitslocs = null; List carryCntrs = null; bool re; var tt = "瓶盖-空上机"; //void func() //{ // tt = "即满瓶盖-空上机"; // goto ___label__else; //} var ba2 = Settings.GetBolAreaList().Find(x => x.DeviceName == plc.deviceName && x.deviceType == plc.deviceType); if (ba2 == null) { LogHelper.Info($"{plc.deviceName}-{workOrder.SQL_WorkNo}的BolArea 未配置。"); goto ______label____end; } List areaList = new List { (plc.deviceType == 2 ? "WJGRGDKQ" : "SGRGDKQ"), ba2.NotUsingEmpty }; bool turn = false; // 是否逻辑回转。 if (workOrder.SQL_UsingNow.Trim() == "Y") { turn = true; goto __label_usingnowY__; } else goto ___label__else; ///1:有没有2个可用位子 ///2:旁边货位是不是即产 ///可用位子 - 旁边筐(即产1,入库0)>0 就叫即产筐。 否则入库筐。 __label_usingnowY__: #region check即产可用位。 //var _t = "注塑即产空筐上线"; tt = "注塑即产空筐上线"; //if (plc.deviceType == 2) _t = "即产满框无菌盖"; //else if (plc.deviceType == 3) _t = "即产满框水盖"; var LineTo = workOrder.SQL_LinkLineNO; var plcTo = Settings.GetDeviceInfoList().Where(a => a.deviceName == LineTo).FirstOrDefault(); if (plcTo == null) { LogHelper.Info($"{plc.deviceName}-{workOrder.SQL_WorkNo}链接的产线号{LineTo} 没找到设备"); goto ______label____end; } var ba = Settings.GetBolAreaList().Find(x => x.DeviceName == plcTo.deviceName && x.deviceType == plcTo.deviceType); if (ba == null) { LogHelper.Info($"{plc.deviceName}-{workOrder.SQL_WorkNo}链接的产线号{LineTo} BolArea 未配置。"); goto ______label____end; } bitslocs = LocationHelper.GetAreaNormalLocList(ba.UsingBolArea); //var bits = Settings.GetInStockCacheList().Where(a => a.deviceName == _t)?.Select(x => x.location); //bitslocs = LocationHelper.GetAllLocList().Where(x => bits.Contains(x.S_LOC_CODE.Trim())).ToList(); //{ //锁定列 剔除 //var loccols = bitslocs.FindAll(x => x.S_LOCK_STATE.Trim() != "无").Select(x => x.N_COL).Distinct(); //if (loccols.Any()) // bitslocs.RemoveAll(x => loccols.Contains(x.N_COL)); //} bitslocs = bitslocs.OrderByDescending(x => x.N_ROW).OrderBy(x => x.N_COL).ToList(); var _locl2 = bitslocs.FindAll(x => x.N_CURRENT_NUM < x.N_CAPACITY);//&& x.S_LOCK_STATE.Trim() == "无"); int _lcount = 0; foreach (var item in _locl2) { if (item.S_LOCK_STATE.Trim() == "出库锁") { LogHelper.Info($"{item.S_LOC_CODE} 出库锁。增加{(item.N_CAPACITY - item.N_CURRENT_NUM + 1)}"); _lcount += item.N_CAPACITY - item.N_CURRENT_NUM + 1; } else if (item.S_LOCK_STATE.Trim() == "无") { LogHelper.Info($"{item.S_LOC_CODE} 无。增加{(item.N_CAPACITY - item.N_CURRENT_NUM)}"); _lcount += item.N_CAPACITY - item.N_CURRENT_NUM; } else if (item.S_LOCK_STATE.Trim() == "入库锁") { //var _c = item.N_CAPACITY - item.N_CURRENT_NUM - 1; //if (_c < 0) // _c = 0; //_lcount += _c; } else continue; } LogHelper.Info($"{plc.deviceName} 叫空框,对应的即产满框位剩余位置: {_lcount}"); var plcllist = Settings.GetDeviceInfoList().FindAll(x => x.deviceType == plc.deviceType); foreach (var _ploc in plc.location) { var cntrEnd = LocationHelper.GetLocCntrRel(_ploc.Trim()).FirstOrDefault(); if (cntrEnd != null && cntrEnd.S_CNTR_CODE.Trim().StartsWith("J")) //即产筐 { var _plocc = LocationHelper.GetLoc(_ploc.Trim()); if (_plocc.S_LOCK_STATE.Trim() == "无") _lcount--; } } LogHelper.Info($"{plc.deviceName} 叫空框,去除所有在下料筐 满框位剩余位置: {_lcount}"); //if (false) //{ if (_lcount > 0) { goto ___label__; } else // if (_lcount == 0) { tt = "注塑库存空筐上线(瓶盖)";// "即满瓶盖-空上机"; goto ___label__else; } //} //if (_lcount >= 2) //else if (_lcount == 1) //{ // //判断隔壁是否即产。 如果是即产,就取即产。 // var l2 = plc.location.ToList().Find(x => x.Trim() != startbit); // if (l2 == null) // goto ___label__; // Location _L2 = GetLoc(l2); // if (_L2.S_LOCK_STATE.Trim() != "无") // goto ___label__; // var cntrEnd = LocationHelper.GetLocCntrRel(_L2.S_LOC_CODE).FirstOrDefault(); // //就一个位子了。旁边的还是即产。 这个只能入库了 // if (cntrEnd != null && !cntrEnd.S_CNTR_CODE.Trim().StartsWith("F")) // { // tt = "即满瓶盖-空上机"; // turn = true; // goto ___label__else; // } // else goto ___label__; //} #endregion ___label__: //var bits = Settings.GetInStockCacheList().Where(a => a.deviceName == "即产空框")?.Select(x => x.location.Trim()); //LogHelper.Info($"{plc.deviceName} 的空框位列表 {JsonConvert.SerializeObject(bits)}"); //bitslocs = LocationHelper.GetLocList(x => x.S_AREA_CODE == ba2.UsingEmpty && x.N_CURRENT_NUM > 0).ToList(); //if (bitslocs.Count == 0) //{ // LogHelper.Info($"{plc.deviceName} 的没有可用的即产空框"); // if (turn) // { // turn = false; // tt = "注塑即产空筐上线(瓶盖)"; // goto ___label__else; // } // else // goto ______label____end; //} ////锁定列 剔除 //var loccols = bitslocs.FindAll(x => x.S_LOCK_STATE.Trim() != "无").Select(x => x.N_COL).Distinct(); //if (loccols.Any()) // bitslocs.RemoveAll(x => loccols.Contains(x.N_COL)); ////bitslocs = bitslocs.OrderBy(x => x.N_ROW).OrderBy(x => x.N_COL).ToList(); if (false) { var locs = LocationHelper.GetLocList(x => x.S_AREA_CODE == ba.UsingEmpty && x.S_LOCK_STATE != "报废").OrderBy(x => x.N_COL).ThenByDescending(x => x.N_ROW).ToList(); var lastffl = locs.FindAll(x => x.N_CURRENT_NUM > 0 && x.T_FULL_TIME != null).OrderBy(x => x.T_FULL_TIME).LastOrDefault(); var lastEmpty = locs.FindAll(x => x.N_CURRENT_NUM == 0 && x.T_EMPTY_TIME != null).OrderBy(x => x.T_EMPTY_TIME).LastOrDefault(); LogHelper.Info($"{locs.Count}-{lastffl?.S_LOC_CODE}{lastEmpty?.S_LOC_CODE}"); if (lastEmpty != null) { if (lastffl == null) lastEmpty = null; else if (lastEmpty.N_COL < lastffl.N_COL) { lastffl = null; lastEmpty = null; } else if (lastEmpty == locs.LastOrDefault()) lastEmpty = null; } else if (locs.Find(x => x.N_CURRENT_NUM == 0) == null) { lastEmpty = null; } var locccccs = locs.Skip((lastEmpty == null || lastEmpty == locs.LastOrDefault() ? 0 : locs.IndexOf(lastEmpty))); if (locccccs.ToList().Find(x => x.N_CURRENT_NUM > 0) == null) locccccs = locs; //foreach (var item in locccccs.GroupBy(x => x.N_COL)) ///最后一个满框入库位往后找。 foreach (var item in locccccs.GroupBy(x => x.N_COL)) { ///先放小排, 先取大排 取放按列 var collist = item.OrderByDescending(x => x.N_ROW).ToList(); if (!collist.Any()) continue; if (collist.Find(x => x.S_LOCK_STATE != "无") != null) continue; Location nex = collist.Find(x => x.N_CURRENT_NUM > 0); if (nex != null) { var cntrEnd = LocationHelper.GetLocCntrRel(nex.S_LOC_CODE); endBit = nex; endLayer = cntrEnd.Count; cntrRel = cntrEnd.FirstOrDefault(); break; } } } else { var _endLoclist = LocationHelper.GetAreaNormalLocList(ba.UsingEmpty); foreach (var item in _endLoclist.GroupBy(x => x.N_ROW).OrderBy(x => x.Count(y => y.N_CURRENT_NUM > 0)).ThenBy(x => x.Key)) { var _ll = item.OrderBy(x => x.N_COL).ToList(); var fulast = _ll.FindAll(x => x.N_CURRENT_NUM > 0).LastOrDefault(); if (fulast != null) { var cntrEnd = LocationHelper.GetLocCntrRel(fulast.S_LOC_CODE); if (cntrEnd.Count > 0) { endLayer = cntrEnd.Count; endBit = fulast; cntrRel = cntrEnd.FirstOrDefault(); } } if (endBit != null) { break; } } } //bitslocs = bitslocs.OrderBy(x => x.N_CURRENT_NUM).ToList(); //var _locl = bitslocs.Find(x => x.S_LOCK_STATE.Trim() == "无"); //if (_locl != null) //{ // var cntrEnd = LocationHelper.GetLocCntrRel(_locl.S_LOC_CODE); // if (cntrEnd.Count > 0) // { // endLayer = cntrEnd.Count; // endBit = _locl; // cntrRel = cntrEnd.FirstOrDefault(); // } // else // { // LogHelper.Info($"-{_locl.S_LOC_CODE} 没绑定筐。"); // } //} //else //{ // LogHelper.Info($"没有可用的即产空框,无法生成搬运任务。"); //} if (endBit == null) { if (turn) { turn = false; tt = "注塑即产空筐上线(瓶盖)"; goto ___label__else; } else goto ______label____end; } carryCntrs = new List { cntrRel.S_CNTR_CODE };//DateTime.Now.ToString("yyMMddHHmmss") }; re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, tt, carryCntrs, endLayer, 1, carryCntrs.Count, plc.taskPri + 2); if (re) { LogHelper.Info($"{plc.deviceName} 当前机器{startbit}位置正在执行{endBit.S_LOC_CODE.Trim()}:{endBit.N_CURRENT_NUM}:{endLayer}送空任务{JsonConvert.SerializeObject(carryCntrs)}"); //LocationHelper.SetT_FULL_TIME(location_.S_LOC_CODE, null); } res = re; goto ______label____end; //else //{ ___label__else: var area = areaList.FirstOrDefault(); if (areaList.Count > 0) areaList.Remove(area); tt = "注塑库存空筐上线(瓶盖)"; ////要求不实用空框入库位空框。 //bitslocs = LocationHelper.GetAllLocList().Where(x => x.N_CURRENT_NUM > 0 && l.Contains(x.S_LOC_CODE.Trim())).ToList(); bitslocs = LocationHelper.GetLocList(x => x.S_AREA_CODE == area && x.N_CURRENT_NUM > 0).ToList(); if (bitslocs.Count == 0) { LogHelper.Info($"{ba2.NotUsingEmpty}位的没有可用的空筐"); endBit = null; goto ______label____end111; } //bitslocs = bitslocs.OrderBy(x => x.N_ROW).OrderBy(x => x.N_COL).ToList(); bitslocs = bitslocs.OrderBy(x => x.N_CURRENT_NUM).ToList(); foreach (var _locrow in bitslocs.GroupBy(x => x.N_ROW).OrderBy(x => x.Count(y => y.N_CURRENT_NUM > 0)).ThenBy(x => x.Key)) { var _locles = _locrow.ToList(); if (_locles.Find(x => x.S_LOCK_STATE != "无") != null) continue; var _locle = _locles.FindAll(x => x.N_CURRENT_NUM > 0).OrderByDescending(x => x.N_COL).FirstOrDefault(); if (_locle.S_LOCK_STATE.Trim() == "无" && _locle.N_CURRENT_NUM > 0) { var cntrEnd = LocationHelper.GetLocCntrRel(_locle.S_LOC_CODE); if (cntrEnd.Count > 0) { endLayer = cntrEnd.Count; endBit = _locle; cntrRel = cntrEnd.FirstOrDefault(); break; } else { LogHelper.Info($"-{_locle.S_LOC_CODE} 没绑定筐。"); continue; } } } if (endBit == null || cntrRel == null) { LogHelper.Info($"{plc.deviceName} 当前机器{startbit} {endBit == null || cntrRel == null} 无法送空。 "); goto ______label____end111; } ______label____end111: if (endBit == null) { if (areaList.Count > 0) goto ___label__else; else goto ______label____end; } carryCntrs = new List { cntrRel.S_CNTR_CODE };//DateTime.Now.ToString("yyMMddHHmmss") }; re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, tt, carryCntrs, endLayer, 1, carryCntrs.Count, plc.taskPri + 1); if (re) { LogHelper.Info($"{plc.deviceName}-{startbit}正在执行送空"); //LocationHelper.SetT_FULL_TIME(location_.S_LOC_CODE, null); } res = re; goto ______label____end; //} } #region noooooo //else if (plc.deviceType == 4) //{ // var ba = Settings.GetBolAreaList().Find(x => x.DeviceName == plc.deviceName && x.deviceType == plc.deviceType); // if (ba == null) // { // LogHelper.Info($"{plc.deviceName}-{workOrder.SQL_WorkNo}的 BolArea 未配置。"); // return false; // } // var bitslocs = LocationHelper.GetAreaNormalLocList(isusing ? ba.UsingBolArea : ba.NotUsingBolArea); // //从非即产拉, 非即产没有,就申请出库。 出库按最早时间算,如果最早时间的有出库任务,就等待 // if (!bitslocs.Any()) // { // LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,没有可用读取位置了"); // return false; // } // foreach (var item in bitslocs) // { // if (item.N_CURRENT_NUM > 0) // { // endBit = item; // break; // } // } // List cntrRel = new List(); // if (endBit == null) // { // if (bitslocs.Find(x => x.N_CURRENT_NUM == 0) != null) // { // LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,没有可用Kong位置了"); // return false; // } // startbit = bitslocs.Find(x => x.N_CURRENT_NUM == 0).S_LOC_CODE; // var loclist = LocationHelper.GetAreaNormalLocList("PGSGCK"); // foreach (var item in loclist) // { // if (item.N_CURRENT_NUM == 0) continue; // var loccntr = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); // if (!loccntr.Any()) continue; // var cnitem = ContainerHelper.GetCntrItemRel(loccntr.FirstOrDefault().S_LOC_CODE); // if (!cnitem.Any()) continue; // if (cnitem.FirstOrDefault().S_ITEM_CODE != workOrder.SQL_ItemCode) continue; // cntrRel = loccntr; // endBit = item; // } // if (endBit == null) // { // LogHelper.Info(plc.deviceName + plc.deviceType + " 水盖的出库位,没有筐,或者筐物料S_ITEM_CODE数据和工单SQL_ItemCode对不上。"); // } // if (startbit != null && endBit != null) // { // var carryCntrs = cntrRel.OrderByDescending(x => x.T_CREATE).Select(x => x.S_CNTR_CODE).Take(1).ToList();//DateTime.Now.ToString("yyMMddHHmmss") }; // var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, "库存盖坯出库(4", carryCntrs, endLayer, 1, carryCntrs.Count, plc.taskPri + 1); // } // } //} #endregion else if (plc.deviceType == 6 || plc.deviceType == 10 || plc.deviceType == 4) { LogHelper.Info("plc.deviceType == 6.10.4" + workOrder.SQL_UsingNow); //var LineTo = workOrder.SQL_LinkLineNO; var ba = Settings.GetBolAreaList().Find(x => x.DeviceName == plc.deviceName && x.deviceType == plc.deviceType); if (ba == null) { LogHelper.Info($"{plc.deviceName}-{workOrder.SQL_WorkNo}的 BolArea 未配置。"); goto ______label____end; } var bitslocs = LocationHelper.GetAreaNormalLocList(isusing ? ba.UsingBolArea : ba.NotUsingBolArea); //从非即产拉, 非即产没有,就申请出库。 出库按最早时间算,如果最早时间的有出库任务,就等待 if (!bitslocs.Any() && plc.deviceType == 10) { LogHelper.Info(plc.deviceName + plc.deviceType + "的线边位,没有可用读取位置了"); goto ______label____end; } List cntrRel = new List(); var turn = false; if (isusing) { turn = true; ////endBit = bitslocs.Find(x => x.N_CURRENT_NUM > 0 && x.T_FULL_TIME == null); ////LogHelper.Info($" [{endBit?.S_LOC_CODE}][前面如果是空的,就按排分组筛选]-可用排是{JsonConvert.SerializeObject(bitslocs.Select(x => x.N_ROW).Distinct())}"); ////if (endBit != null) ////{ //// //endBit = null; //// endBit = bitslocs.FindAll(x => x.N_ROW == endBit.N_ROW && x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); //// cntrRel = GetLocCntrRel(endBit.S_LOC_CODE); //// //endLayer = endBit.N_CURRENT_NUM; ////} ////else { if (true) { if (bitslocs.Any()) { var rowlist = LocationHelper.GetRowLock(ba.UsingBolArea); var t = DateTime.Now; //foreach (var itemrs in _l.GroupBy(x => x.N_ROW).OrderBy(y => rowlist.Find(x => x.S_LOCK_STATE == "库锁" && x.N_ROW == y.Key)?.T_CREATE ?? t).ThenBy(x => x.Key)) //foreach (var itemrs in bitslocs.GroupBy(x => x.N_ROW).OrderBy(y => rowlist.Find(x => x.S_LOCK_STATE == "出库锁" && x.N_ROW == y.Key)?.T_CREATE ?? t).ThenBy(x => x.Count(y => y.N_CURRENT_NUM > 0))) foreach (var itemrs in bitslocs.GroupBy(x => x.N_ROW).OrderBy(y => rowlist.Find(x => x.S_LOCK_STATE == "出库锁" && x.N_ROW == y.Key)?.T_CREATE ?? t).ThenBy(x => x.Count(y => y.N_CURRENT_NUM > 0))) { if (rowlist.Find(x => x.S_LOCK_STATE == "入库锁" && x.N_ROW == itemrs.Key) != null) continue; var _r = itemrs.ToList(); var f = _r.FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); if (f != null) { cntrRel = LocationHelper.GetLocCntrRel(f.S_LOC_CODE); if (cntrRel.Any()) { var _pc = Settings.GetDeviceInfoList().Find(x => x.deviceName == workOrder.SQL_LinkLineNO && x.enable == 1); if (_pc != null) { LogHelper.Info($"{workOrder.SQL_LinkLineNO} - 叫筐,找到位置{f.S_LOC_CODE}- 对应设备:{_pc.deviceType}, 时间{f.T_FULL_TIME}"); if (_pc.deviceType == 2)// && string.IsNullOrEmpty(cntrRel.FirstOrDefault()?.S_TYPE)) { if (DateTime.Now.Subtract(f.T_FULL_TIME ?? DateTime.Now) < TimeSpan.FromHours(1.5)) { continue; } } } else { LogHelper.Info($"{workOrder.SQL_LinkLineNO} - 叫筐,找到位置{f.S_LOC_CODE}-{workOrder.SQL_LinkLineNO}>{workOrder.SQL_ItemCode} 没有对应查询,"); continue; } endBit = f; } } if (endBit != null) break; } } } if (false) { var hasRows = bitslocs.FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.T_FULL_TIME); //var EptRows = allrows.Except(hasRows.Select(x => x.N_ROW).Distinct()); LogHelper.Info($"{plc.deviceName} - 即产上线,检验出库数据。最先入库排顺序{JsonConvert.SerializeObject(hasRows.Select(x => x.N_ROW).Distinct())}"); //最后一个入的排,如果是满的就找空的。 if (hasRows.Any()) { var lastFull = hasRows.FirstOrDefault(); endBit = bitslocs.FindAll(x => x.N_ROW == lastFull.N_ROW && x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); } else LogHelper.Info($"{plc.deviceName} - 即产上线,没有可出库数据。"); if (endBit != null) { endLayer = endBit.N_CURRENT_NUM; cntrRel = LocationHelper.GetLocCntrRel(endBit.S_LOC_CODE); } } if (false) foreach (var item in bitslocs.FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.T_FULL_TIME).GroupBy(x => x.N_ROW)) { var itlast = item.ToList().OrderBy(x => x.N_COL).LastOrDefault(); if (itlast != null) { endBit = itlast; endLayer = endBit.N_CURRENT_NUM; cntrRel = LocationHelper.GetLocCntrRel(endBit.S_LOC_CODE); } if (endBit != null) break; } if (false) foreach (var item in bitslocs.OrderBy(x => x.T_FULL_TIME)) { if (item.N_CURRENT_NUM > 0) { endBit = item; endLayer = endBit.N_CURRENT_NUM; cntrRel = LocationHelper.GetLocCntrRel(endBit.S_LOC_CODE); break; } } } //var locs = LocationHelper.GetLocList(x => x.S_AREA_CODE == ba.UsingBolArea && x.S_LOC_CODE != "报废").OrderBy(x => x.N_COL).ThenByDescending(x => x.N_ROW).ToList(); //var lastffl = locs.FindAll(x => x.N_CURRENT_NUM > 0 && x.T_FULL_TIME != null).OrderBy(x => x.T_FULL_TIME).LastOrDefault(); //var lastEmpty = locs.FindAll(x => x.N_CURRENT_NUM == 0 && x.T_EMPTY_TIME != null).OrderBy(x => x.T_EMPTY_TIME).LastOrDefault(); //LogHelper.Info($"{locs.Count}-{lastffl?.S_LOC_CODE}{lastEmpty?.S_LOC_CODE}"); //if (lastEmpty != null) //{ // if (lastffl == null) lastEmpty = null; // else if (lastEmpty.N_COL <= lastffl.N_COL) { lastffl = null; lastEmpty = null; } // else if (lastEmpty == locs.LastOrDefault()) lastEmpty = null; //} //LogHelper.Info($"{(lastEmpty == null || lastEmpty == locs.LastOrDefault() ? 0 : locs.IndexOf(lastEmpty))}"); /////最后一个满框入库位往后找。 //var locccccs = locs.Skip((lastEmpty == null || lastEmpty == locs.LastOrDefault() ? 0 : locs.IndexOf(lastEmpty))); //if (locccccs.ToList().Find(x => x.N_CURRENT_NUM > 0) == null) // locccccs = locs; //foreach (var item in locccccs.GroupBy(x => x.N_COL)) //{ // ///先放小排, 先取大排 取放按列 // var collist = item.OrderByDescending(x => x.N_ROW).ToList(); // if (!collist.Any()) continue; // if (collist.Find(x => x.S_LOCK_STATE != "无") != null) continue; // Location nex = collist.Find(x => x.N_CURRENT_NUM > 0); // if (nex != null) // { // endBit = nex; // endLayer = endBit.N_CURRENT_NUM; // cntrRel = LocationHelper.GetLocCntrRel(endBit.S_LOC_CODE); // break; // } //} } else if (plc.deviceType == 10) { foreach (var item in bitslocs) { if (item.N_CURRENT_NUM > 0) { endBit = item; //endLayer = endBit.N_CURRENT_NUM; cntrRel = LocationHelper.GetLocCntrRel(endBit.S_LOC_CODE); break; } } } if (plc.deviceType != 10 && endBit == null) if (!isusing || turn) { //var rowlist = LocationHelper.GetRowLock(item); //foreach (var itemrs in _l.GroupBy(x => x.N_ROW).OrderBy(y => rowlist.Find(x => x.S_LOCK_STATE == "入库锁" && x.N_ROW == y.Key) != null ? 0 : 1).ThenByDescending(x => x.Count(y => y.N_CURRENT_NUM > 0))) //{ // if (rowlist.Find(x => x.S_LOCK_STATE == "出库锁" && x.N_ROW == itemrs.Key) != null) continue; foreach (var item in plc.areaPriy) { bitslocs = LocationHelper.GetAreaNormalLocList(item); if (bitslocs.Any()) { var rowlist = LocationHelper.GetRowLock(item); var t = DateTime.Now; //foreach (var itemrs in _l.GroupBy(x => x.N_ROW).OrderBy(y => rowlist.Find(x => x.S_LOCK_STATE == "库锁" && x.N_ROW == y.Key)?.T_CREATE ?? t).ThenBy(x => x.Key)) /// foreach (var itemrs in bitslocs.GroupBy(x => x.N_ROW).OrderBy(y => rowlist.Find(x => x.S_LOCK_STATE == "出库锁" && x.N_ROW == y.Key)?.T_CREATE ?? t).ThenBy(x => x.Count(y => y.N_CURRENT_NUM > 0))) { if (rowlist.Find(x => x.S_LOCK_STATE == "入库锁" && x.N_ROW == itemrs.Key) != null) continue; var _r = itemrs.ToList(); var f = _r.FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); if (f != null) { cntrRel = LocationHelper.GetLocCntrRel(f.S_LOC_CODE); var cntrrel = ContainerHelper.GetCntrItemRel(cntrRel.FirstOrDefault()?.S_CNTR_CODE); if (cntrrel.FirstOrDefault()?.S_ITEM_CODE != $"{workOrder.SQL_LinkLineNO}>{workOrder.SQL_ItemCode}") //if (rel.FirstOrDefault()?.S_TYPE != $"{workOrder.SQL_PLineNo}>{SQL_ItemCode}") { //LogHelper.Info($"{f.S_LOC_CODE} 位置的 物料{cntrrel.FirstOrDefault()?.S_ITEM_CODE} 与本次下线{workOrder.SQL_PLineNo}>{workOrder.SQL_ItemCode} 不符。 筛选下一排"); continue; } var _pc = Settings.GetDeviceInfoList().Find(x => x.deviceName == workOrder.SQL_LinkLineNO && x.enable == 1); if (_pc != null) { if (_pc.deviceType == 2) { if (DateTime.Now.Subtract(cntrRel.OrderBy(x => x.T_CREATE).LastOrDefault().T_CREATE) < TimeSpan.FromHours(1.5)) { continue; } } } else { LogHelper.Info($"{workOrder.SQL_LinkLineNO} - 叫筐,找到位置{f.S_LOC_CODE}-{workOrder.SQL_LinkLineNO}>{workOrder.SQL_ItemCode} 没有对应查询,"); continue; } endBit = f; } if (endBit != null) break; } } if (endBit != null) break; } } //if (endBit == null) //{ // if (bitslocs.Find(x => x.N_CURRENT_NUM == 0) == null) // { // LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,没有可用Kong位置了"); // return false; // } // startbit = bitslocs.Find(x => x.N_CURRENT_NUM == 0).S_LOC_CODE; // var loclist = LocationHelper.GetLocList(x => x.S_AREA_CODE == "PGWJCK"); // var oneonelist = loclist.GroupBy(x => x.N_ROW).Select(x => x.ToList().Find(y => y.S_LOCK_STATE == "无" && y.N_CURRENT_NUM > 0)).ToList(); // foreach (var item in oneonelist.OrderBy(x => x.T_CREATE)) // { // var loccntr = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); // if (loccntr.Any() && loccntr.FirstOrDefault()?.S_TYPE == LineTo) // { // //这里就是该机器的最后一次入库列。 // var rl = loclist.FindAll(x => x.N_ROW == item.N_ROW); // if (rl.Find(x => x.S_LOCK_STATE != "无" && x.S_LOCK_STATE != "报废") != null) // { // break; // } // var crl = rl.FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); // endBit = crl; // break; // } // if (endBit != null) // cntrRel = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); // } //} if (startbit != null && endBit != null) { var carryCntrs = cntrRel.OrderByDescending(x => x.T_CREATE).Select(x => x.S_CNTR_CODE).Take(1).ToList();//DateTime.Now.ToString("yyMMddHHmmss") }; //if (carryCntrs.Count > 3) //{ // carryCntrs = carryCntrs.Take(carryCntrs.Count - 3).ToList(); // endLayer = 4; //} var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, "翻斗机" + (isusing ? "即产" : "库存") + "满筐上线(瓶盖)", carryCntrs, endBit.N_CURRENT_NUM, 1, carryCntrs.Count, plc.taskPri + 1); } else { LogHelper.Info($"4610,没有可用满框"); } } else { LogHelper.Info(plc.deviceName + plc.deviceType + "当前不是 坯、盖 FDJ"); } } else { LogHelper.Info("起点找不到机器PLC, 失败"); } ______label____end: GetT_FULL_ready[startbit] = false; return res; } /* | 即产空框区 UsingEmpty ;分开 PG | 非即产空框区 NotUsingEmpty ;分开 | 即产满框区 ->工单设置 | 非即产满区 ->s_row 工单选择 Auto:Y,按s_row 的库区 2排一组筛选 | 即产满 工单设置 FDJ| 非即产满 NotUsingBolArea | 即产空 暂定UsingEmpty吧 | 非即产空 暂定NotUsingEmpty吧 */ [Obsolete] public static bool TakeEmptyToBottleBoyd2346(WMSTask mst) { var startbit = mst.S_START_LOC.Trim(); bool res = false; var hasin = false; GetT_FULL_ready.TryGetValue(startbit, out hasin); if (hasin) { LogHelper.Info($"{startbit} 胚盖送空 / 翻斗机取满 流程 已在筛选中。"); return true; } else { if (GetT_FULL_ready.ContainsKey(startbit)) GetT_FULL_ready[startbit] = true; else GetT_FULL_ready.Add(startbit, true); } var plc = Settings.GetDeviceInfoList().Where(a => a.location.Contains(startbit) && a.enable == 1).FirstOrDefault(); LogHelper.Info($"{startbit} 开始 胚盖送空 / 翻斗机取满 流程"); if (plc != null) { var workOrder = WCSHelper.GetWorkOrder(plc.deviceName); if (workOrder == null) { LogHelper.Info($"工单没有执行,送空流程取消", "PEM机"); goto ______label____end; } if (plc.deviceType <= 3 || plc.deviceType == 4 || plc.deviceType == 6 || plc.deviceType == 10) { var ret = false; LocationHelper.DoAction(db => { var tasks = db.Queryable().Where(x => x.S_START_LOC == startbit && "取货完成,开始卸货,卸货完成".Contains(x.S_B_STATE)).ToList(); if (tasks.Any()) { LogHelper.Info($"{startbit} 的下线任务还没完成。 等待完成后 在呼叫二段任务(翻斗机取空卸货,或者瓶盖满框卸货!"); ret = true; } return true; }); if (ret) goto ______label____end; ; } var isusing = workOrder.SQL_UsingNow.Trim() == "Y"; Location endBit = null; var loc_list_PEM = new List(); // 水 无菌 盖机 if (plc.deviceType <= 3) { var ba = Settings.GetBolAreaList().Find(x => x.DeviceName == plc.deviceName && x.deviceType == plc.deviceType); if (ba == null) { LogHelper.Info($"{plc.deviceName}-{workOrder.SQL_WorkNo}的 BolArea 未配置。"); goto ______label____end; } if (isusing) { List lp_ = new List(); //即产即用时 必填的。 var _l = LocationHelper.GetAllLocListByAreaCode(workOrder.SQL_Area, 0, 0).FindAll(x => x.S_LOCK_STATE != "入库锁" && x.S_LOCK_STATE != "报废"); var UsingEnough = _l.FindAll(x => x.S_LOCK_STATE.Trim() == "出库锁").Count + _l.FindAll(x => x.S_LOCK_STATE == "无" && x.N_CURRENT_NUM < x.N_CAPACITY).Count; if (UsingEnough > 0) { foreach (var _oloc in plc.location) { if (_oloc != startbit) { var _ctrl = LocationHelper.GetLocCntrRel(_oloc); if (_ctrl.Count > 0 && _ctrl.FirstOrDefault().S_CNTR_CODE.Contains("J")) UsingEnough--; } } } else { LogHelper.Info($"{workOrder.SQL_WorkNo} 链接的即产满框区{workOrder.SQL_Area}位置不足。叫筐切筐。"); } //即产即用满框有空位 if (UsingEnough > 0) //lp_ = LocationHelper.GetAllLocListByAreaCode("JCJYKK", 0, 0).FindAll(x => x.S_LOCK_STATE == "无" && x.N_CURRENT_NUM > 0); { foreach (var area in ba.UsingEmpty.Split(';')) { var bitslocs = LocationHelper.GetAreaNormalLocList(area); foreach (var locsss in bitslocs.GroupBy(x => x.N_ROW)) { var locss = locsss.OrderByDescending(x => x.N_COL).ToList().Find(x => x.N_CURRENT_NUM > 0); var _ctrl = LocationHelper.GetLocCntrRel(locss.S_LOC_CODE); if (_ctrl.Count > 0 && _ctrl.FirstOrDefault().S_CNTR_CODE.Contains("J")) { loc_list_PEM = _ctrl; goto bbbb; } } } } bbbb: if (loc_list_PEM.Count > 0) { var location_ = loc_list_PEM.FirstOrDefault(); var carryCntrs = new List { location_.S_CNTR_CODE };//DateTime.Now.ToString("yyMMddHHmmss") }; var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, location_.S_LOC_CODE.Trim(), startbit, "瓶盖-空上机", carryCntrs, loc_list_PEM.Count, 1, carryCntrs.Count, plc.taskPri + 2); if (re) { LogHelper.Info($"{plc.deviceName}-{startbit}正在执行送空"); } res = re; goto ______label____end; } else { // 转筐 //时间分钟 DateTime dateTime = DateTime.Now; if (Turn_ready.TryGetValue(startbit, out dateTime)) { if (DateTime.Now.Subtract(dateTime).TotalMinutes > plc.EmptyWait) { Turn_ready.Remove(startbit); goto labelUsingNo; } else { if (UsingEnough > 0) LogHelper.Info($"{workOrder.SQL_WorkNo} 即产空框不足。。叫筐切筐等待时间不足{plc.EmptyWait}分钟。"); else LogHelper.Info($"{workOrder.SQL_WorkNo} 链接的即产满框区{workOrder.SQL_Area}位置不足,叫筐切筐等待时间不足{plc.EmptyWait}分钟。"); } } else { Turn_ready.Add(startbit, DateTime.Now); } LogHelper.Info(plc.deviceName + "[" + startbit + "]送空托 失败,没有空托了"); goto ______label____end; } } labelUsingNo: { List areasssss = ba.NotUsingEmpty.Split(';').ToList(); balellll: loc_list_PEM.Clear(); var _areaCode = areasssss.FirstOrDefault(); areasssss.Remove(_areaCode); var _l = LocationHelper.GetAreaNormalLocList(_areaCode); //endBit = _l?.OrderBy(x => x.N_ROW).ThenByDescending(x => x.N_COL).ToList().Find(x => x.N_CURRENT_NUM > 0); foreach (var locsss in _l.GroupBy(x => x.N_ROW)) { var locss = locsss.OrderByDescending(x => x.N_COL).ToList().Find(x => x.N_CURRENT_NUM > 0); var _ctrl = LocationHelper.GetLocCntrRel(locss.S_LOC_CODE); if (_ctrl.Count > 0 && _ctrl.FirstOrDefault().S_CNTR_CODE.Contains("F")) { endBit = locss; loc_list_PEM = _ctrl; break; } } if (loc_list_PEM.Any()) { var carryCntrs = new List { loc_list_PEM.FirstOrDefault().S_CNTR_CODE };//DateTime.Now.ToString("yyMMddHHmmss") }; var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, "瓶盖-空上机", carryCntrs, loc_list_PEM.Count, 1, carryCntrs.Count, plc.taskPri + 2); if (re) { LogHelper.Info($"{plc.deviceName}-{startbit}正在执行送空"); } res = re; goto ______label____end; } else { LogHelper.Info(_areaCode + "没有可搬运的空框"); if (areasssss.Count > 0) goto balellll; } } } //水 无菌 翻斗机。 else if (plc.deviceType == 4 || plc.deviceType == 6) { endBit = null; loc_list_PEM.Clear(); var ba = Settings.GetBolAreaList().Find(x => x.DeviceName == plc.deviceName && x.deviceType == plc.deviceType); if (ba == null) { LogHelper.Info($"{plc.deviceName}-{workOrder.SQL_WorkNo}的 BolArea 未配置。"); goto ______label____end; } //var bitslocs = LocationHelper.GetAreaNormalLocList(isusing ? ba.UsingBolArea : ba.NotUsingBolArea); ////从非即产拉, 非即产没有,就申请出库。 出库按最早时间算,如果最早时间的有出库任务,就等待 //if (!bitslocs.Any()) //{ // LogHelper.Info(plc.deviceName + plc.deviceType + "的线边位,没有可用读取位置了"); // goto ______label____end; //} var LineTo = workOrder.SQL_LinkLineNO; var SQL_ItemCode = workOrder.SQL_ItemCode; var lis = $"{LineTo}>{SQL_ItemCode}"; string cntrcode = ""; if (isusing) { var _l = LocationHelper.GetAreaNormalLocList(workOrder.SQL_Area); foreach (var locRow in _l.GroupBy(x => x.N_ROW)) { var locss = locRow.OrderByDescending(x => x.N_COL).ToList().Find(x => x.N_CURRENT_NUM > 0); var _ctrl = LocationHelper.GetLocCntrRel(locss.S_LOC_CODE); if (_ctrl.Count > 0 && _ctrl.FirstOrDefault().S_CNTR_CODE.Contains("J")) { var cntrrel = ContainerHelper.GetCntrItemRel(_ctrl.FirstOrDefault()?.S_CNTR_CODE); if (cntrrel.FirstOrDefault()?.S_ITEM_CODE == lis) { endBit = locss; loc_list_PEM = _ctrl; cntrcode = _ctrl.FirstOrDefault().S_CNTR_CODE; LogHelper.Info($"翻斗机即产满筐上线 筛选位置:{locss.S_LOC_CODE}-{loc_list_PEM.First().S_CNTR_CODE}-{cntrcode}"); break; } } } if (endBit != null) { var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, "翻斗机即产满筐上线(瓶盖)", new List { cntrcode }, endBit.N_CURRENT_NUM, 1, 1, plc.taskPri + 1); goto ______label____end; } else { LogHelper.Info($"{startbit} - 即产满框区 没有筐了 切筐。"); goto Notusing; } } Notusing: { if (!string.IsNullOrEmpty(workOrder.S_ROW1)) { var rs = workOrder.S_ROW1.Split('='); var rows = Array.ConvertAll(rs[rs.Length - 1].Split('-'), Convert.ToInt32); var locs = LocationHelper.GetAreaNormalLocList(rs[0]).FindAll(x => rows.Contains(x.N_ROW)); foreach (IGrouping item in locs.GroupBy(x => x.N_ROW).OrderBy(x => x.Count(y => y.N_CURRENT_NUM > 0))) { List _cols = item.OrderBy(x => x.N_COL).ToList(); Location e = _cols.FindAll((Location x) => x.N_CURRENT_NUM > 0).LastOrDefault();//从左往右最后一个满位。 if (e != null) { var rel = LocationHelper.GetLocCntrRel(e.S_LOC_CODE); if (rel.Count > 0 && rel.FirstOrDefault().S_CNTR_CODE.Contains("F")) { var cntrrel = ContainerHelper.GetCntrItemRel(rel.FirstOrDefault()?.S_CNTR_CODE); if (cntrrel.FirstOrDefault()?.S_ITEM_CODE == lis) { endBit = e; loc_list_PEM = rel; break; } } } //else LogHelper.Info($"({rs[0]})>{item.Key}空排"); } } if (endBit == null) foreach (var area in ba.NotUsingBolArea.Split(';')) { var _l = LocationHelper.GetAreaNormalLocList(area); foreach (var locRow in _l.GroupBy(x => x.N_ROW)) { var locss = locRow.OrderByDescending(x => x.N_COL).ToList().Find(x => x.N_CURRENT_NUM > 0); var _ctrl = LocationHelper.GetLocCntrRel(locss.S_LOC_CODE); if (_ctrl.Count > 0 && _ctrl.FirstOrDefault().S_CNTR_CODE.Contains("F")) { var cntrrel = ContainerHelper.GetCntrItemRel(_ctrl.FirstOrDefault()?.S_CNTR_CODE); if (cntrrel.FirstOrDefault()?.S_ITEM_CODE == lis) { endBit = locss; loc_list_PEM = _ctrl; break; } } } } if (endBit != null) { var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit, "翻斗机库存满筐上线(瓶盖)", new List { loc_list_PEM.First().S_CNTR_CODE }, endBit.N_CURRENT_NUM, 1, 1, plc.taskPri + 1); goto ______label____end; } } } else { LogHelper.Info($"{startbit} -plcdeviceType:{plc.deviceType} 位置类型。!2346"); } } else { LogHelper.Info("起点找不到机器PLC, 失败"); } ______label____end: GetT_FULL_ready[startbit] = false; return res; } //public Location GetLast /// /// 仓库空框 出瓶盖线边 - s_type 水盖空框, 无菌空框 /// /// /// /// /// 空框标识 public static void TakeEmpty2PGxb(Settings.BolArea ba, Settings.deviceInfo plc, WorkOrder workOrder, string ConNmae, int __iii) { var bitslocs = LocationHelper.GetAreaNormalLocList(ba.NotUsingBolArea); // 非即产 申请出库。 出库按最早时间算,如果最早时间的有出库任务,就等待 if (!bitslocs.Any()) { LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,没有可用读取位置了"); return; } Location endBit = null; Location startbit = null; List cntrRel = new List(); if (endBit == null) { if (bitslocs.Find(x => x.N_CURRENT_NUM == 0) != null) { LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,空转胚盖线边,没有可用Kong位置了"); return; } if (__iii == 1)///即产下, 有非即产就行了, 不要出太多。 { if (bitslocs.Find(x => x.N_CURRENT_NUM > 0) != null) return; } //if (__iii == 0)//留一个空位。就不再出了 //{ // int erow = 0; // foreach (var item in bitslocs.GroupBy(x => x.N_ROW)) // { // if (item.ToList().Find(x => x.N_CURRENT_NUM > 0) == null) // erow++; // } // if (erow < 2) // { // LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边空位,因为出入库共用位置, 目前就一个空位了,不再出库。"); // return; // } //} startbit = bitslocs.Find(x => x.N_CURRENT_NUM == 0); var loclist = LocationHelper.GetLocList(x => x.S_AREA_CODE == (plc.deviceType == 2 ? "PGWJCK" : "SGK")); //var oneonelist = loclist.GroupBy(x => x.N_ROW).Select(x => x.ToList().Find(y => y.S_LOCK_STATE == "无" && y.N_CURRENT_NUM > 0)).ToList(); //LogHelper.Info($"oneonelist" + oneonelist?.Count); //foreach (var item in oneonelist.OrderBy(x => x.T_CREATE)) //{ // LogHelper.Info($"oneonelist1" + oneonelist?.Count); var oneonelist = loclist.OrderBy(x => x.T_FULL_TIME).GroupBy(x => x.N_ROW);//.Select(x => x.ToList().Find(y => y.N_CURRENT_NUM > 0)).ToList(); LogHelper.Info($"oneonelist非即产空框出瓶盖线边" + oneonelist?.Count()); foreach (var itemr in oneonelist) { var item = itemr.ToList().FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); if (item == null) continue; var loccntr = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); if (loccntr.Any() && loccntr.FirstOrDefault().S_TYPE.Contains(ConNmae)) { //这里就是该机器的最后一次入库列。 var rl = loclist.FindAll(x => x.N_ROW == item.N_ROW); if (rl.Find(x => x.S_LOCK_STATE != "无" && x.S_LOCK_STATE != "报废") != null) { continue; } var crl = rl.FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); endBit = crl; break; } if (endBit != null) cntrRel = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); } } if (startbit != null && endBit != null) { int endLayer = 1; var carryCntrs = cntrRel.OrderByDescending(x => x.T_CREATE).Select(x => x.S_CNTR_CODE).ToList();//DateTime.Now.ToString("yyMMddHHmmss") }; if (carryCntrs.Count > 3) { carryCntrs = carryCntrs.Take(carryCntrs.Count - 3).ToList(); endLayer = 4; } var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit.S_LOC_CODE, "瓶盖空筐转运-2J", carryCntrs, endLayer, 1, carryCntrs.Count, plc.taskPri + 1); } } public static void WJGTakeFull2FDJXB(Settings.BolArea ba, Settings.deviceInfo plc, WorkOrder workOrder, LingItemOrder od = null) { var LineTo = workOrder.SQL_LinkLineNO; if (string.IsNullOrEmpty(LineTo)) { LogHelper.Info(plc.deviceName + workOrder.SQL_WorkNo + "的链接产线为空,无法确定出库的机器标识"); return; } var bitslocs = LocationHelper.GetAreaNormalLocList(ba.NotUsingBolArea); // 非即产 申请出库。 出库按最早时间算,如果最早时间的有出库任务,就等待 if (!bitslocs.Any()) { LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边没可用位置,无法满出库"); return; } // 因为出入库共用位置。 如果翻斗机是非即产。 入库时必留一个空位。 // 所以 这里判断如果空位<2 就不出库了。 //int erow = 0; //foreach (var item in bitslocs.GroupBy(x => x.N_ROW)) //{ // if (item.ToList().Find(x => x.N_CURRENT_NUM > 0) == null) // erow++; //} //if (erow < 2) //{ // LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,因为出入库共用位置, 目前就一个空位了,不再出库。"); // return; //} Location endBit = null; Location startbit = null; int pcnum = 0; List cntrRel = new List(); if (endBit == null) { if (bitslocs.Find(x => x.N_CURRENT_NUM == 0) != null) { LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边没可用Kong位,无法满框出库"); return; } startbit = bitslocs.Find(x => x.N_CURRENT_NUM == 0); var loclist = LocationHelper.GetAreaNormalLocList((plc.deviceType == 6 ? "PGWJCK" : "SGK"));//LocationHelper.GetLocList(x => x.S_AREA_CODE == (plc.deviceType == 6 ? "PGWJCK" : "SGK")); //var oneonelist = loclist.GroupBy(x => x.N_ROW).Select(x => x.ToList().Find(y => y.S_LOCK_STATE == "无" && y.N_CURRENT_NUM > 0)).ToList(); //foreach (var item in oneonelist.OrderBy(x => x.T_CREATE)) //{ var oneonelist = loclist.OrderBy(x => x.T_FULL_TIME).GroupBy(x => x.N_ROW);//.Select(x => x.ToList().Find(y => y.N_CURRENT_NUM > 0)).ToList(); LogHelper.Info($"oneonelist非即产出翻斗线边" + oneonelist?.Count()); foreach (var itemr in oneonelist) { var item = itemr.ToList().FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); if (item == null) continue; var loccntr = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); if (loccntr.Any() && loccntr.FirstOrDefault().S_TYPE.Contains(LineTo)) { //这里就是该机器的最后一次入库列。 var rl = loclist.FindAll(x => x.N_ROW == item.N_ROW); if (rl.Find(x => x.S_LOCK_STATE != "无" && x.S_LOCK_STATE != "报废") != null) { continue; } var crl = rl.FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); var cntrEnd = LocationHelper.GetLocCntrRel(crl?.S_LOC_CODE); if (cntrEnd.Count > 0) { var cntritemrel = ContainerHelper.GetCntrItemRel(cntrEnd.FirstOrDefault().S_CNTR_CODE); pcnum = cntritemrel?.FirstOrDefault()?.qty ?? 0; if (od != null) { if (cntritemrel.Count == 0)// || od.ItemCode != cntritemrel.FirstOrDefault().S_ITEM_CODE) { LogHelper.Info($"富勒工单, 托盘码{cntrEnd.FirstOrDefault().S_CNTR_CODE}不存在物料,或物料不符合 continue。"); //bbs.Remove(bft); continue; } } else { if (cntritemrel.Count() > 0 && cntritemrel.FirstOrDefault().S_ORDER_NO.Contains("_Y")) { LogHelper.Info($"{workOrder.SQL_WorkNo} 非富勒工单, 但是{crl?.S_LOC_CODE}托盘码{cntrEnd.FirstOrDefault().S_CNTR_CODE}是富勒工单下线,无法生成搬运任务。"); //bbs.Remove(bft); continue; } } } endBit = crl; break; } if (endBit != null) cntrRel = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); } } if (startbit != null && endBit != null) { int endLayer = 1; var carryCntrs = cntrRel.OrderByDescending(x => x.T_CREATE).Select(x => x.S_CNTR_CODE).ToList();//DateTime.Now.ToString("yyMMddHHmmss") }; if (carryCntrs.Count > 3) { carryCntrs = carryCntrs.Take(carryCntrs.Count - 3).ToList(); endLayer = 4; } if (od != null) if (od.AreaNum - od.current - od.AllocQTY < carryCntrs.Count * pcnum) { LogHelper.Info($"领料工单{od.WorkFromNo} 单量{od.AreaNum} 已领{od.current} 分配中{od.AllocQTY} 单托{pcnum} 此次搬运{carryCntrs.Count}托。 出库后数量超出, 不进行领料。"); } var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit.S_LOC_CODE, "库存盖坯出库-2J", carryCntrs, endLayer, 1, carryCntrs.Count, plc.taskPri + 1); if (re && od != null) { LocationHelper.DoAction(db => { od.AllocQTY = od.AllocQTY + carryCntrs.Count * pcnum; db.Updateable(od).UpdateColumns(it => new { it.AllocQTY }).ExecuteCommand(); return true; }); } } } public static void SGTakeFull2FDJXB(Settings.BolArea ba, Settings.deviceInfo plc, WorkOrder workOrder) { var bitslocs = LocationHelper.GetAreaNormalLocList(ba.NotUsingBolArea); // 非即产 申请出库。 出库按最早时间算,如果最早时间的有出库任务,就等待 if (!bitslocs.Any()) { LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,没有可用读取位置了"); return; } ///出入 公用库位。 这里保留一个空位就不出了。 //int erow = 0; //foreach (var item in bitslocs.GroupBy(x => x.N_ROW)) //{ // if (item.ToList().Find(x => x.N_CURRENT_NUM > 0) == null) // erow++; //} //if (erow < 2) //{ // LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,因为出入库共用位置, 目前就一个空位了,不再出库。"); // return; //} Location endBit = null; Location startbit = null; List cntrRel = new List(); if (endBit == null) { if (bitslocs.Find(x => x.N_CURRENT_NUM == 0) != null) { LogHelper.Info(plc.deviceName + plc.deviceType + "的非即产线边位,水盖出翻斗线边,没有可用Kong位置了"); return; } startbit = bitslocs.Find(x => x.N_CURRENT_NUM == 0); var loclist = LocationHelper.GetAreaNormalLocList("PGSGCK"); foreach (var item in loclist) { if (item.N_CURRENT_NUM == 0) continue; var loccntr = LocationHelper.GetLocCntrRel(item.S_LOC_CODE); if (!loccntr.Any()) continue; var cnitem = ContainerHelper.GetCntrItemRel(loccntr.FirstOrDefault().S_LOC_CODE); if (!cnitem.Any()) continue; if (cnitem.FirstOrDefault().S_ITEM_CODE != workOrder.SQL_ItemCode) continue; cntrRel = loccntr; endBit = item; } if (endBit == null) { LogHelper.Info(plc.deviceName + plc.deviceType + " 水盖的出库位,没有筐,或者筐物料S_ITEM_CODE数据和工单SQL_ItemCode对不上。"); } } if (startbit != null && endBit != null) { int endLayer = 1; var carryCntrs = cntrRel.OrderByDescending(x => x.T_CREATE).Select(x => x.S_CNTR_CODE).ToList();//DateTime.Now.ToString("yyMMddHHmmss") }; if (carryCntrs.Count > 3) { carryCntrs = carryCntrs.Take(carryCntrs.Count - 3).ToList(); endLayer = 4; } var re = TaskProcess.CreateTransport(workOrder.SQL_WorkNo, endBit.S_LOC_CODE.Trim(), startbit.S_LOC_CODE, "库存盖坯出库-2J", carryCntrs, endLayer, 1, carryCntrs.Count, plc.taskPri + 1); } } /// /// 删除货位容器表记录,修改货位容器数量 /// /// /// /// public static bool UnBindingLoc(string loc, List cntrs) { var res = false; var db = new SqlHelper().GetInstance(); var location = db.Queryable().Where(a => a.S_LOC_CODE == loc).First(); try { var lcrList = db.Queryable().Where(a => a.S_LOC_CODE == loc).ToList(); int count = lcrList.Count; db.BeginTran(); foreach (var c in cntrs) { var _cr = lcrList.Find(x => x.S_CNTR_CODE.Trim() == c.Trim()); if (_cr != null) { db.Deleteable().Where(it => it.S_ID.Trim() == _cr.S_ID.Trim()).ExecuteCommand(); count--; lcrList.Remove(_cr); } } //int count = db.Deleteable().Where(it => cntrs.Contains(it.S_CNTR_CODE) && it.S_LOC_CODE == loc).ExecuteCommand(); location.N_CURRENT_NUM = count; //if (location.N_CURRENT_NUM < 0) // location.N_CURRENT_NUM = 0; //location.S_LOCK_STATE = "无"; if (location.N_CURRENT_NUM <= 0) { location.N_CURRENT_NUM = 0; location.T_FULL_TIME = null; location.T_EMPTY_TIME = DateTime.Now; } db.Updateable(location).UpdateColumns(it => new { it.N_CURRENT_NUM, it.T_FULL_TIME, it.T_EMPTY_TIME }).ExecuteCommand(); db.Ado.CommitTran(); LogHelper.Info("UnBindingLoc::::" + JsonConvert.SerializeObject(location)); res = true; } catch (Exception ex) { db.Ado.RollbackTran(); } return res; } /// /// 货位绑定容器 /// /// /// /// public static bool BindingLoc(string loc, List cntrs, string desc = null) { var res = false; var db = new SqlHelper().GetInstance(); var location = db.Queryable().Where(a => a.S_LOC_CODE == loc).First(); if (string.IsNullOrEmpty(desc)) { desc = LocationHelper.GetList(x => x.S_CNTR_CODE == cntrs.FirstOrDefault()).FirstOrDefault()?.B_TYPE; if (string.IsNullOrEmpty(desc)) { desc = Settings.areaSuffixR(loc); } } try { var lcrList = db.Queryable().Where(a => a.S_LOC_CODE == loc).ToList(); LogHelper.Info("BindingLoc::B::" + lcrList.Count + "::" + JsonConvert.SerializeObject(location)); db.BeginTran(); int count = 0; cntrs.ForEach(a => { //if (lcrList.Count(b => b.S_CNTR_CODE.Trim() == a) == 0) { db.Insertable(new LocCntrRel { S_LOC_CODE = loc, S_CNTR_CODE = a, S_TYPE = desc }).ExecuteCommand(); count++; } }); location.N_CURRENT_NUM = lcrList.Count + count; //location.S_LOCK_STATE = "无"; if (location.N_CURRENT_NUM > 0) { location.T_FULL_TIME = DateTime.Now; location.T_EMPTY_TIME = null; } db.Updateable(location).UpdateColumns(it => new { it.N_CURRENT_NUM, it.T_FULL_TIME, it.T_EMPTY_TIME }).ExecuteCommand(); //db.Updateable(location).UpdateColumns(it => new { it.N_CURRENT_NUM, it.S_LOCK_STATE }).ExecuteCommand(); db.Ado.CommitTran(); LogHelper.Info("BindingLoc::A:[S_TYPE:" + desc + "]:" + JsonConvert.SerializeObject(location)); res = true; } catch (Exception ex) { db.Ado.RollbackTran(); } return res; } internal static bool DoAction(Func action) { var res = false; var db = new SqlHelper().GetInstance(); if (action != null) res = action(db); return res; } public static InworkRecord GetRecord(string FlinNoorIp) { return new SqlHelper().GetInstance().Queryable().Where(x => x.SQL_PLineNo == FlinNoorIp || x.S_IP_Address == FlinNoorIp).First(); } public static List GetRecord(Expression> expression) { return new SqlHelper().GetInstance().Queryable().Where(expression).ToList(); } public static bool AddRecord(InworkRecord FlinNo) { return new SqlHelper().GetInstance().Insertable(FlinNo).ExecuteCommand() > 0; } internal static List GetRowLock(string S_AREA_CODE) { //return new List(); var db = new SqlHelper().GetInstance(); return db.Queryable().Where(x => (string.IsNullOrEmpty(S_AREA_CODE) ? true : x.S_AREA_CODE == S_AREA_CODE)).ToList(); } internal static List GetRowLock(Expression> expression) { var db = new SqlHelper().GetInstance(); return db.Queryable().Where(expression).ToList(); } /// /// /// /// /// 1 写 0 删 /// internal static bool SetRowLock(RowLock r, int rr, SqlSugarClient db = null) { if (db == null) db = new SqlHelper().GetInstance(); var row = db.Queryable().Where(x => x.S_AREA_CODE == r.S_AREA_CODE && x.S_LOCK_SRC == r.S_LOCK_SRC && r.N_ROW == x.N_ROW).ToList(); if (rr == 0) { if (row.Count > 0) { return db.Deleteable(row).ExecuteCommand() > 0;//.Where(x => x.S_AREA_CODE == r.S_AREA_CODE && r.N_ROW == x.N_ROW).ExecuteCommand() > 0; } else return true; } else { if (row.Count == 0) return db.Insertable(r).ExecuteCommand() > 0; else return true; } //return db.Queryable().Where(x => string.IsNullOrEmpty(S_AREA_CODE) ? true : x.S_AREA_CODE == S_AREA_CODE).ToList(); } public static bool ExistRowLock(string area, int row) { var db = new SqlHelper().GetInstance(); return db.Queryable().Count(a => a.S_AREA_CODE == area.Trim() && a.N_ROW == row) > 0; } internal static List GetFuLeTrayCodeList(Expression> expression) { var db = new SqlHelper().GetInstance(); return db.Queryable().Where(expression).ToList(); } public static List GetList(Expression> expression = null) where T : new() { if (expression != null) { var list = new SqlHelper().GetInstance().Queryable().Where(expression).ToList(); return list; } else { var list = new SqlHelper().GetInstance().Queryable().ToList(); return list; } } public static IEnumerable getLastFull(List loclist) { foreach (var item in loclist.GroupBy(x => x.N_ROW).OrderBy(x => x.Key)) { var rs = item.ToList().FindAll(x => x.N_CURRENT_NUM > 0).OrderBy(x => x.N_COL).LastOrDefault(); if (rs.N_CURRENT_NUM == rs.N_CAPACITY) yield return rs; } } } }