Commit 45597119 刘韬

AGV对接调通, AGV需求与MES未通

1 个父辈 119302e9
......@@ -258,4 +258,8 @@ paket-files/
# Python Tools for Visual Studio (PTVS)
__pycache__/
*.pyc
\ No newline at end of file
*.pyc
/SO1057项目3D模型/盘料仓行走机构-3D.PDF
/SO1057项目3D模型/滚筒线3D.PDF
/SO1057项目3D模型/散料仓行走机构-3D.PDF
/SO1057项目3D模型/上料模型总装配-3D.PDF
......@@ -210,6 +210,7 @@ namespace OnlineStore.Common
/// 库位 ID
/// </summary>
public static string posId = "posId";
public static string hSerial = "hSerial";
/// <summary>
/// 料盘宽
/// </summary>
......
using log4net;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Collections.Specialized;
......@@ -154,7 +155,31 @@ namespace OnlineStore.Common
bool IsTimeOut = false;
return Post(url, paramData, Encoding.UTF8, timeOut,out IsTimeOut);
}
public static T Post<T>(string url, T operation, bool printlog = false)
{
try
{
//lock (lockpost)
{
string json = JsonConvert.SerializeObject(operation);
string result = Post(url, json, 2000);
T op = JsonConvert.DeserializeObject<T>(result);
if (printlog)
{
LogUtil.info("Send [" + json + "] Revice [" + result + "]");
}
return op;
}
}
catch (Exception ex)
{
LogUtil.error("Post 出错:" + ex);
}
return default;
}
private static int isLog = ConfigAppSettings.GetIntValue(Setting_Init.Server_Log_Open);
public static string Post(string url, string paramData, Encoding encoding, int timeOut, out bool IsTimeOut)
{
......@@ -240,5 +265,22 @@ namespace OnlineStore.Common
}
return "";
}
public static string GetPostApi(string api)
{
var host = ConfigAppSettings.GetValue(Setting_Init.http_server);
if (!host.StartsWith("http://"))
{
host = "http://" + host;
}
if (!host.EndsWith("/"))
{
host = host + "/";
}
if (api.StartsWith("/"))
{
api = api.Substring(1);
}
return host + api;
}
}
}
......@@ -77,6 +77,7 @@
</ItemGroup>
<ItemGroup>
<Compile Include="manager\agvClient\AgvClient.cs" />
<Compile Include="manager\agvClient\DoorInfo.cs" />
<Compile Include="manager\BufferDataManager.cs" />
<Compile Include="manager\StoreManager.cs" />
<Compile Include="deviceLibrary\RFID\RFIDManagercs.cs" />
......

