feat: Implement AGV command prediction system for real-time control
- Add motor/magnet/speed enums and AGVCommand class for AGV control - Implement Predict() method for next action prediction based on path and state - Add RFID position tracking (requires 2 RFIDs for position confirmation) - Add SetPath() method to VirtualAGV for path management - Implement GetCommandFromPath() to extract motor/magnet/speed from DetailedPath - Add real-time prediction display in SimulatorForm (timer1_Tick) - Support automatic forward movement at low speed when position unconfirmed - Support stop command when destination reached or no destination set Key Features: - Position unconfirmed (RFID < 2): Forward + Straight + Low speed - Position confirmed + no destination: Stop (position found) - Position confirmed + destination reached: Stop (arrived) - Path execution: Motor/Magnet/Speed from DetailedPath NodeMotorInfo - Rotation nodes: Automatic low speed - Junction handling: Magnet direction (Left/Right/Straight) 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -111,7 +111,7 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
return null;
|
||||
}
|
||||
|
||||
public AGVPathResult FindPath_test(MapNode startNode, MapNode targetNode,
|
||||
public AGVPathResult FindPath(MapNode startNode, MapNode targetNode,
|
||||
MapNode prevNode, AgvDirection prevDirection, AgvDirection currentDirection, bool crossignore = false)
|
||||
{
|
||||
// 입력 검증
|
||||
@@ -154,6 +154,8 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
{
|
||||
MakeDetailData(pathResult, currentDirection);
|
||||
MakeMagnetDirection(pathResult);
|
||||
for (int i = 0; i < pathResult.DetailedPath.Count; i++)
|
||||
pathResult.DetailedPath[i].seq = i + 1;
|
||||
return pathResult;
|
||||
}
|
||||
}
|
||||
@@ -182,6 +184,8 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
{
|
||||
MakeDetailData(pathResult, ReverseDirection);
|
||||
MakeMagnetDirection(pathResult);
|
||||
for (int i = 0; i < pathResult.DetailedPath.Count; i++)
|
||||
pathResult.DetailedPath[i].seq = i + 1;
|
||||
return pathResult;
|
||||
}
|
||||
}
|
||||
@@ -196,6 +200,8 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
{
|
||||
MakeDetailData(pathResult, currentDirection);
|
||||
MakeMagnetDirection(pathResult);
|
||||
for (int i = 0; i < pathResult.DetailedPath.Count; i++)
|
||||
pathResult.DetailedPath[i].seq = i + 1;
|
||||
return pathResult;
|
||||
}
|
||||
|
||||
@@ -220,7 +226,7 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
Path0.PrevDirection = prevDirection;
|
||||
MakeDetailData(Path0, prevDirection);
|
||||
|
||||
var Path1 = FindPath_test(nextNodeForward, targetNode, startNode, prevDirection, currentDirection, true);
|
||||
var Path1 = FindPath(nextNodeForward, targetNode, startNode, prevDirection, currentDirection, true);
|
||||
Path1.PrevNode = startNode;
|
||||
Path1.PrevDirection = prevDirection;
|
||||
//MakeDetailData(Path1, ReverseDirection);
|
||||
@@ -228,6 +234,9 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
var combinedResult0 = Path0;
|
||||
combinedResult0 = _basicPathfinder.CombineResults(combinedResult0, Path1);
|
||||
MakeMagnetDirection(combinedResult0);
|
||||
|
||||
for (int i = 0; i < combinedResult0.DetailedPath.Count; i++)
|
||||
combinedResult0.DetailedPath[i].seq = i + 1;
|
||||
return combinedResult0;
|
||||
}
|
||||
else if (nextNodeBackward != null)
|
||||
@@ -404,6 +413,8 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
|
||||
MakeMagnetDirection(combinedResult);
|
||||
|
||||
for (int i = 0; i < combinedResult.DetailedPath.Count; i++)
|
||||
combinedResult.DetailedPath[i].seq = i + 1;
|
||||
return combinedResult;
|
||||
|
||||
|
||||
@@ -427,7 +438,7 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
string nextNodeId = (i + 1 < path1.Path.Count) ? path1.Path[i + 1].NodeId : null;
|
||||
|
||||
// 노드 정보 생성 (현재 방향 유지)
|
||||
var nodeInfo = new NodeMotorInfo(
|
||||
var nodeInfo = new NodeMotorInfo(i+1,
|
||||
nodeId, RfidId,
|
||||
currentDirection,
|
||||
nextNodeId,
|
||||
|
||||
@@ -28,6 +28,10 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
/// </summary>
|
||||
public class NodeMotorInfo
|
||||
{
|
||||
/// <summary>
|
||||
/// 일련번호
|
||||
/// </summary>
|
||||
public int seq { get; set; }
|
||||
/// <summary>
|
||||
/// 노드 ID
|
||||
/// </summary>
|
||||
@@ -68,13 +72,19 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
/// </summary>
|
||||
public bool RequiresSpecialAction { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 해당노드가 인식되면 이 값이 셋팅됩니다.
|
||||
/// </summary>
|
||||
public bool IsPass { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 특수 동작 설명
|
||||
/// </summary>
|
||||
public string SpecialActionDescription { get; set; }
|
||||
|
||||
public NodeMotorInfo(string nodeId,string rfid, AgvDirection motorDirection, string nextNodeId = null, MagnetDirection magnetDirection = MagnetDirection.Straight)
|
||||
public NodeMotorInfo(int seqno,string nodeId,string rfid, AgvDirection motorDirection, string nextNodeId = null, MagnetDirection magnetDirection = MagnetDirection.Straight)
|
||||
{
|
||||
seq = seqno;
|
||||
NodeId = nodeId;
|
||||
RfidId = rfid;
|
||||
MotorDirection = motorDirection;
|
||||
@@ -84,6 +94,7 @@ namespace AGVNavigationCore.PathFinding.Planning
|
||||
IsDirectionChangePoint = false;
|
||||
RequiresSpecialAction = false;
|
||||
SpecialActionDescription = string.Empty;
|
||||
IsPass = false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user