mirror of
https://github.com/ajisaacs/OpenNest.git
synced 2026-10-27 05:01:05 -04:00
Revert "fix(ui): make part fills, labels and the cut trail easier to read"
This reverts commit 66afea5a51.
This commit is contained in:
1 parent
9d68945e75
commit
87b6d7ee90
6 files changed
+24
-123
No files matched your search
@@ -1,78 +0,0 @@
|
||||
using System.Drawing;
|
||||
|
||||
namespace OpenNest.WinForms.Tests;
|
||||
|
||||
public class ClassicPaletteTests
|
||||
{
|
||||
private static double Linear(byte channel)
|
||||
{
|
||||
var value = channel / 255.0;
|
||||
return value <= 0.04045 ? value / 12.92 : System.Math.Pow((value + 0.055) / 1.055, 2.4);
|
||||
}
|
||||
|
||||
private static double Luminance(Color c) => 0.2126 * Linear(c.R) + 0.7152 * Linear(c.G) + 0.0722 * Linear(c.B);
|
||||
|
||||
private static double Contrast(Color a, Color b)
|
||||
{
|
||||
var (hi, lo) = (System.Math.Max(Luminance(a), Luminance(b)), System.Math.Min(Luminance(a), Luminance(b)));
|
||||
return (hi + 0.05) / (lo + 0.05);
|
||||
}
|
||||
|
||||
// CIE76 distance in Lab, D65.
|
||||
private static (double L, double A, double B) Lab(Color c)
|
||||
{
|
||||
var r = Linear(c.R);
|
||||
var g = Linear(c.G);
|
||||
var b = Linear(c.B);
|
||||
var x = (0.4124 * r + 0.3576 * g + 0.1805 * b) / 0.95047;
|
||||
var y = 0.2126 * r + 0.7152 * g + 0.0722 * b;
|
||||
var z = (0.0193 * r + 0.1192 * g + 0.9505 * b) / 1.08883;
|
||||
static double F(double t) => t > 0.008856 ? System.Math.Cbrt(t) : 7.787 * t + 16.0 / 116;
|
||||
return (116 * F(y) - 16, 500 * (F(x) - F(y)), 200 * (F(y) - F(z)));
|
||||
}
|
||||
|
||||
private static double DeltaE(Color a, Color b)
|
||||
{
|
||||
var (l1, a1, b1) = Lab(a);
|
||||
var (l2, a2, b2) = Lab(b);
|
||||
return System.Math.Sqrt((l1 - l2) * (l1 - l2) + (a1 - a2) * (a1 - a2) + (b1 - b2) * (b1 - b2));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ClassicFillsAreClearlyDistinctFromEachOther()
|
||||
{
|
||||
var colors = ColorSchemeRegistry.Get("Classic").PartColors;
|
||||
Assert.Equal(12, colors.Length);
|
||||
for (var i = 0; i < colors.Length; i++)
|
||||
{
|
||||
for (var j = i + 1; j < colors.Length; j++)
|
||||
Assert.True(DeltaE(colors[i], colors[j]) >= 30,
|
||||
$"Classic colors {i} and {j} are too similar ({DeltaE(colors[i], colors[j]):F1}).");
|
||||
}
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ClassicFillsStayReadableAndClearOfEtchGreenAndTheSheet()
|
||||
{
|
||||
var scheme = ColorSchemeRegistry.Get("Classic");
|
||||
Assert.All(scheme.PartColors, color =>
|
||||
{
|
||||
Assert.True(Contrast(color, Color.Black) >= 4.5, $"{color} is too dark for black part IDs.");
|
||||
Assert.True(DeltaE(color, scheme.EtchColor) >= 50, $"{color} is too close to the etch color.");
|
||||
Assert.True(DeltaE(color, scheme.LayoutFillColor) >= 25, $"{color} blends into the sheet.");
|
||||
Assert.True(DeltaE(color, scheme.BackgroundColor) >= 25, $"{color} blends into the canvas.");
|
||||
});
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(255, 255, 255, false)]
|
||||
[InlineData(206, 153, 85, false)]
|
||||
[InlineData(104, 113, 230, false)]
|
||||
[InlineData(30, 30, 34, true)]
|
||||
[InlineData(60, 60, 140, true)]
|
||||
public void LabelIsWhiteOnDarkFillsAndBlackOnLightOnes(int r, int g, int b, bool expectWhite)
|
||||
{
|
||||
var brush = LayoutPart.LabelBrushFor(Color.FromArgb(r, g, b));
|
||||
Assert.Same(expectWhite ? Brushes.White : Brushes.Black, brush);
|
||||
}
|
||||
}
|
||||
@@ -33,7 +33,7 @@ namespace OpenNest
|
||||
public static readonly ColorScheme Default = new ColorScheme
|
||||
{
|
||||
Name = "Classic",
|
||||
BackgroundColor = Color.FromArgb(104, 108, 114),
|
||||
BackgroundColor = Color.DarkGray,
|
||||
LayoutOutlineColor = Color.Gray,
|
||||
LayoutFillColor = Color.WhiteSmoke,
|
||||
BoundingBoxColor = Color.FromArgb(128, 128, 255),
|
||||
|
||||
@@ -231,7 +231,7 @@ namespace OpenNest
|
||||
new ColorScheme
|
||||
{
|
||||
Name = "Classic",
|
||||
BackgroundColor = Color.FromArgb(104, 108, 114),
|
||||
BackgroundColor = Color.DarkGray,
|
||||
LayoutOutlineColor = Color.Gray,
|
||||
LayoutFillColor = Color.WhiteSmoke,
|
||||
BoundingBoxColor = Color.FromArgb(128, 128, 255),
|
||||
@@ -239,23 +239,20 @@ namespace OpenNest
|
||||
OriginColor = Color.Gray,
|
||||
EdgeSpacingColor = Color.FromArgb(180, 180, 180),
|
||||
PreviewPartColor = Color.FromArgb(255, 140, 0),
|
||||
// Twelve fills at least ~35 CIE76 apart from each other (the old set had near-duplicate
|
||||
// teals and purples under 10), each readable with black part IDs and clear of etch green.
|
||||
// Ordered so neighboring drawings contrast.
|
||||
PartColors = new[]
|
||||
{
|
||||
Color.FromArgb(206, 153, 85),
|
||||
Color.FromArgb(196, 66, 221),
|
||||
Color.FromArgb(196, 220, 67),
|
||||
Color.FromArgb(104, 113, 230),
|
||||
Color.FromArgb(62, 223, 145),
|
||||
Color.FromArgb(223, 67, 118),
|
||||
Color.FromArgb(135, 231, 224),
|
||||
Color.FromArgb(219, 91, 64),
|
||||
Color.FromArgb(82, 166, 223),
|
||||
Color.FromArgb(194, 217, 148),
|
||||
Color.FromArgb(212, 147, 220),
|
||||
Color.FromArgb(204, 132, 135),
|
||||
Color.FromArgb(205, 92, 92),
|
||||
Color.FromArgb(148, 103, 189),
|
||||
Color.FromArgb(75, 180, 175),
|
||||
Color.FromArgb(210, 190, 75),
|
||||
Color.FromArgb(190, 85, 175),
|
||||
Color.FromArgb(185, 115, 85),
|
||||
Color.FromArgb(120, 100, 190),
|
||||
Color.FromArgb(200, 100, 140),
|
||||
Color.FromArgb(80, 175, 155),
|
||||
Color.FromArgb(195, 160, 85),
|
||||
Color.FromArgb(175, 95, 160),
|
||||
Color.FromArgb(215, 130, 130),
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
@@ -484,8 +484,7 @@ internal sealed class CutSimulationOverlay : IDisposable
|
||||
private sealed class TrailPens(float dpi) : IDisposable
|
||||
{
|
||||
public Pen Rapid { get; } = new(Color.FromArgb(150, 70, 150, 255), 1 * dpi) { DashStyle = DashStyle.Dash };
|
||||
// A pale casing under the orange core keeps the trail visible on red, orange and brown parts.
|
||||
public Pen Glow { get; } = new(Color.FromArgb(210, 255, 255, 255), 5 * dpi) { LineJoin = LineJoin.Round };
|
||||
public Pen Glow { get; } = new(Color.FromArgb(70, 255, 140, 0), 6 * dpi) { LineJoin = LineJoin.Round };
|
||||
public Pen Cut { get; } = new(Color.OrangeRed, 2 * dpi) { LineJoin = LineJoin.Round };
|
||||
public Pen Scribe { get; } = new(Color.MediumOrchid, 1.5f * dpi);
|
||||
|
||||
|
||||
@@ -133,12 +133,11 @@ namespace OpenNest.Forms
|
||||
return;
|
||||
}
|
||||
|
||||
// Same numbering as the plate header: the trailing empty "new plate" workspace isn't counted.
|
||||
var plates = form.Nest.Plates;
|
||||
var shown = PlateDisplayNumbering.DisplayedPlateNumber(plates, form.PlateManager.CurrentIndex);
|
||||
plateIndex.Text = shown == null
|
||||
? "Plate: new"
|
||||
: string.Format("Plate: {0} of {1}", shown.Value, PlateDisplayNumbering.DisplayedPlateCount(plates));
|
||||
plateIndex.Text = string.Format(
|
||||
"Plate: {0} of {1}",
|
||||
form.PlateManager.CurrentIndex + 1,
|
||||
form.PlateManager.Count
|
||||
);
|
||||
|
||||
plateSize.Text = string.Format("Size: {0}", form.PlateView.Plate.Size);
|
||||
|
||||
|
||||
+4
-20
@@ -35,7 +35,7 @@ namespace OpenNest
|
||||
|
||||
static LayoutPart()
|
||||
{
|
||||
programIdFont = new Font(SystemFonts.DefaultFont, FontStyle.Bold);
|
||||
programIdFont = new Font(SystemFonts.DefaultFont, FontStyle.Bold | FontStyle.Underline);
|
||||
SelectedColor = Color.FromArgb(90, 150, 200, 255);
|
||||
leadInPen = new Pen(Color.OrangeRed, 1.5f);
|
||||
}
|
||||
@@ -110,10 +110,10 @@ namespace OpenNest
|
||||
DrawDisplay(g, muted);
|
||||
DrawEtch(g, muted);
|
||||
// Keep real cuts visible even where an etch overlaps them.
|
||||
g.DrawPath(muted ? Pens.DimGray : IsSelected && colorScheme.PartOutlineColor.IsEmpty ? selectedPen : pen, Path);
|
||||
g.DrawPath(muted ? Pens.Gray : IsSelected && colorScheme.PartOutlineColor.IsEmpty ? selectedPen : pen, Path);
|
||||
|
||||
if (LeadInPath != null)
|
||||
g.DrawPath(muted ? Pens.DimGray : leadInPen, LeadInPath);
|
||||
g.DrawPath(muted ? Pens.Gray : leadInPen, LeadInPath);
|
||||
}
|
||||
|
||||
public void Draw(Graphics g, string id) => Draw(g, id, false);
|
||||
@@ -130,29 +130,13 @@ namespace OpenNest
|
||||
g.DrawString(
|
||||
id,
|
||||
programIdFont,
|
||||
muted ? Brushes.DimGray : LabelBrushFor(color),
|
||||
muted ? Brushes.DimGray : Brushes.Black,
|
||||
_labelScreenPoint.X,
|
||||
_labelScreenPoint.Y,
|
||||
sf
|
||||
);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Black or white, whichever contrasts more with <paramref name="fill"/> (WCAG relative
|
||||
/// luminance; the two are equal at a luminance of about 0.179).
|
||||
/// </summary>
|
||||
internal static Brush LabelBrushFor(Color fill)
|
||||
{
|
||||
static double Linear(byte channel)
|
||||
{
|
||||
var value = channel / 255.0;
|
||||
return value <= 0.04045 ? value / 12.92 : System.Math.Pow((value + 0.055) / 1.055, 2.4);
|
||||
}
|
||||
|
||||
var luminance = 0.2126 * Linear(fill.R) + 0.7152 * Linear(fill.G) + 0.0722 * Linear(fill.B);
|
||||
return luminance > 0.179 ? Brushes.Black : Brushes.White;
|
||||
}
|
||||
|
||||
internal void ReleaseDisplayResources()
|
||||
{
|
||||
brush?.Dispose();
|
||||
|
||||
Reference in new issue
Block a user