using System; using System.Collections.Generic; using OpenNest.Geometry; namespace OpenNest.Converters { /// What a drawing does with a source entity. public enum EntityRole { /// Cut through the material. Cut, /// Marked on the surface (a Scribe pass): never material. Etch, /// /// Shown with the part for reference only. It is kept out of the program, so it is never /// cut, posted, nested against or verified. /// Display, } /// /// Applies per-entity role overrides. An entity without an override keeps the role its layer /// implies: mark layers (ETCH, SCRIBE, ENGRAVE) etch, everything else cuts. /// public static class EntityRoles { public static EntityRole Default(Entity entity) => ScribeLayerRepair.IsMarkLayer(entity.Layer) ? EntityRole.Etch : EntityRole.Cut; public static EntityRole Of(Entity entity, IReadOnlyDictionary overrides) => overrides != null && overrides.TryGetValue(entity.Id, out var role) ? role : Default(entity); /// /// The entities a program is built from: display-only entities are left out and entities /// whose override differs from their layer's role are replaced by copies, with the same /// ID, on a layer the converters read as that role. Inputs are never mutated. /// public static List ForProgram(IEnumerable entities, IReadOnlyDictionary overrides) { var result = new List(); foreach (var entity in entities) { if (overrides == null || !overrides.TryGetValue(entity.Id, out var role) || role == Default(entity)) { result.Add(entity); continue; } if (role == EntityRole.Display) continue; var copy = entity.Clone(); copy.Id = entity.Id; copy.Layer = new Layer(role == EntityRole.Etch ? SpecialLayers.Scribe.Name : SpecialLayers.Cut.Name) { Color = entity.Layer?.Color ?? SpecialLayers.Cut.Color, IsVisible = true, }; result.Add(copy); } return result; } /// /// A drawing's unsuppressed display-only entities as copies in its program frame (source /// coordinates shifted by -Source.Offset, before any program rotation). /// public static List DisplayGeometry(Drawing drawing) { var result = new List(); if (drawing?.SourceEntities == null || drawing.EntityRoles == null || drawing.EntityRoles.Count == 0) return result; var offset = drawing.Source?.Offset ?? Vector.Zero; foreach (var entity in drawing.SourceEntities) { if (drawing.SuppressedEntityIds.Contains(entity.Id) || Of(entity, drawing.EntityRoles) != EntityRole.Display) continue; var copy = entity.Clone(); copy.Id = entity.Id; copy.Offset(-offset.X, -offset.Y); result.Add(copy); } return result; } } }