public class DoorInfo
{
public DoorInfo()
{
doorIndex = doorIndexE.LeftIn;
status = doorStatusE.free;
hasContainer = false;
hSerial = "";
}
public doorIndexE doorIndex;
public doorStatusE status;
public bool hasContainer;
public string hSerial;
}
public enum doorIndexE
{
LeftIn = 2,
LeftOut = 1,
RightIn = 4,
RightOut = 3,
}
public enum doorStatusE
{
/// <summary>
/// 空闲
/// </summary>
free = 1,
/// <summary>
/// 入库中
/// </summary>
inStore = 2,
/// <summary>
/// 出库中
/// </summary>
outStore = 3,
/// <summary>
/// 需要空料串出库
/// </summary>
needBox = 4,
/// <summary>
/// 满料串需要取走
/// </summary>
fullBoxNeedLeave = 5
}
\ No newline at end of file
......@@ -1240,10 +1240,11 @@ namespace OnlineStore.DeviceLibrary
/// 料串出库:阻挡气缸下降
/// </summary>
IS22_StopDown,
IS23_WaitAgv,
/// <summary>
/// 料串出库:通知agv来拉料串
/// </summary>
IS23_ShelfOut,
IS24_ShelfOut,
#endregion
}
......
......@@ -92,6 +92,10 @@ namespace OnlineStore.DeviceLibrary
/// </summary>
public string barcode { get; set; }
/// <summary>
/// 需求单号
/// </summary>
public string hSerial { get; set; }
/// <summary>
/// 库位号编码
/// </summary>
public string PosId { get; set; }
......
......@@ -57,6 +57,9 @@ namespace OnlineStore.DeviceLibrary
if (StoreManager.IsConnectServer)
{
SendLineStatus();
HttpHelper.Post<DoorInfo>(HttpHelper.GetPostApi("/api/xlc/updateDoorInfo"), StoreManager.XLRStore.inputEquip.BatchMove_A.doorInfo);
HttpHelper.Post<DoorInfo>(HttpHelper.GetPostApi("/api/xlc/updateDoorInfo"), StoreManager.XLRStore.inputEquip.BatchMove_B.doorInfo);
}
}
}
......@@ -284,6 +287,10 @@ namespace OnlineStore.DeviceLibrary
//string realRfid = data.ContainsKey(ParamDefine.realRfid) ? data[ParamDefine.realRfid] : "";
//int taskCount = FormUtil.GetIntData(data, ParamDefine.taskCount, 0);
string hSerials = "";
if (data.ContainsKey(ParamDefine.hSerial))
hSerials = data[ParamDefine.hSerial];
//urgentReel: true 表示紧急料,需要出到料串上
//cutReel: true 表示分盘料,需要出到料串上
//smallReel: true 小料(7x8),放置到小料架上
......@@ -301,6 +308,7 @@ namespace OnlineStore.DeviceLibrary
int plateH = Convert.ToInt32(plateHArray[index]);
InOutParam inoutParam = new InOutParam(new InOutPosInfo(barcode, posId, plateW, plateH, urgentReel));
inoutParam.PosInfo.hSerial = hSerials;
//根据发送的posId获取位置列表
BoxPosition position = CSVPositionReader<BoxPosition>.GetPositon(posId);
if (position == null)
......
......@@ -21,7 +21,7 @@ namespace OnlineStore.DeviceLibrary
public DeviceMoveInfo MoveInfo;
public string WarnMsg = "";
public BatchMoveConfig Config = null;
public DoorInfo doorInfo = new DoorInfo();
private InputEquip Robot
{
get { return StoreManager.XLRStore.inputEquip; }
......@@ -78,7 +78,10 @@ namespace OnlineStore.DeviceLibrary
}
else
{
if (Robot.AutoInput && Robot.IOValue(Config.IO_LineIn_Check).Equals(IO_VALUE.HIGH))
if (Robot.IOValue(Config.IO_AGV_RequestIn).Equals(IO_VALUE.HIGH))
{
ShelfEnterProcess("", "");
}else if (Robot.AutoInput && Robot.IOValue(Config.IO_LineIn_Check).Equals(IO_VALUE.HIGH))
{
StartInstore(new InOutParam());
}
......@@ -108,21 +111,33 @@ namespace OnlineStore.DeviceLibrary
&& Robot.IOValue(Config.IO_LineEnd_Check).Equals(IO_VALUE.LOW)
&& Robot.CylinderIsOk(Config.IO_Shelf_StopUp, Config.IO_Shelf_StopDown))
{
if (StoreManager.checkWatch(shelfWatch, 10000, true))
{
Asa.ClientAction action= AgvClient.GetAction(Config.AgvName);
var agvcallresult = AgvClient.NeedEnter(Config.AgvName, "", Asa.ClientLevel.High);
if (!action.Equals(Asa.ClientAction.NeedEnter))
{
WorkLog("无料串,:通知agv来送料串AgvName:" + Config.AgvName + ",send NeedEnter=:" + agvcallresult.ToString());
}
doorInfo.doorIndex = ShelfType == 1 ? doorIndexE.LeftIn : doorIndexE.RightIn;
//doorInfo.hSerial = MoveInfo.MoveParam.hSerial;
doorInfo.status = doorStatusE.needBox;
doorInfo.hasContainer = false;
WorkLog($"无料串,:通知agv来送料串 ShelfType:{ShelfType},{doorInfo.doorIndex},hasContainer:{doorInfo.hasContainer}");
//Asa.ClientAction action= AgvClient.GetAction(Config.AgvName);
//var agvcallresult = AgvClient.NeedEnter(Config.AgvName, "", Asa.ClientLevel.High);
//if (!action.Equals(Asa.ClientAction.NeedEnter))
//{
// WorkLog("无料串,:通知agv来送料串AgvName:" + Config.AgvName + ",send NeedEnter=:" + agvcallresult.ToString());
//}
}
}
else if (Robot.IOValue(Config.IO_LineIn_Check).Equals(IO_VALUE.HIGH) && Robot.IOValue(Config.IO_LineEnd_Check).Equals(IO_VALUE.HIGH)
&& AgvClient.GetAction(Config.AgvName) != Asa.ClientAction.NeedLeave && AgvClient.GetAction(Config.AgvName) != Asa.ClientAction.MayLeave && AgvClient.GetAction(Config.AgvName) != Asa.ClientAction.FinishLeave)
{
shelfWatch.Stop();
AgvClient.SetToNone(Config.AgvName);
doorInfo.doorIndex = ShelfType == 1 ? doorIndexE.LeftIn : doorIndexE.RightIn;
doorInfo.status = doorStatusE.free;
doorInfo.hasContainer = false;
//AgvClient.SetToNone(Config.AgvName);
}
}
private Stopwatch shelfWatch = new Stopwatch();
......
......@@ -37,6 +37,10 @@ namespace OnlineStore.DeviceLibrary
//{
// return false;
//}
if (doorInfo.status == doorStatusE.fullBoxNeedLeave)
{
return false;
}
if (AgvClient.GetAction(Config.AgvName) == ClientAction.NeedLeave || AgvClient.GetAction(Config.AgvName) == ClientAction.MayLeave)
{
//WorkLog("料串入料 :等待AGV来取空料串1");
......@@ -45,8 +49,15 @@ namespace OnlineStore.DeviceLibrary
UpdateShelf(1);
if (CurrShelf.ShelfState.Equals(3))
{
bool agvcallresult = AgvClient.NeedLeave(Config.AgvName, CurrShelf.ShelfRfid, ClientLevel.High);
LogUtil.info(Name + "StartInstore 失败,料串" + CurrShelf.ToStr() + "需要离开,NeedLeave:" + Config.AgvName + "," + CurrShelf.ShelfRfid + ",agvcallresult:" + agvcallresult.ToString());
//bool agvcallresult = AgvClient.NeedLeave(Config.AgvName, CurrShelf.ShelfRfid, ClientLevel.High);
//LogUtil.info(Name + "StartInstore 失败,料串" + CurrShelf.ToStr() + "需要离开,NeedLeave:" + Config.AgvName + "," + CurrShelf.ShelfRfid + ",agvcallresult:" + agvcallresult.ToString());
doorInfo.doorIndex = ShelfType == 1 ? doorIndexE.LeftOut : doorIndexE.RightOut;
//doorInfo.hSerial = MoveInfo.MoveParam.hSerial;
doorInfo.status = doorStatusE.fullBoxNeedLeave;
doorInfo.hasContainer = false;
WorkLog($"有料串,:通知agv来取料串 ShelfType:{ShelfType},{doorInfo.doorIndex},hasContainer:{doorInfo.hasContainer}");
return false;
}
else if (Robot.IOValue(Config.IO_LineIn_Check).Equals(IO_VALUE.HIGH) )
......@@ -304,16 +315,37 @@ namespace OnlineStore.DeviceLibrary
}
else if (MoveInfo.IsStep(StepEnum.IB22_StopDown))
{
MoveInfo.NextMoveStep(StepEnum.IB23_ShelfOut);
MoveInfo.TimeOutSeconds = 40;
MoveInfo.OneWaitCanEndStep = true;
MoveInfo.NextMoveStep(StepEnum.IS23_WaitAgv);
//MoveInfo.TimeOutSeconds = 40;
//MoveInfo.OneWaitCanEndStep = true;
//bool agvcallresult = AgvClient.NeedLeave(Config.AgvName, CurrShelf.ShelfRfid, ClientLevel.High);
//WorkLog("送出出库料串 :通知agv来取料串,等待料串离开Config.AgvName:" + Config.AgvName + ",CurrShelfId:" + CurrShelf.ShelfRfid + ",agvcallresult:" + agvcallresult.ToString());
bool agvcallresult = AgvClient.NeedLeave(Config.AgvName, CurrShelf.ShelfRfid, ClientLevel.High);
WorkLog("上料完成 :通知agv来取料串,等待料串离开Config.AgvName:" + Config.AgvName + ",CurrShelfId:" + CurrShelf.ShelfRfid + ",agvcallresult:" + agvcallresult.ToString());
MoveInfo.WaitList.Add(WaitResultInfo.WaitTime(60000));
MoveInfo.WaitList.Add(WaitResultInfo.WaitIO(Config.IO_LineIn_Check, IO_VALUE.LOW));
doorInfo.doorIndex = ShelfType == 1 ? doorIndexE.LeftOut : doorIndexE.RightOut;
//doorInfo.hSerial = MoveInfo.MoveParam.hSerial;
doorInfo.status = doorStatusE.fullBoxNeedLeave;
doorInfo.hasContainer = false;
WorkLog($"有料串,:通知agv来取料串 ShelfType:{ShelfType},{doorInfo.doorIndex},hasContainer:{doorInfo.hasContainer}");
//MoveInfo.WaitList.Add(WaitResultInfo.WaitTime(60000));
//MoveInfo.WaitList.Add(WaitResultInfo.WaitIO(Config.IO_LineIn_Check, IO_VALUE.LOW));
}
else if (MoveInfo.IsStep(StepEnum.IS23_WaitAgv))
{
if (Robot.IOValue(Config.IO_AGV_RequestOut).Equals(IO_VALUE.HIGH))
{
MoveInfo.NextMoveStep(StepEnum.IS24_ShelfOut);
WorkLog("收到AGV抵达信号");
ShelfOutProcess("", CurrShelf.ShelfRfid);
}
else if (Robot.IOValue(Config.IO_LineEnd_Check).Equals(IO_VALUE.LOW))
{
MoveInfo.NextMoveStep(StepEnum.IS24_ShelfOut);
WorkLog("料串已离开");
}
}
else if (MoveInfo.IsStep(StepEnum.IB23_ShelfOut))
else if (MoveInfo.IsStep(StepEnum.IS24_ShelfOut))
{
WarnMsg = "";
alarmType = AlarmType.None;
......@@ -636,16 +668,33 @@ namespace OnlineStore.DeviceLibrary
}
else if (MoveInfo.IsStep(StepEnum.IB22_StopDown))
{
MoveInfo.NextMoveStep(StepEnum.IS23_ShelfOut);
MoveInfo.TimeOutSeconds = 40;
MoveInfo.OneWaitCanEndStep = true;
bool agvcallresult = AgvClient.NeedLeave(Config.AgvName, CurrShelf.ShelfRfid, ClientLevel.High);
WorkLog("送出出库料串 :通知agv来取料串,等待料串离开Config.AgvName:" + Config.AgvName + ",CurrShelfId:" + CurrShelf.ShelfRfid + ",agvcallresult:" + agvcallresult.ToString());
MoveInfo.WaitList.Add(WaitResultInfo.WaitTime(60000));
MoveInfo.WaitList.Add(WaitResultInfo.WaitIO(Config.IO_LineIn_Check, IO_VALUE.LOW));
MoveInfo.NextMoveStep(StepEnum.IS23_WaitAgv);
//MoveInfo.TimeOutSeconds = 40;
//MoveInfo.OneWaitCanEndStep = true;
//bool agvcallresult = AgvClient.NeedLeave(Config.AgvName, CurrShelf.ShelfRfid, ClientLevel.High);
//WorkLog("送出出库料串 :通知agv来取料串,等待料串离开Config.AgvName:" + Config.AgvName + ",CurrShelfId:" + CurrShelf.ShelfRfid + ",agvcallresult:" + agvcallresult.ToString());
doorInfo.doorIndex = ShelfType == 1 ? doorIndexE.LeftOut : doorIndexE.RightOut;
doorInfo.hSerial = MoveInfo.MoveParam.PosInfo.hSerial;
doorInfo.status = doorStatusE.fullBoxNeedLeave;
doorInfo.hasContainer = true;
WorkLog($"有料串,:通知agv来取料串 ShelfType:{ShelfType},{doorInfo.doorIndex},hasContainer:{doorInfo.hasContainer}");
//MoveInfo.WaitList.Add(WaitResultInfo.WaitTime(60000));
//MoveInfo.WaitList.Add(WaitResultInfo.WaitIO(Config.IO_LineIn_Check, IO_VALUE.LOW));
}
else if (MoveInfo.IsStep(StepEnum.IS23_WaitAgv)) {
if (Robot.IOValue(Config.IO_AGV_RequestOut).Equals(IO_VALUE.HIGH)) {
MoveInfo.NextMoveStep(StepEnum.IS24_ShelfOut);
WorkLog("收到AGV抵达信号");
ShelfOutProcess("", CurrShelf.ShelfRfid);
}else if (Robot.IOValue(Config.IO_LineEnd_Check).Equals(IO_VALUE.LOW)) {
MoveInfo.NextMoveStep(StepEnum.IS24_ShelfOut);
WorkLog("料串已离开");
}
}
else if (MoveInfo.IsStep(StepEnum.IS23_ShelfOut))
else if (MoveInfo.IsStep(StepEnum.IS24_ShelfOut))
{
WarnMsg = "";
alarmType = AlarmType.None;
......@@ -786,6 +835,7 @@ namespace OnlineStore.DeviceLibrary
{
LogUtil.info(logName + " 开始转动线体");
ProcessShelfEnter = true;
Robot.IOMove(Config.IO_AGV_Response, IO_VALUE.HIGH);
LineRun();
//等待进料检测信号
......@@ -814,7 +864,7 @@ namespace OnlineStore.DeviceLibrary
LogUtil.info(logName + "等待3000后,停止链条转动");
LineStop();
Robot.IOMove(Config.IO_AGV_Response, IO_VALUE.LOW);
//料串可离开
AgvClient.SetStatus(Config.AgvName, "", ClientAction.FinishEnter, ClientLevel.High, true);
Task.Factory.StartNew(delegate
......@@ -864,6 +914,7 @@ namespace OnlineStore.DeviceLibrary
{
ProcessShelfOut = true;
LineBack();
Robot.IOMove(Config.IO_AGV_Response, IO_VALUE.HIGH);
bool result = Robot.WaitIo(Config.IO_LineIn_Check, IO_VALUE.LOW, 60000);
if (!result)
{
......@@ -876,6 +927,7 @@ namespace OnlineStore.DeviceLibrary
//再转动2000
Thread.Sleep(8000);
LineStop();
Robot.IOMove(Config.IO_AGV_Response, IO_VALUE.LOW);
AgvClient.SetStatus(Config.AgvName, CurrShelf.ShelfRfid, ClientAction.FinishLeave, ClientLevel.High, true);
Task.Factory.StartNew(delegate
{
......
......@@ -517,6 +517,13 @@ namespace OnlineStore.DeviceLibrary
{
foreach (BatchMoveBean moveBean in BatchMoveList)
{
var curhSerial = moveBean.MoveInfo.MoveParam.PosInfo.hSerial;
if (!string.IsNullOrEmpty(curhSerial) && curhSerial != posInfo.hSerial) {
LogInfo($"{posType}当前料串的 hSerial:{curhSerial},与准备出库到料串 hSerial:{posInfo.hSerial} 不符");
moveBean.ShelfNeedLeave = true;
return false;
}
else
if (moveBean.ShelfReadyOut(posInfo, shelfAutoLeave))
{
InOutParam param = new InOutParam(posInfo.ToCopy());
......
......@@ -56,6 +56,9 @@
<ApplicationIcon>DfIcon.ico</ApplicationIcon>
</PropertyGroup>
<PropertyGroup />
<PropertyGroup>
<ApplicationManifest>app.manifest</ApplicationManifest>
</PropertyGroup>
<ItemGroup>
<Reference Include="Client">
<HintPath>..\..\dll\Client.dll</HintPath>
......@@ -283,6 +286,7 @@
<Content Include="model\sr.prototxt">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<None Include="app.manifest" />
<None Include="packages.config" />
<None Include="Properties\Settings.settings">
<Generator>SettingsSingleFileGenerator</Generator>
......
<?xml version="1.0" encoding="utf-8"?>
<assembly manifestVersion="1.0" xmlns="urn:schemas-microsoft-com:asm.v1">
<assemblyIdentity version="1.0.0.0" name="MyApplication.app"/>
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v2">
<security>
<requestedPrivileges xmlns="urn:schemas-microsoft-com:asm.v3">
<!-- UAC 清单选项
如果想要更改 Windows 用户帐户控制级别,请使用
以下节点之一替换 requestedExecutionLevel 节点。n
<requestedExecutionLevel level="asInvoker" uiAccess="false" />
<requestedExecutionLevel level="requireAdministrator" uiAccess="false" />
<requestedExecutionLevel level="highestAvailable" uiAccess="false" />
指定 requestedExecutionLevel 元素将禁用文件和注册表虚拟化。
如果你的应用程序需要此虚拟化来实现向后兼容性,则删除此
元素。
-->
<requestedExecutionLevel level="requireAdministrator" uiAccess="false" />
</requestedPrivileges>
</security>
</trustInfo>
<compatibility xmlns="urn:schemas-microsoft-com:compatibility.v1">
<application>
<!-- 设计此应用程序与其一起工作且已针对此应用程序进行测试的
Windows 版本的列表。取消评论适当的元素,
Windows 将自动选择最兼容的环境。 -->
<!-- Windows Vista -->
<!--<supportedOS Id="{e2011457-1546-43c5-a5fe-008deee3d3f0}" />-->
<!-- Windows 7 -->
<!--<supportedOS Id="{35138b9a-5d96-4fbd-8e2d-a2440225f93a}" />-->
<!-- Windows 8 -->
<!--<supportedOS Id="{4a2f28e3-53b9-4441-ba9c-d69d4a4a6e38}" />-->
<!-- Windows 8.1 -->
<!--<supportedOS Id="{1f676c76-80e1-4239-95bb-83d0f6d0da78}" />-->
<!-- Windows 10 -->
<!--<supportedOS Id="{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}" />-->
</application>
</compatibility>
<!-- 指示该应用程序可感知 DPI 且 Windows 在 DPI 较高时将不会对其进行
自动缩放。Windows Presentation Foundation (WPF)应用程序自动感知 DPI,无需
选择加入。选择加入此设置的 Windows 窗体应用程序(面向 .NET Framework 4.6)还应
在其 app.config 中将 "EnableWindowsFormsHighDpiAutoResizing" 设置设置为 "true"。
将应用程序设为感知长路径。请参阅 https://docs.microsoft.com/windows/win32/fileio/maximum-file-path-limitation -->
<!--
<application xmlns="urn:schemas-microsoft-com:asm.v3">
<windowsSettings>
<dpiAware xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">true</dpiAware>
<longPathAware xmlns="http://schemas.microsoft.com/SMI/2016/WindowsSettings">true</longPathAware>
</windowsSettings>
</application>
-->
<!-- 启用 Windows 公共控件和对话框的主题(Windows XP 和更高版本) -->
<!--
<dependency>
<dependentAssembly>
<assemblyIdentity
type="win32"
name="Microsoft.Windows.Common-Controls"
version="6.0.0.0"
processorArchitecture="*"
publicKeyToken="6595b64144ccf1df"
language="*"
/>
</dependentAssembly>
</dependency>
-->
</assembly>
支持 Markdown 格式
你添加了 0 到此讨论。请谨慎行事。
Finish editing this message first!