public void Filter(SkeletonBuilder skeleton) { foreach (SkeletonBuilder.Minutia minutia in skeleton.Minutiae) { if (minutia.Ridges.Count == 3) { for (int exit = 0; exit < 3; ++exit) { SkeletonBuilder.Ridge exitRidge = minutia.Ridges[exit]; SkeletonBuilder.Ridge arm1 = minutia.Ridges[(exit + 1) % 3]; SkeletonBuilder.Ridge arm2 = minutia.Ridges[(exit + 2) % 3]; if (arm1.End == arm2.End && exitRidge.End != arm1.End && arm1.End != minutia && exitRidge.End != minutia) { SkeletonBuilder.Minutia end = arm1.End; if (end.Ridges.Count == 3 && arm1.Points.Count <= MaxArmLength && arm2.Points.Count <= MaxArmLength) { arm1.Detach(); arm2.Detach(); SkeletonBuilder.Ridge merged = new SkeletonBuilder.Ridge(); merged.Start = minutia; merged.End = end; foreach (Point point in Calc.ConstructLine(minutia.Position, end.Position)) { merged.Points.Add(point); } } break; } } } } KnotRemover.Filter(skeleton); Logger.Log(skeleton); }
bool IsWithinLimits(SkeletonBuilder.Minutia end1, SkeletonBuilder.Minutia end2) { int distanceSq = Calc.DistanceSq(end1.Position, end2.Position); if (distanceSq <= Calc.Sq(RuptureSize)) { return(true); } if (distanceSq > Calc.Sq(GapSize)) { return(false); } byte gapDirection = Angle.AtanB(end1.Position, end2.Position); byte direction1 = Angle.AtanB(end1.Position, GetAngleSample(end1)); if (Angle.Distance(direction1, Angle.Opposite(gapDirection)) > GapAngle) { return(false); } byte direction2 = Angle.AtanB(end2.Position, GetAngleSample(end2)); if (Angle.Distance(direction2, gapDirection) > GapAngle) { return(false); } return(true); }
Point GetAngleSample(SkeletonBuilder.Minutia minutia) { SkeletonBuilder.Ridge ridge = minutia.Ridges[0]; if (AngleSampleOffset < ridge.Points.Count) { return(ridge.Points[AngleSampleOffset]); } else { return(ridge.End.Position); } }
Dictionary<Point, SkeletonBuilder.Minutia> ComputeMinutiaCenters(Dictionary<Point, List<Point>> linking, SkeletonBuilder skeleton) { Dictionary<Point, SkeletonBuilder.Minutia> centers = new Dictionary<Point, SkeletonBuilder.Minutia>(); foreach (Point currentPos in linking.Keys) { List<Point> linkedMinutiae = linking[currentPos]; Point primaryPos = linkedMinutiae[0]; if (!centers.ContainsKey(primaryPos)) { Point sum = new Point(); foreach (Point linkedPos in linkedMinutiae) sum = Calc.Add(sum, linkedPos); Point center = new Point(sum.X / linkedMinutiae.Count, sum.Y / linkedMinutiae.Count); SkeletonBuilder.Minutia minutia = new SkeletonBuilder.Minutia(center); skeleton.AddMinutia(minutia); centers[primaryPos] = minutia; } centers[currentPos] = centers[primaryPos]; } return centers; }
Dictionary <Point, SkeletonBuilder.Minutia> ComputeMinutiaCenters(Dictionary <Point, List <Point> > linking, SkeletonBuilder skeleton) { Dictionary <Point, SkeletonBuilder.Minutia> centers = new Dictionary <Point, SkeletonBuilder.Minutia>(); foreach (Point currentPos in linking.Keys) { List <Point> linkedMinutiae = linking[currentPos]; Point primaryPos = linkedMinutiae[0]; if (!centers.ContainsKey(primaryPos)) { Point sum = new Point(); foreach (Point linkedPos in linkedMinutiae) { sum = Calc.Add(sum, linkedPos); } Point center = new Point(sum.X / linkedMinutiae.Count, sum.Y / linkedMinutiae.Count); SkeletonBuilder.Minutia minutia = new SkeletonBuilder.Minutia(center); skeleton.AddMinutia(minutia); centers[primaryPos] = minutia; } centers[currentPos] = centers[primaryPos]; } return(centers); }