diff --git a/OpenNest/Controls/EntityView.cs b/OpenNest/Controls/EntityView.cs index 96b8f1b..2adf2a1 100644 --- a/OpenNest/Controls/EntityView.cs +++ b/OpenNest/Controls/EntityView.cs @@ -1,6 +1,7 @@ using OpenNest.Bending; using OpenNest.Geometry; using OpenNest.Math; +using System; using System.Collections.Generic; using System.Drawing; using System.Drawing.Drawing2D; @@ -17,6 +18,20 @@ namespace OpenNest.Controls private readonly Pen gridPen = new Pen(Color.FromArgb(70, 70, 70)); private readonly Dictionary penCache = new Dictionary(); + public event EventHandler LinePicked; + public event EventHandler PickCancelled; + + private bool isPickingBendLine; + public bool IsPickingBendLine + { + get => isPickingBendLine; + set + { + isPickingBendLine = value; + Cursor = value ? Cursors.Hand : Cursors.Cross; + } + } + public EntityView() { Entities = new List(); @@ -34,6 +49,13 @@ namespace OpenNest.Controls { base.OnMouseClick(e); if (!Focused) Focus(); + + if (IsPickingBendLine && e.Button == MouseButtons.Left) + { + var line = HitTestLine(e.Location); + if (line != null) + LinePicked?.Invoke(this, line); + } } protected override void OnPaint(PaintEventArgs e) @@ -123,6 +145,12 @@ namespace OpenNest.Controls if (e.KeyCode == Keys.F) ZoomToFit(); + + if (IsPickingBendLine && e.KeyCode == Keys.Escape) + { + IsPickingBendLine = false; + PickCancelled?.Invoke(this, EventArgs.Empty); + } } private Pen GetEntityPen(Color color) @@ -180,6 +208,32 @@ namespace OpenNest.Controls } } + private Line HitTestLine(Point controlPoint) + { + var worldPoint = PointControlToWorld(controlPoint); + var tolerance = LengthGuiToWorld(6); + Line bestLine = null; + var bestDistance = double.MaxValue; + + foreach (var entity in Entities) + { + if (entity.Type != EntityType.Line || !entity.IsVisible) + continue; + + var line = (Line)entity; + var closest = line.ClosestPointTo(worldPoint); + var distance = worldPoint.DistanceTo(closest); + + if (distance < tolerance && distance < bestDistance) + { + bestLine = line; + bestDistance = distance; + } + } + + return bestLine; + } + protected override void Dispose(bool disposing) { if (disposing)