public static List <Line> setConcaveHull(double concavity, int scaleFactor) { /* Run setConvHull before! * Concavity is a value used to restrict the concave angles * It can go from -1 (no concavity) to 1 (extreme concavity) * Avoid concavity == 1 if you don't want 0º angles * */ bool aLineWasDividedInTheIteration; hull_concave_edges.AddRange(hull_edges); do { aLineWasDividedInTheIteration = false; for (int linePositionInHull = 0; linePositionInHull < hull_concave_edges.Count && !aLineWasDividedInTheIteration; linePositionInHull++) { Line line = hull_concave_edges[linePositionInHull]; List <Node> nearbyPoints = HullFunctions.getNearbyPoints(line, unused_nodes, scaleFactor); List <Line> dividedLine = HullFunctions.getDividedLine(line, nearbyPoints, hull_concave_edges, concavity); if (dividedLine.Count > 0) // Line divided! { aLineWasDividedInTheIteration = true; unused_nodes.Remove(unused_nodes.Where(n => n.id == dividedLine[0].nodes[1].id).FirstOrDefault()); // Middlepoint no longer free hull_concave_edges.AddRange(dividedLine); hull_concave_edges.RemoveAt(linePositionInHull); // Divided line no longer exists } } hull_concave_edges = hull_concave_edges.OrderByDescending(a => Line.getLength(a.nodes[0], a.nodes[1])).ToList(); } while (aLineWasDividedInTheIteration); return(hull_concave_edges); }
public static void setConcaveHull(decimal concavity, int scaleFactor, bool isSquareGrid) { /* Run setConvHull before! * Concavity is a value used to restrict the concave angles * it can go from -1 to 1 (it wont crash if you go further) * */ Hull.scaleFactor = scaleFactor; hull_concave_edges = new List <Line>(hull_edges.OrderByDescending(a => Line.getLength(a.nodes[0], a.nodes[1])).ToList()); Line selected_edge; List <Line> aux = new List <Line>();; int list_original_size; int count = 0; bool listIsModified = false; do { listIsModified = false; count = 0; list_original_size = hull_concave_edges.Count; while (count < list_original_size) { selected_edge = hull_concave_edges[0]; hull_concave_edges.RemoveAt(0); aux = new List <Line>(); if (!selected_edge.isChecked) { List <Node> nearby_points = HullFunctions.getNearbyPoints(selected_edge, unused_nodes, Hull.scaleFactor); aux.AddRange(HullFunctions.setConcave(selected_edge, nearby_points, hull_concave_edges, concavity, isSquareGrid)); listIsModified = listIsModified || (aux.Count > 1); if (aux.Count > 1) { foreach (Node node in aux[0].nodes) { if (unused_nodes.Find(a => a.id == node.id) != null) { unused_nodes.Remove(unused_nodes.Where(a => a.id == node.id).First()); } } } else { aux[0].isChecked = true; } } else { aux.Add(selected_edge); } hull_concave_edges.AddRange(aux); count++; } hull_concave_edges = hull_concave_edges.OrderByDescending(a => Line.getLength(a.nodes[0], a.nodes[1])).ToList(); list_original_size = hull_concave_edges.Count; } while (listIsModified); }