diff --git a/OpenNest.Core/CNC/CuttingStrategy/CuttingParameters.cs b/OpenNest.Core/CNC/CuttingStrategy/CuttingParameters.cs index ddd33099..81c38dc5 100644 --- a/OpenNest.Core/CNC/CuttingStrategy/CuttingParameters.cs +++ b/OpenNest.Core/CNC/CuttingStrategy/CuttingParameters.cs @@ -81,9 +81,9 @@ namespace OpenNest.CNC.CuttingStrategy /// With on a plate with a support bed, the longest part (the /// long side of its outline's minimum-area bounding rectangle) its tab alone holds: such a /// part the bed cannot hold level is tabbed, and any tab clear of inside corners steadies - /// it. 0 turns the rule off. + /// it. 0 turns the rule off. New settings start at 6; settings saved without it read as 0. /// - public double TabHeldMaxLength { get; set; } + public double TabHeldMaxLength { get; set; } = 6; /// Whether a part long is held by its tab alone (see ). public bool TabHoldsAt(double length) => diff --git a/OpenNest.Tests/Support/TabHeldSupportTabTests.cs b/OpenNest.Tests/Support/TabHeldSupportTabTests.cs index cb89e874..c86ae53f 100644 --- a/OpenNest.Tests/Support/TabHeldSupportTabTests.cs +++ b/OpenNest.Tests/Support/TabHeldSupportTabTests.cs @@ -60,6 +60,35 @@ public class TabHeldSupportTabTests Assert.Equal(holdsALengthOfOneAndAHalf, new CuttingParameters { TabHeldMaxLength = max }.TabHoldsAt(1.5)); } + [Theory] + [InlineData(0)] + [InlineData(45)] + [InlineData(90)] + [InlineData(135)] + [InlineData(180)] + [InlineData(270)] + [InlineData(315)] + public void LengthOfATriangleWithTwoLeastBoxes_DoesNotDependOnItsRotation(double degrees) + { + // A 5 x 5 right triangle fits its legs' square and its hypotenuse's 7.07 x 3.54 box, both + // of area 25: the squarer box is the one measured, whatever way the part is turned. + var triangle = new Program(); + triangle.MoveTo(0, 0); triangle.LineTo(5, 0); triangle.LineTo(0, 5); triangle.LineTo(0, 0); + var part = new Part(new Drawing("gusset", triangle), new Vector(10, 10)); + part.Rotate(degrees * System.Math.PI / 180); + var material = SupportMaterial.FromPart(part); + + Assert.Equal(5, SupportAnalyzer.Length(material), 6); + Assert.Equal(5, SupportAnalyzer.Width(material), 6); + } + + [Fact] + public void NewSettingsHoldPartsUpToSixLong() + { + Assert.Equal(6, new CuttingParameters().TabHeldMaxLength); + Assert.True(new CuttingParameters().TabHoldsAt(5)); + } + [Fact] public void Analyze_HoldsAShortPartTheBedCannotByAnyClearTab() { diff --git a/docs/support-tabs.md b/docs/support-tabs.md index 422e02ec..2790ad72 100644 --- a/docs/support-tabs.md +++ b/docs/support-tabs.md @@ -102,7 +102,12 @@ hold level whose length (the long side of its outline's minimum-area bounding re `SupportAnalyzer.Length`) is at most that, bound included, is still tabbed, but `SupportAnalyzer.HeldByTab` marks its analysis `IsHeldByTab`: it keeps its contacts and margin, every tab clear of inside corners steadies it, and its best tab point is chosen as on a plate -with no bed (below). A part the bed holds is not tabbed. 0 turns the rule off. +with no bed (below). A part the bed holds is not tabbed. 0 turns the rule off; new settings +start at 6, while settings saved without the field read as 0, so saved settings keep their +meaning. Some outlines have two minimum-area rectangles (a right isosceles triangle fits both +its legs' square and its hypotenuse's 2:1 box), and which one rounding finds depends on how the +part is turned; of rectangles tied for area, `SupportAnalyzer` measures the one with the shorter +long side, so a drawing's length and width are the same at every rotation. `SupportTabSettings.Analyze` applies it for Plan Cutting, hand-placed lead-ins and the pre-post review alike, so such a part warns only when it is cut with no tab at all. View > Draw Support does not read cutting settings and still shows it red, since it would tip without its tab.