public List <Vector3[]> Generate(WallGrid grid) { byte[,] configurations = MarchingSquares.ComputeConfigurations(grid); length = configurations.GetLength(0); width = configurations.GetLength(1); TwoWayLookup outlineLookup = CreateLookupTable(configurations, outlineTable); var outlines = cachedOutlines; outlines.Clear(); var visited = cachedVisited; visited.Clear(); foreach (var pair in outlineLookup) { if (!visited.Contains(pair.Key)) { LocalPosition start = pair.Key; LocalPosition next = pair.Value; var outline = new List <LocalPosition>(); AddToOutline(outline, start, visited); AddToOutline(outline, next, visited); // first do a backward pass until looping or running out of connected outline edges while (start != next && outlineLookup.TryGetBackwardValue(next, out next)) { AddToOutline(outline, next, visited); } outline.Reverse(); // if no loop, then do a forward pass from the starting point if (start != next) { next = start; while (outlineLookup.TryGetForwardValue(next, out next)) { AddToOutline(outline, next, visited); } } Vector3[] completeOutline = outline.Select(p => p.ToGlobalPosition(grid.Scale, grid.Position)).ToArray(); outlines.Add(completeOutline); } } return(outlines); }
public static List <Vector3[]> Generate(WallGrid grid) { byte[][] outlineTable = BuildOutlineTable(); byte[,] configurations = MarchingSquares.ComputeConfigurations(grid); int numOutlineEdges = CountOutlineEdges(configurations, outlineTable); TwoWayLookup outlineLookup = CreateLookupTable(configurations, outlineTable, numOutlineEdges); var outlines = new List <Vector3[]>(); var visited = new HashSet <LocalPosition>(); foreach (var pair in outlineLookup) { if (!visited.Contains(pair.Key)) { LocalPosition start = pair.Key; LocalPosition next = pair.Value; var outline = new List <LocalPosition>(); AddToOutline(outline, start, visited); AddToOutline(outline, next, visited); // first do a backward pass until looping or running out of connected outline edges while (start != next && outlineLookup.TryGetBackwardValue(next, out next)) { AddToOutline(outline, next, visited); } outline.Reverse(); // if no loop, then do a forward pass from the starting point if (start != next) { next = start; while (outlineLookup.TryGetForwardValue(next, out next)) { AddToOutline(outline, next, visited); } } outlines.Add(ToGlobalPositions(outline, grid.Scale, grid.Position)); } } return(outlines); }
static TwoWayLookup CreateLookupTable(byte[,] configurations, byte[][] outlineTable, int capacity) { var lookupTable = new TwoWayLookup(capacity); int length = configurations.GetLength(0); int width = configurations.GetLength(1); for (int y = 0; y < width; y++) { for (int x = 0; x < length; x++) { byte[] outlineData = outlineTable[configurations[x, y]]; for (int i = 0; i < outlineData.Length; i += 2) { var a = new LocalPosition(x, y, outlineData[i]); var b = new LocalPosition(x, y, outlineData[i + 1]); lookupTable.AddPair(a, b); } } } return(lookupTable); }