feat: Improve path preview visualization in UnifiedAGVCanvas
Enhanced path drawing with better visibility: 1. Arrow improvements: - Changed from line-based arrows to filled triangle shapes - Increased arrow size by 1.5x for better visibility - Added polygon fill with outline for clearer identification 2. Path line improvements: - Added 50% transparency to purple path color (Alpha: 128) - Increased line thickness by 2x (from 4 to 8 pixels) - Improved visual contrast and clarity 3. Bidirectional path detection: - Detect routes that traverse the same segment multiple times - Display bidirectional paths with higher opacity (darker color, Alpha: 200) - Visual distinction helps identify round-trip routes Changes in UnifiedAGVCanvas.Events.cs: - Modified DrawDirectionArrow() to use FillPolygon instead of DrawLine - Enhanced DrawPath() with transparency, thickness, and bidirectional detection - Added System.Collections.Generic using statement Result: Much better visual identification of calculated paths in HMI 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -2,6 +2,7 @@ using AGVNavigationCore.Models;
|
||||
using AGVNavigationCore.PathFinding;
|
||||
using AGVNavigationCore.PathFinding.Core;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Drawing;
|
||||
using System.Drawing.Drawing2D;
|
||||
using System.Linq;
|
||||
@@ -153,28 +154,42 @@ namespace AGVNavigationCore.Controls
|
||||
|
||||
private void DrawDirectionArrow(Graphics g, Point point, double angle, AgvDirection direction)
|
||||
{
|
||||
var arrowSize = CONNECTION_ARROW_SIZE;
|
||||
var arrowSize = CONNECTION_ARROW_SIZE * 1.5; // 화살표 크기 증가
|
||||
var arrowAngle = Math.PI / 6; // 30도
|
||||
|
||||
var cos = Math.Cos(angle);
|
||||
var sin = Math.Sin(angle);
|
||||
|
||||
// 화살표 끝점 (방향)
|
||||
var arrowTipPoint = new Point(
|
||||
(int)(point.X + arrowSize * Math.Cos(angle)),
|
||||
(int)(point.Y + arrowSize * Math.Sin(angle))
|
||||
);
|
||||
|
||||
// 화살표 좌측 점
|
||||
var arrowPoint1 = new Point(
|
||||
(int)(point.X - arrowSize * Math.Cos(angle - arrowAngle)),
|
||||
(int)(point.Y - arrowSize * Math.Sin(angle - arrowAngle))
|
||||
);
|
||||
|
||||
// 화살표 우측 점
|
||||
var arrowPoint2 = new Point(
|
||||
(int)(point.X - arrowSize * Math.Cos(angle + arrowAngle)),
|
||||
(int)(point.Y - arrowSize * Math.Sin(angle + arrowAngle))
|
||||
);
|
||||
|
||||
var arrowColor = direction == AgvDirection.Forward ? Color.Blue : Color.Red;
|
||||
var arrowPen = new Pen(arrowColor, 2);
|
||||
var arrowBrush = new SolidBrush(arrowColor);
|
||||
|
||||
g.DrawLine(arrowPen, point, arrowPoint1);
|
||||
g.DrawLine(arrowPen, point, arrowPoint2);
|
||||
// 삼각형으로 화살표 그리기 (내부 채움)
|
||||
var trianglePoints = new Point[] { arrowTipPoint, arrowPoint1, arrowPoint2 };
|
||||
g.FillPolygon(arrowBrush, trianglePoints);
|
||||
|
||||
// 윤곽선 그리기
|
||||
var arrowPen = new Pen(arrowColor, 1.5f);
|
||||
g.DrawPolygon(arrowPen, trianglePoints);
|
||||
|
||||
arrowBrush.Dispose();
|
||||
arrowPen.Dispose();
|
||||
}
|
||||
|
||||
@@ -204,20 +219,55 @@ namespace AGVNavigationCore.Controls
|
||||
{
|
||||
if (path?.Path == null || path.Path.Count < 2) return;
|
||||
|
||||
var pathPen = new Pen(color, 4) { DashStyle = DashStyle.Dash };
|
||||
// 현재 선택된 경로인 경우 보라색 + 투명도 50% + 선 두께 2배
|
||||
Color lineColor = color;
|
||||
float lineThickness = 4;
|
||||
|
||||
if (color == Color.Purple)
|
||||
{
|
||||
// 투명도 50% (Alpha = 128 / 255)
|
||||
lineColor = Color.FromArgb(128, color.R, color.G, color.B);
|
||||
lineThickness = 8; // 2배 증가
|
||||
}
|
||||
|
||||
var pathPen = new Pen(lineColor, lineThickness) { DashStyle = DashStyle.Dash };
|
||||
|
||||
// 왕복 경로 감지: 방문한 노드 추적
|
||||
var visitedSegments = new Dictionary<string, int>();
|
||||
|
||||
for (int i = 0; i < path.Path.Count - 1; i++)
|
||||
{
|
||||
var currentNodeId = path.Path[i];
|
||||
var nextNodeId = path.Path[i + 1];
|
||||
|
||||
// 왕복 구간 키 생성 (양방향 모두 같은 키)
|
||||
var segmentKey = string.Compare(currentNodeId, nextNodeId) < 0
|
||||
? $"{currentNodeId}_{nextNodeId}"
|
||||
: $"{nextNodeId}_{currentNodeId}";
|
||||
|
||||
if (!visitedSegments.ContainsKey(segmentKey))
|
||||
visitedSegments[segmentKey] = 0;
|
||||
visitedSegments[segmentKey]++;
|
||||
|
||||
var currentNode = _nodes?.FirstOrDefault(n => n.NodeId == currentNodeId);
|
||||
var nextNode = _nodes?.FirstOrDefault(n => n.NodeId == nextNodeId);
|
||||
|
||||
if (currentNode != null && nextNode != null)
|
||||
{
|
||||
// 경로 선 그리기
|
||||
g.DrawLine(pathPen, currentNode.Position, nextNode.Position);
|
||||
// 왕복 경로면 더 진한 색상으로 표시
|
||||
if (visitedSegments[segmentKey] > 1 && color == Color.Purple)
|
||||
{
|
||||
// 왕복 경로는 투명도를 낮춤 (더 진하게)
|
||||
var darkPathColor = Color.FromArgb(200, color.R, color.G, color.B);
|
||||
var darkPathPen = new Pen(darkPathColor, lineThickness) { DashStyle = DashStyle.Dash };
|
||||
g.DrawLine(darkPathPen, currentNode.Position, nextNode.Position);
|
||||
darkPathPen.Dispose();
|
||||
}
|
||||
else
|
||||
{
|
||||
// 일반 경로 선 그리기
|
||||
g.DrawLine(pathPen, currentNode.Position, nextNode.Position);
|
||||
}
|
||||
|
||||
// 경로 방향 표시 (계산된 경로의 경우에만 방향 화살표 표시)
|
||||
var midPoint = new Point(
|
||||
|
||||
Reference in New Issue
Block a user