fix: allow line-on-line contact and remove extra spacing gap
- Part.Intersects: filter intersection points at a vertex of either shape (was both), so edge-touching parts are not flagged as overlapping - NestEngineBase.HasOverlaps: use epsilon-based bounding box pre-filter consistent with FillExtents and Plate.HasOverlappingParts - PartGeometry.GetOffsetPartLines: remove extra chordTolerance added to spacing offset — was causing 0.002" gap beyond the intended part spacing Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -177,15 +177,16 @@ namespace OpenNest
|
|||||||
if (!perimeter1.Intersects(perimeter2, out var rawPts))
|
if (!perimeter1.Intersects(perimeter2, out var rawPts))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// Exclude intersection points that coincide with vertices of BOTH
|
// Exclude intersection points that coincide with a vertex of either
|
||||||
// perimeters — these are touch points (shared corners/endpoints),
|
// perimeter — these are boundary contact points (shared corners,
|
||||||
|
// endpoints, or a corner touching an edge) with zero area overlap,
|
||||||
// not actual crossings where one shape enters the other's interior.
|
// not actual crossings where one shape enters the other's interior.
|
||||||
var verts1 = CollectVertices(perimeter1);
|
var verts1 = CollectVertices(perimeter1);
|
||||||
var verts2 = CollectVertices(perimeter2);
|
var verts2 = CollectVertices(perimeter2);
|
||||||
|
|
||||||
foreach (var pt in rawPts)
|
foreach (var pt in rawPts)
|
||||||
{
|
{
|
||||||
if (IsNearAnyVertex(pt, verts1) && IsNearAnyVertex(pt, verts2))
|
if (IsNearAnyVertex(pt, verts1) || IsNearAnyVertex(pt, verts2))
|
||||||
continue;
|
continue;
|
||||||
pts.Add(pt);
|
pts.Add(pt);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -45,7 +45,7 @@ namespace OpenNest
|
|||||||
var profile = new ShapeProfile(
|
var profile = new ShapeProfile(
|
||||||
entities.Where(e => e.Layer != SpecialLayers.Rapid).ToList());
|
entities.Where(e => e.Layer != SpecialLayers.Rapid).ToList());
|
||||||
var lines = new List<Line>();
|
var lines = new List<Line>();
|
||||||
var totalSpacing = spacing + chordTolerance;
|
var totalSpacing = spacing;
|
||||||
|
|
||||||
AddOffsetLines(lines, profile.Perimeter.OffsetOutward(totalSpacing),
|
AddOffsetLines(lines, profile.Perimeter.OffsetOutward(totalSpacing),
|
||||||
chordTolerance, part.Location);
|
chordTolerance, part.Location);
|
||||||
@@ -63,7 +63,7 @@ namespace OpenNest
|
|||||||
var profile = new ShapeProfile(
|
var profile = new ShapeProfile(
|
||||||
entities.Where(e => e.Layer != SpecialLayers.Rapid).ToList());
|
entities.Where(e => e.Layer != SpecialLayers.Rapid).ToList());
|
||||||
var lines = new List<Line>();
|
var lines = new List<Line>();
|
||||||
var totalSpacing = spacing + chordTolerance;
|
var totalSpacing = spacing;
|
||||||
|
|
||||||
AddOffsetDirectionalLines(lines, profile.Perimeter.OffsetOutward(totalSpacing),
|
AddOffsetDirectionalLines(lines, profile.Perimeter.OffsetOutward(totalSpacing),
|
||||||
chordTolerance, part.Location, facingDirection);
|
chordTolerance, part.Location, facingDirection);
|
||||||
@@ -97,7 +97,7 @@ namespace OpenNest
|
|||||||
var profile = new ShapeProfile(
|
var profile = new ShapeProfile(
|
||||||
entities.Where(e => e.Layer != SpecialLayers.Rapid).ToList());
|
entities.Where(e => e.Layer != SpecialLayers.Rapid).ToList());
|
||||||
var lines = new List<Line>();
|
var lines = new List<Line>();
|
||||||
var totalSpacing = spacing + chordTolerance;
|
var totalSpacing = spacing;
|
||||||
|
|
||||||
AddOffsetDirectionalLines(lines, profile.Perimeter.OffsetOutward(totalSpacing),
|
AddOffsetDirectionalLines(lines, profile.Perimeter.OffsetOutward(totalSpacing),
|
||||||
chordTolerance, part.Location, facingDirection);
|
chordTolerance, part.Location, facingDirection);
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ using OpenNest.Engine;
|
|||||||
using OpenNest.Engine.Fill;
|
using OpenNest.Engine.Fill;
|
||||||
using OpenNest.Engine.Strategies;
|
using OpenNest.Engine.Strategies;
|
||||||
using OpenNest.Geometry;
|
using OpenNest.Geometry;
|
||||||
|
using OpenNest.Math;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
@@ -275,8 +276,12 @@ namespace OpenNest
|
|||||||
{
|
{
|
||||||
var box2 = parts[j].BoundingBox;
|
var box2 = parts[j].BoundingBox;
|
||||||
|
|
||||||
if (box1.Right < box2.Left || box2.Right < box1.Left ||
|
var overlapX = System.Math.Min(box1.Right, box2.Right)
|
||||||
box1.Top < box2.Bottom || box2.Top < box1.Bottom)
|
- System.Math.Max(box1.Left, box2.Left);
|
||||||
|
var overlapY = System.Math.Min(box1.Top, box2.Top)
|
||||||
|
- System.Math.Max(box1.Bottom, box2.Bottom);
|
||||||
|
|
||||||
|
if (overlapX <= Tolerance.Epsilon || overlapY <= Tolerance.Epsilon)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
List<Vector> pts;
|
List<Vector> pts;
|
||||||
|
|||||||
Reference in New Issue
Block a user