diff --git a/Distance/Models/MapLogicSupport.cs b/Distance/Models/MapLogicSupport.cs new file mode 100644 index 0000000..0323ad9 --- /dev/null +++ b/Distance/Models/MapLogicSupport.cs @@ -0,0 +1,300 @@ +using ShellProgressBar; +using System.Text.Json; +using View_by_Distance.FaceRecognitionDotNet; +using View_by_Distance.Map.Models; +using View_by_Distance.Shared.Models; +using View_by_Distance.Shared.Models.Properties; + +namespace View_by_Distance.Distance.Models; + +public class MapLogicSupport : Shared.Models.Methods.IMapLogicSupport +{ + + private readonly int _FaceDistancePermyriad; + private readonly int _SortingDaysDeltaTolerance; + private readonly double _FaceDistanceMinimumConfidence; + private readonly int _FaceDistanceAreaPermilleTolerance; + private readonly int _SortingMaximumPerFaceShouldBeHigh; + + public MapLogicSupport(int faceDistanceAreaPermilleTolerance, double faceDistanceMinimumConfidence, int faceDistancePermyriad, int sortingDaysDeltaTolerance, int sortingMaximumPerFaceShouldBeHigh) + { + _FaceDistancePermyriad = faceDistancePermyriad; + _SortingDaysDeltaTolerance = sortingDaysDeltaTolerance; + _FaceDistanceMinimumConfidence = faceDistanceMinimumConfidence; + _FaceDistanceAreaPermilleTolerance = faceDistanceAreaPermilleTolerance; + _SortingMaximumPerFaceShouldBeHigh = sortingMaximumPerFaceShouldBeHigh; + } + + public static void SaveFaceDistances(Property.Models.Configuration configuration, SortingContainer[] sortingContainers) + { + string eDistanceContentCollectionDirectory = Property.Models.Stateless.IResult.GetResultsDateGroupDirectory(configuration, nameof(E_Distance), "([])"); + if (!Directory.Exists(eDistanceContentCollectionDirectory)) + _ = Directory.CreateDirectory(eDistanceContentCollectionDirectory); +#pragma warning disable + string[] results = (from l in sortingContainers select l.ToString()).ToArray(); +#pragma warning restore + string eDistanceContentFileName = Path.Combine(eDistanceContentCollectionDirectory, $"{configuration.ResultAllInOne}.tvs"); + File.WriteAllLines(eDistanceContentFileName, results); + } + + private List GetSortingContainers(Face face, FaceDistance faceDistanceEncoding, List sortingCollection, int? useFiltersCounter) + { + List results = new(); + SortingContainer sortingContainer; + Sorting[] collection = Shared.Models.Stateless.Methods.ISorting.Sort(sortingCollection); + double faceDistancePermyriad; + double sortingDaysDeltaTolerance; + double faceDistanceMinimumConfidence; + double faceDistanceAreaPermilleTolerance; + if (useFiltersCounter is null) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance; + faceDistancePermyriad = _FaceDistancePermyriad; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence; + } + else if (useFiltersCounter.Value == 1) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5; + faceDistancePermyriad = _FaceDistancePermyriad; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence; + } + else if (useFiltersCounter.Value == 2) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance; + faceDistancePermyriad = _FaceDistancePermyriad * 1.5; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence; + } + else if (useFiltersCounter.Value == 3) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance; + faceDistancePermyriad = _FaceDistancePermyriad; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5; + } + else if (useFiltersCounter.Value == 4) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2; + faceDistancePermyriad = _FaceDistancePermyriad * 1.5; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5; + } + else if (useFiltersCounter.Value == 5) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5; + faceDistancePermyriad = _FaceDistancePermyriad * 2; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5; + } + else if (useFiltersCounter.Value == 6) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5; + faceDistancePermyriad = _FaceDistancePermyriad * 1.5; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25; + } + else if (useFiltersCounter.Value == 7) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2.5; + faceDistancePermyriad = _FaceDistancePermyriad * 2; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25; + } + else if (useFiltersCounter.Value == 8) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2; + faceDistancePermyriad = _FaceDistancePermyriad * 2.5; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25; + } + else if (useFiltersCounter.Value == 9) + { + sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2; + faceDistancePermyriad = _FaceDistancePermyriad * 2; + faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; + faceDistanceMinimumConfidence = 0; + } + else + { + sortingDaysDeltaTolerance = int.MaxValue; + faceDistancePermyriad = int.MaxValue; + faceDistanceAreaPermilleTolerance = 0; + faceDistanceMinimumConfidence = 0; + } + foreach (Sorting sorting in collection) + { + if (face.Mapping is null || faceDistanceEncoding.NormalizedPixelPercentage is null) + throw new NotSupportedException(); + if (sorting.DaysDelta > sortingDaysDeltaTolerance || sorting.DistancePermyriad > faceDistancePermyriad || face.Mapping.MappingFromLocation.Confidence < faceDistanceMinimumConfidence || face.Mapping.MappingFromLocation.AreaPermille < faceDistanceAreaPermilleTolerance) + continue; + sortingContainer = new(face.Mapping, sorting); + results.Add(sortingContainer); + if (results.Count >= _SortingMaximumPerFaceShouldBeHigh) + break; + } + return results; + } + + private static List GetSortingCollection(MapLogic mapLogic, List faceDistanceEncodings, int faceDistanceContainersLength, int i, FaceDistance faceDistanceEncoding) + { + List results; + List faceDistanceLengths = FaceRecognition.FaceDistances(faceDistanceEncodings, faceDistanceEncoding); + if (faceDistanceLengths.Count != faceDistanceContainersLength) + throw new NotSupportedException(); + results = mapLogic.GetSortingCollection(i, faceDistanceEncoding, faceDistanceLengths); + return results; + } + + private static FaceDistanceContainer[] GetFaceDistanceContainers(Face[] distinctFilteredFaces) + { + FaceDistanceContainer[] results; + FaceDistance faceDistance; + FaceDistanceContainer faceDistanceContainer; + List collection = new(); + foreach (Face face in distinctFilteredFaces) + { + if (face.Mapping is null) + throw new NotSupportedException(); + if (face.FaceDistance?.Encoding is not FaceRecognitionDotNet.FaceEncoding faceEncoding) + continue; + faceDistance = new(face.Mapping.MappingFromLocation.Confidence, faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromItem.MinimumDateTime, face.Mapping.MappingFromLocation.NormalizedPixelPercentage); + faceDistanceContainer = new(face, faceDistance); + collection.Add(faceDistanceContainer); + } + results = collection.ToArray(); + return results; + } + + private static List GetFaceDistanceEncodings(FaceDistanceContainer[] faceDistanceContainers) + { + List faceDistanceEncodings = new(); + foreach (FaceDistanceContainer faceDistanceContainer in faceDistanceContainers) + { + if (faceDistanceContainer.FaceDistance.Encoding is null) + continue; + faceDistanceEncodings.Add(faceDistanceContainer.FaceDistance); + } + return faceDistanceEncodings; + } + + public SortingContainer[] SetFaceMappingSortingCollectionThenGetSortingContainers(int maxDegreeOfParallelism, long ticks, MapLogic mapLogic, Face[] distinctFilteredFaces, int? useFiltersCounter) + { + SortingContainer[] results; + List collection = new(); + int totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); + ParallelOptions parallelOptions = new() { MaxDegreeOfParallelism = maxDegreeOfParallelism }; + FaceDistanceContainer[] faceDistanceContainers = GetFaceDistanceContainers(distinctFilteredFaces); + List faceDistanceEncodings = GetFaceDistanceEncodings(faceDistanceContainers); + string message = $") {faceDistanceContainers.Length:000} Get Sorting Containers Then Set Face Mapping Sorting Collection - {totalSeconds} total second(s)"; + ProgressBarOptions options = new() { ProgressCharacter = '─', ProgressBarOnBottom = true, DisableBottomPercentage = true }; + using ProgressBar progressBar = new(faceDistanceContainers.Length, message, options); + _ = Parallel.For(0, faceDistanceContainers.Length, parallelOptions, (i, state) => + { + progressBar.Tick(); + Face face = faceDistanceContainers[i].Face; + if (face.Mapping is null) + throw new NotSupportedException(); + FaceDistance faceDistanceEncoding = faceDistanceContainers[i].FaceDistance; + if (mapLogic.Used(faceDistanceEncoding)) + return; + List sortingCollection = GetSortingCollection(mapLogic, faceDistanceEncodings, faceDistanceContainers.Length, i, faceDistanceEncoding); + if (!sortingCollection.Any()) + return; + List sortingContainers = GetSortingContainers(face, faceDistanceEncoding, sortingCollection, useFiltersCounter); + if (sortingContainers.Any()) + { + lock (collection) + collection.AddRange(sortingContainers); + } + }); + if (!collection.Any()) + results = Array.Empty(); + else + results = Shared.Models.Stateless.Methods.ISortingContainer.Sort(collection); + return results; + } + + public static Mapping[] GetSelectedMappingCollection(Face[] distinctFilteredFaces) + { + Mapping[] results; + IEnumerable collection = from l in distinctFilteredFaces orderby l.Mapping?.MappingFromItem.MinimumDateTime descending select l.Mapping; + results = (from l in collection where l is not null select l).ToArray(); + return results; + } + + public static void SetFaceDistances(int maxDegreeOfParallelism, long ticks, Face[] distinctFilteredFaces) + { + int totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); + ParallelOptions parallelOptions = new() { MaxDegreeOfParallelism = maxDegreeOfParallelism }; + string message = $") {distinctFilteredFaces.Length:000} Load Face Encoding - {totalSeconds} total second(s)"; + ProgressBarOptions options = new() { ProgressCharacter = '─', ProgressBarOnBottom = true, DisableBottomPercentage = true }; + using ProgressBar progressBar = new(distinctFilteredFaces.Length, message, options); + _ = Parallel.For(0, distinctFilteredFaces.Length, parallelOptions, (i, state) => + { + Face face = distinctFilteredFaces[i]; + if (face.FaceEncoding is null || face.Mapping is null) + throw new NotSupportedException(); + if (face.FaceDistance?.Encoding is not null && face.FaceDistance.Encoding is FaceRecognitionDotNet.FaceEncoding faceEncoding) + return; + progressBar.Tick(); + faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); + FaceDistance faceDistance = new(face.Mapping.MappingFromLocation.Confidence, faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromItem.MinimumDateTime, face.Mapping.MappingFromLocation.NormalizedPixelPercentage); + lock (face) + face.SetFaceDistance(faceDistance); + }); + } + + void Shared.Models.Methods.IMapLogicSupport.SavePossiblyNewPersonContainers(IPropertyConfiguration propertyConfiguration, string personBirthdayFormat, string facesFileNameExtension, string? a2PeopleSingletonDirectory, Dictionary personKeyToPersonContainer, List<(string[], PersonContainer)> possiblyNewPersonDisplayDirectoryNamesAndPersonContainer) + { + char @char; + string json; + string[] files; + string checkFile; + string[] segments; + const int zero = 0; + string personKeyFormatted; + string personDisplayDirectory; + PersonBirthday personBirthday; + string personDisplayDirectoryName; + string checkPersonDisplayDirectory; + string checkPersonKeyFormattedDirectory; + char[] chars = Shared.Models.Stateless.Methods.IAge.GetChars(); + JsonSerializerOptions jsonSerializerOptions = new() { WriteIndented = true }; + foreach ((string[] personDisplayDirectoryNames, PersonContainer personContainer) in possiblyNewPersonDisplayDirectoryNamesAndPersonContainer) + { + if (a2PeopleSingletonDirectory is null || personContainer.Key is null || personContainer.Birthdays is null || !personContainer.Birthdays.Any()) + continue; + personBirthday = personContainer.Birthdays[zero]; + personDisplayDirectoryName = personDisplayDirectoryNames[^1]; + personDisplayDirectory = Path.Combine(personDisplayDirectoryNames); + personKeyFormatted = Shared.Models.Stateless.Methods.IPersonBirthday.GetFormatted(personBirthdayFormat, personBirthday); + segments = personDisplayDirectoryName.Split(chars); + if (segments.Length != 2) + @char = '_'; + else + @char = personDisplayDirectoryName[segments[zero].Length]; + checkPersonDisplayDirectory = Path.Combine(a2PeopleSingletonDirectory, @char.ToString(), personDisplayDirectoryName); + checkPersonKeyFormattedDirectory = Path.Combine(checkPersonDisplayDirectory, personKeyFormatted); + if (Directory.Exists(checkPersonKeyFormattedDirectory)) + continue; + _ = Directory.CreateDirectory(checkPersonKeyFormattedDirectory); + checkFile = Path.Combine(checkPersonKeyFormattedDirectory, $"{personKeyFormatted}.json"); + json = JsonSerializer.Serialize(personContainer.Person, jsonSerializerOptions); + _ = Shared.Models.Stateless.Methods.IPath.WriteAllText(checkFile, json, updateDateWhenMatches: false, compareBeforeWrite: true); + if (!Directory.Exists(personDisplayDirectory)) + continue; + files = Directory.GetFiles(personDisplayDirectory, $"*{facesFileNameExtension}", SearchOption.TopDirectoryOnly); + foreach (string file in files) + { + checkFile = Path.Combine(checkPersonDisplayDirectory, Path.GetFileName(file)); + if (File.Exists(checkFile)) + continue; + File.Copy(files[0], checkFile); + break; + } + } + } + +} \ No newline at end of file diff --git a/Distance/Models/_E_Distance.cs b/Distance/Models/_E_Distance.cs index bceeb51..d35f5cf 100644 --- a/Distance/Models/_E_Distance.cs +++ b/Distance/Models/_E_Distance.cs @@ -1,333 +1,35 @@ -using ShellProgressBar; using System.Text.Json; using View_by_Distance.FaceRecognitionDotNet; -using View_by_Distance.Map.Models; using View_by_Distance.Shared.Models; -using View_by_Distance.Shared.Models.Properties; namespace View_by_Distance.Distance.Models; -public class E_Distance : Shared.Models.Methods.IFaceDistance +public partial class E_Distance { private readonly List _Moved; private readonly List _Debug; private readonly List _Renamed; - private readonly Serilog.ILogger? _Log; - private readonly string _ResultAllInOne; - private readonly int _FaceDistancePermyriad; private readonly bool _DistanceRenameToMatch; private readonly double _FaceDistanceTolerance; - private readonly int _SortingDaysDeltaTolerance; private readonly bool _DistanceMoveUnableToMatch; private readonly List _AllMappedFaceFiles; private readonly int _DistancePixelDistanceTolerance; private readonly List _AllMappedFaceFileNames; - private readonly double _FaceDistanceMinimumConfidence; private readonly List _DuplicateMappedFaceFiles; - private readonly int _FaceDistanceAreaPermilleTolerance; - private readonly int _SortingMaximumPerFaceShouldBeHigh; - public E_Distance(bool distanceMoveUnableToMatch, int distancePixelDistanceTolerance, bool distanceRenameToMatch, int faceDistanceAreaPermilleTolerance, double faceDistanceMinimumConfidence, int faceDistancePermyriad, double faceDistanceTolerance, string resultAllInOne, int sortingDaysDeltaTolerance, int sortingMaximumPerFaceShouldBeHigh) + public E_Distance(bool distanceMoveUnableToMatch, int distancePixelDistanceTolerance, bool distanceRenameToMatch, double faceDistanceTolerance) { _Debug = new(); _Moved = new(); _Renamed = new(); _AllMappedFaceFiles = new(); _AllMappedFaceFileNames = new(); - _ResultAllInOne = resultAllInOne; _DuplicateMappedFaceFiles = new(); - _Log = Serilog.Log.ForContext(); _DistanceRenameToMatch = distanceRenameToMatch; - _FaceDistancePermyriad = faceDistancePermyriad; _FaceDistanceTolerance = faceDistanceTolerance; _DistanceMoveUnableToMatch = distanceMoveUnableToMatch; - _SortingDaysDeltaTolerance = sortingDaysDeltaTolerance; - _FaceDistanceMinimumConfidence = faceDistanceMinimumConfidence; _DistancePixelDistanceTolerance = distancePixelDistanceTolerance; - _FaceDistanceAreaPermilleTolerance = faceDistanceAreaPermilleTolerance; - _SortingMaximumPerFaceShouldBeHigh = sortingMaximumPerFaceShouldBeHigh; - } - - public static void SaveFaceDistances(Property.Models.Configuration configuration, SortingContainer[] sortingContainers) - { - string eDistanceContentCollectionDirectory = Property.Models.Stateless.IResult.GetResultsDateGroupDirectory(configuration, nameof(E_Distance), "([])"); - if (!Directory.Exists(eDistanceContentCollectionDirectory)) - _ = Directory.CreateDirectory(eDistanceContentCollectionDirectory); -#pragma warning disable - string[] results = (from l in sortingContainers select l.ToString()).ToArray(); -#pragma warning restore - string eDistanceContentFileName = Path.Combine(eDistanceContentCollectionDirectory, $"{configuration.ResultAllInOne}.tvs"); - File.WriteAllLines(eDistanceContentFileName, results); - } - - private static List GetSortingCollection(MapLogic mapLogic, List faceDistanceEncodings, int faceDistanceContainersLength, int i, FaceDistance faceDistanceEncoding) - { - List results; - List faceDistanceLengths = FaceRecognition.FaceDistances(faceDistanceEncodings, faceDistanceEncoding); - if (faceDistanceLengths.Count != faceDistanceContainersLength) - throw new NotSupportedException(); - results = mapLogic.GetSortingCollection(i, faceDistanceEncoding, faceDistanceLengths); - return results; - } - - private List GetSortingContainers(Face face, FaceDistance faceDistanceEncoding, List sortingCollection, int? useFiltersCounter) - { - List results = new(); - SortingContainer sortingContainer; - Sorting[] collection = Shared.Models.Stateless.Methods.ISorting.Sort(sortingCollection); - double faceDistancePermyriad; - double sortingDaysDeltaTolerance; - double faceDistanceMinimumConfidence; - double faceDistanceAreaPermilleTolerance; - if (useFiltersCounter is null) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance; - faceDistancePermyriad = _FaceDistancePermyriad; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence; - } - else if (useFiltersCounter.Value == 1) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5; - faceDistancePermyriad = _FaceDistancePermyriad; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence; - } - else if (useFiltersCounter.Value == 2) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance; - faceDistancePermyriad = _FaceDistancePermyriad * 1.5; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence; - } - else if (useFiltersCounter.Value == 3) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance; - faceDistancePermyriad = _FaceDistancePermyriad; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5; - } - else if (useFiltersCounter.Value == 4) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2; - faceDistancePermyriad = _FaceDistancePermyriad * 1.5; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5; - } - else if (useFiltersCounter.Value == 5) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5; - faceDistancePermyriad = _FaceDistancePermyriad * 2; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5; - } - else if (useFiltersCounter.Value == 6) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5; - faceDistancePermyriad = _FaceDistancePermyriad * 1.5; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25; - } - else if (useFiltersCounter.Value == 7) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2.5; - faceDistancePermyriad = _FaceDistancePermyriad * 2; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25; - } - else if (useFiltersCounter.Value == 8) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2; - faceDistancePermyriad = _FaceDistancePermyriad * 2.5; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25; - } - else if (useFiltersCounter.Value == 9) - { - sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2; - faceDistancePermyriad = _FaceDistancePermyriad * 2; - faceDistanceAreaPermilleTolerance = _FaceDistanceAreaPermilleTolerance; - faceDistanceMinimumConfidence = 0; - } - else - { - sortingDaysDeltaTolerance = int.MaxValue; - faceDistancePermyriad = int.MaxValue; - faceDistanceAreaPermilleTolerance = 0; - faceDistanceMinimumConfidence = 0; - } - foreach (Sorting sorting in collection) - { - if (face.Mapping is null || faceDistanceEncoding.NormalizedPixelPercentage is null) - throw new NotSupportedException(); - if (sorting.DaysDelta > sortingDaysDeltaTolerance || sorting.DistancePermyriad > faceDistancePermyriad || face.Mapping.MappingFromLocation.Confidence < faceDistanceMinimumConfidence || face.Mapping.MappingFromLocation.AreaPermille < faceDistanceAreaPermilleTolerance) - continue; - sortingContainer = new(face.Mapping, sorting); - results.Add(sortingContainer); - if (results.Count >= _SortingMaximumPerFaceShouldBeHigh) - break; - } - return results; - } - - private static FaceDistanceContainer[] GetOrderedFaceDistanceContainers(List collection) - { - FaceDistanceContainer[] results; - results = (from l in collection orderby l.FaceDistance.Encoding is not null select l).ToArray(); - if (results.Any() && results[0].FaceDistance.Encoding is null) - throw new Exception("Sorting failed!"); - return results; - } - - private static FaceDistanceContainer[] GetOrderedFaceDistanceContainers(Face[] distinctFilteredFaces) - { - FaceDistanceContainer[] results; - FaceDistance faceDistance; - FaceDistanceContainer faceDistanceContainer; - List collection = new(); - foreach (Face face in distinctFilteredFaces) - { - if (face.Mapping is null) - throw new NotSupportedException(); - if (face.FaceDistance?.Encoding is not FaceRecognitionDotNet.FaceEncoding faceEncoding) - continue; - faceDistance = new(face.Mapping.MappingFromLocation.Confidence, faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromItem.MinimumDateTime, face.Mapping.MappingFromLocation.NormalizedPixelPercentage); - faceDistanceContainer = new(face, faceDistance); - collection.Add(faceDistanceContainer); - } - results = GetOrderedFaceDistanceContainers(collection); - return results; - } - - private static List GetFaceDistanceEncodings(FaceDistanceContainer[] faceDistanceContainers) - { - List faceDistanceEncodings = new(); - foreach (FaceDistanceContainer faceDistanceContainer in faceDistanceContainers) - { - if (faceDistanceContainer.FaceDistance.Encoding is null) - continue; - faceDistanceEncodings.Add(faceDistanceContainer.FaceDistance); - } - return faceDistanceEncodings; - } - - public SortingContainer[] SetFaceMappingSortingCollectionThenGetSortingContainers(int maxDegreeOfParallelism, long ticks, MapLogic mapLogic, Face[] distinctFilteredFaces, int? useFiltersCounter) - { - SortingContainer[] results; - List collection = new(); - int totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); - ParallelOptions parallelOptions = new() { MaxDegreeOfParallelism = maxDegreeOfParallelism }; - FaceDistanceContainer[] faceDistanceContainers = GetOrderedFaceDistanceContainers(distinctFilteredFaces); - List faceDistanceEncodings = GetFaceDistanceEncodings(faceDistanceContainers); - string message = $") {faceDistanceContainers.Length:000} Get Sorting Containers Then Set Face Mapping Sorting Collection - {totalSeconds} total second(s)"; - ProgressBarOptions options = new() { ProgressCharacter = '─', ProgressBarOnBottom = true, DisableBottomPercentage = true }; - using ProgressBar progressBar = new(faceDistanceContainers.Length, message, options); - _ = Parallel.For(0, faceDistanceContainers.Length, parallelOptions, (i, state) => - { - progressBar.Tick(); - Face face = faceDistanceContainers[i].Face; - if (face.Mapping is null) - throw new NotSupportedException(); - FaceDistance faceDistanceEncoding = faceDistanceContainers[i].FaceDistance; - if (mapLogic.Used(faceDistanceEncoding)) - return; - List sortingCollection = GetSortingCollection(mapLogic, faceDistanceEncodings, faceDistanceContainers.Length, i, faceDistanceEncoding); - if (!sortingCollection.Any()) - return; - List sortingContainers = GetSortingContainers(face, faceDistanceEncoding, sortingCollection, useFiltersCounter); - if (sortingContainers.Any()) - { - lock (collection) - collection.AddRange(sortingContainers); - } - }); - if (!collection.Any()) - results = Array.Empty(); - else - results = Shared.Models.Stateless.Methods.ISortingContainer.Sort(collection); - return results; - } - - public static Mapping[] GetSelectedMappingCollection(Face[] distinctFilteredFaces) - { - Mapping[] results; - IEnumerable collection = from l in distinctFilteredFaces orderby l.Mapping?.MappingFromItem.MinimumDateTime descending select l.Mapping; - results = (from l in collection where l is not null select l).ToArray(); - return results; - } - - public static void SetFaceDistances(int maxDegreeOfParallelism, long ticks, Face[] distinctFilteredFaces) - { - int totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); - ParallelOptions parallelOptions = new() { MaxDegreeOfParallelism = maxDegreeOfParallelism }; - string message = $") {distinctFilteredFaces.Length:000} Load Face Encoding - {totalSeconds} total second(s)"; - ProgressBarOptions options = new() { ProgressCharacter = '─', ProgressBarOnBottom = true, DisableBottomPercentage = true }; - using ProgressBar progressBar = new(distinctFilteredFaces.Length, message, options); - _ = Parallel.For(0, distinctFilteredFaces.Length, parallelOptions, (i, state) => - { - Face face = distinctFilteredFaces[i]; - if (face.FaceEncoding is null || face.Mapping is null) - throw new NotSupportedException(); - if (face.FaceDistance?.Encoding is not null && face.FaceDistance.Encoding is FaceRecognitionDotNet.FaceEncoding faceEncoding) - return; - progressBar.Tick(); - faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); - FaceDistance faceDistance = new(face.Mapping.MappingFromLocation.Confidence, faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromItem.MinimumDateTime, face.Mapping.MappingFromLocation.NormalizedPixelPercentage); - lock (face) - face.SetFaceDistance(faceDistance); - }); - } - - void Shared.Models.Methods.IFaceDistance.SavePossiblyNewPersonContainers(IPropertyConfiguration propertyConfiguration, string personBirthdayFormat, string facesFileNameExtension, string? a2PeopleSingletonDirectory, Dictionary personKeyToPersonContainer, List<(string[], PersonContainer)> possiblyNewPersonDisplayDirectoryNamesAndPersonContainer) - { - char @char; - string json; - string[] files; - string checkFile; - string[] segments; - const int zero = 0; - string personKeyFormatted; - string personDisplayDirectory; - PersonBirthday personBirthday; - string personDisplayDirectoryName; - string checkPersonDisplayDirectory; - string checkPersonKeyFormattedDirectory; - char[] chars = Shared.Models.Stateless.Methods.IAge.GetChars(); - JsonSerializerOptions jsonSerializerOptions = new() { WriteIndented = true }; - foreach ((string[] personDisplayDirectoryNames, PersonContainer personContainer) in possiblyNewPersonDisplayDirectoryNamesAndPersonContainer) - { - if (a2PeopleSingletonDirectory is null || personContainer.Key is null || personContainer.Birthdays is null || !personContainer.Birthdays.Any()) - continue; - personBirthday = personContainer.Birthdays[zero]; - personDisplayDirectoryName = personDisplayDirectoryNames[^1]; - personDisplayDirectory = Path.Combine(personDisplayDirectoryNames); - personKeyFormatted = Shared.Models.Stateless.Methods.IPersonBirthday.GetFormatted(personBirthdayFormat, personBirthday); - segments = personDisplayDirectoryName.Split(chars); - if (segments.Length != 2) - @char = '_'; - else - @char = personDisplayDirectoryName[segments[zero].Length]; - checkPersonDisplayDirectory = Path.Combine(a2PeopleSingletonDirectory, @char.ToString(), personDisplayDirectoryName); - checkPersonKeyFormattedDirectory = Path.Combine(checkPersonDisplayDirectory, personKeyFormatted); - if (Directory.Exists(checkPersonKeyFormattedDirectory)) - continue; - _ = Directory.CreateDirectory(checkPersonKeyFormattedDirectory); - checkFile = Path.Combine(checkPersonKeyFormattedDirectory, $"{personKeyFormatted}.json"); - json = JsonSerializer.Serialize(personContainer.Person, jsonSerializerOptions); - _ = Shared.Models.Stateless.Methods.IPath.WriteAllText(checkFile, json, updateDateWhenMatches: false, compareBeforeWrite: true); - if (!Directory.Exists(personDisplayDirectory)) - continue; - files = Directory.GetFiles(personDisplayDirectory, $"*{facesFileNameExtension}", SearchOption.TopDirectoryOnly); - foreach (string file in files) - { - checkFile = Path.Combine(checkPersonDisplayDirectory, Path.GetFileName(file)); - if (File.Exists(checkFile)) - continue; - File.Copy(files[0], checkFile); - break; - } - } } private void MoveUnableToMatch(string eDistanceContentDirectory, string mappedFaceFile, string mappedFaceFileName) @@ -428,14 +130,14 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance return result; } - private static FaceDistanceContainer[] GetOrderedFaceDistanceContainers(MappingFromItem mappingFromItem, List faces) + private static FaceDistanceContainer[] GetFaceDistanceContainers(MappingFromItem mappingFromItem, Face[] filteredFaces) { FaceDistanceContainer[] results; FaceDistance faceDistance; int normalizedPixelPercentage; FaceDistanceContainer faceDistanceContainer; List collection = new(); - foreach (Face face in faces) + foreach (Face face in filteredFaces) { if (face.FaceEncoding is null || face.Location is null || face.OutputResolution is null) throw new NotSupportedException(); @@ -446,17 +148,29 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance { faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); faceDistance = new(face.Location.Confidence, faceEncoding, mappingFromItem.Id, mappingFromItem.IsWrongYear, mappingFromItem.MinimumDateTime, normalizedPixelPercentage); - lock (faces) + lock (filteredFaces) face.SetFaceDistance(faceDistance); } faceDistanceContainer = new(face, faceDistance); collection.Add(faceDistanceContainer); } - results = GetOrderedFaceDistanceContainers(collection); + results = collection.ToArray(); return results; } - private static List<(Face Face, double? Length)> GetValues(MappingFromItem mappingFromItem, List faces, string json) + private static List GetFaceDistanceEncodings(FaceDistanceContainer[] faceDistanceContainers) + { + List faceDistanceEncodings = new(); + foreach (FaceDistanceContainer faceDistanceContainer in faceDistanceContainers) + { + if (faceDistanceContainer.FaceDistance.Encoding is null) + continue; + faceDistanceEncodings.Add(faceDistanceContainer.FaceDistance); + } + return faceDistanceEncodings; + } + + private static List<(Face Face, double? Length)> GetValues(MappingFromItem mappingFromItem, Face[] filteredFaces, string json) { List<(Face Face, double? Length)> results = new(); Face face; @@ -466,19 +180,19 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance throw new NotSupportedException(); FaceRecognitionDotNet.FaceEncoding faceRecognitionDotNetFaceEncoding = FaceRecognition.LoadFaceEncoding(modelsFaceEncoding.RawEncoding); FaceDistance faceDistanceEncoding = new(faceRecognitionDotNetFaceEncoding); - FaceDistanceContainer[] faceDistanceContainers = GetOrderedFaceDistanceContainers(mappingFromItem, faces); + FaceDistanceContainer[] faceDistanceContainers = GetFaceDistanceContainers(mappingFromItem, filteredFaces); int faceDistanceContainersLength = faceDistanceContainers.Length; - if (faceDistanceContainersLength != faces.Count) + if (faceDistanceContainersLength != filteredFaces.Length) throw new NotSupportedException(); List faceDistanceEncodings = GetFaceDistanceEncodings(faceDistanceContainers); - if (faceDistanceEncodings.Count != faces.Count) + if (faceDistanceEncodings.Count != filteredFaces.Length) throw new NotSupportedException(); List faceDistanceLengths = FaceRecognition.FaceDistances(faceDistanceEncodings, faceDistanceEncoding); if (faceDistanceLengths.Count != faceDistanceContainersLength) throw new NotSupportedException(); - for (int i = 0; i < faces.Count; i++) + for (int i = 0; i < filteredFaces.Length; i++) { - face = faces[i]; + face = filteredFaces[i]; faceDistanceLength = faceDistanceLengths[i]; if (faceDistanceLength.Length is null) throw new NotSupportedException(); @@ -487,10 +201,10 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance return results; } - private (Face, double?)[] GetClosestFaceByDistanceIgnoringTolerance(MappingFromItem mappingFromItem, List faces, string json) + private (Face, double?)[] GetClosestFaceByDistanceIgnoringTolerance(MappingFromItem mappingFromItem, Face[] filteredFaces, string json) { (Face, double?)[] results; - List<(Face Face, double? Length)> collection = GetValues(mappingFromItem, faces, json); + List<(Face Face, double? Length)> collection = GetValues(mappingFromItem, filteredFaces, json); results = (from l in collection orderby l.Length select l).Take(1).ToArray(); (Face face, double? length) = results.First(); lock (_Debug) @@ -515,7 +229,7 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance return new(x, y); } - private (Face, double?)[] GetClosestFaceByPixel(List faces, int? x1, int? y1) + private (Face, double?)[] GetClosestFaceByPixel(Face[] filteredFaces, int? x1, int? y1) { (Face, double?)[] results; int? x2; @@ -526,7 +240,7 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance List<(Face Face, double? Order)> collection = new(); if (x1 is null || y1 is null) throw new NotSupportedException(); - foreach (Face face in faces) + foreach (Face face in filteredFaces) { if (face.Location is null || face.OutputResolution is null) throw new NotSupportedException(); @@ -542,25 +256,25 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance return results; } - private (Face, double?)[] GetClosestFaceByPixel(List faces, int normalizedPixelPercentage) + private (Face, double?)[] GetClosestFaceByPixel(Face[] filteredFaces, int normalizedPixelPercentage) { - if (!faces.Any()) + if (!filteredFaces.Any()) throw new NotSupportedException(); (Face, double?)[] results; const int zero = 0; - OutputResolution? outputResolution = faces[zero].OutputResolution; + OutputResolution? outputResolution = filteredFaces[zero].OutputResolution; (int? x1, int? y1) = GetXY(normalizedPixelPercentage, outputResolution); - results = GetClosestFaceByPixel(faces, x1, y1); + results = GetClosestFaceByPixel(filteredFaces, x1, y1); return results; } - private (Face, double?)[] GetClosestFaceByPixel(List faces, string json) + private (Face, double?)[] GetClosestFaceByPixel(Face[] filteredFaces, string json) { - if (!faces.Any()) + if (!filteredFaces.Any()) throw new NotSupportedException(); (Face, double?)[] results; const int zero = 0; - OutputResolution? outputResolution = faces[zero].OutputResolution; + OutputResolution? outputResolution = filteredFaces[zero].OutputResolution; if (outputResolution is null) throw new NullReferenceException(nameof(outputResolution)); Location? location = JsonSerializer.Deserialize(json); @@ -568,15 +282,15 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance throw new NullReferenceException(nameof(location)); int normalizedPixelPercentage = Shared.Models.Stateless.Methods.ILocation.GetNormalizedPixelPercentage(location, Shared.Models.Stateless.ILocation.Digits, Shared.Models.Stateless.ILocation.Factor, outputResolution); (int? x1, int? y1) = GetXY(normalizedPixelPercentage, outputResolution); - results = GetClosestFaceByPixel(faces, x1, y1); + results = GetClosestFaceByPixel(filteredFaces, x1, y1); return results; } - private static List<(Face, double?)> GetMatchingFacesByFaceEncoding(List faces, string? json) + private static List<(Face, double?)> GetMatchingFacesByFaceEncoding(Face[] filteredFaces, string? json) { List<(Face, double?)> results = new(); string check; - foreach (Face face in faces) + foreach (Face face in filteredFaces) { if (json is null || face.FaceEncoding is null) continue; @@ -648,6 +362,9 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance FileInfo? fileInfo; string mappedFaceFileName; List<(Face, double?)> checkFaces = new(); + Face[] filteredFaces = (from l in faces where l.FaceEncoding is not null && l.Location is not null && l.OutputResolution is not null select l).ToArray(); + if (filteredFaces.Length != faces.Count) + checkFaces.Clear(); foreach ((string mappedFaceFile, int normalizedPixelPercentage) in collection) { mappedFaceFileName = Path.GetFileName(mappedFaceFile); @@ -661,7 +378,7 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance MoveUnableToMatch(eDistanceContentDirectory, mappedFaceFile, mappedFaceFileName); continue; } - checkFaces.AddRange(GetMatchingFacesByFaceEncoding(faces, json)); + checkFaces.AddRange(GetMatchingFacesByFaceEncoding(filteredFaces, json)); if (checkFaces.Count == 1) _Debug.Add(0); if (checkFaces.Count != 1 && !string.IsNullOrEmpty(json)) @@ -669,16 +386,16 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance checkFaces.Clear(); if (json is null) throw new NotSupportedException(); - checkFaces.AddRange(GetClosestFaceByDistanceIgnoringTolerance(mappingFromItem, faces, json)); + checkFaces.AddRange(GetClosestFaceByDistanceIgnoringTolerance(mappingFromItem, filteredFaces, json)); } if (checkFaces.Count != 1 && _DistancePixelDistanceTolerance > 0) { checkFaces.Clear(); json = GetFaceLocation(mappedFaceFile); if (json is not null) - checkFaces.AddRange(GetClosestFaceByPixel(faces, json)); + checkFaces.AddRange(GetClosestFaceByPixel(filteredFaces, json)); else - checkFaces.AddRange(GetClosestFaceByPixel(faces, normalizedPixelPercentage)); + checkFaces.AddRange(GetClosestFaceByPixel(filteredFaces, normalizedPixelPercentage)); throw new NotImplementedException("Without a tolerance this should not ever occur!"); } if (!checkFaces.Any()) diff --git a/Instance/DlibDotNet.cs b/Instance/DlibDotNet.cs index 8f8b0a3..85f389f 100644 --- a/Instance/DlibDotNet.cs +++ b/Instance/DlibDotNet.cs @@ -75,13 +75,7 @@ public partial class DlibDotNet configuration.DistanceMoveUnableToMatch, configuration.DistancePixelDistanceTolerance, configuration.DistanceRenameToMatch, - configuration.FaceDistanceAreaPermilleTolerance, - configuration.FaceDistanceMinimumConfidence, - configuration.FaceDistancePermyriad, - configuration.FaceDistanceTolerance, - configuration.PropertyConfiguration.ResultAllInOne, - configuration.SortingDaysDeltaTolerance, - configuration.SortingMaximumPerFaceShouldBeHigh); + configuration.FaceDistanceTolerance); if (configuration.IgnoreExtensions is null) throw new NullReferenceException(nameof(configuration.IgnoreExtensions)); string propertyRoot = Property.Models.Stateless.IResult.GetResultsGroupDirectory(propertyConfiguration, nameof(A_Property), create: false); @@ -422,7 +416,6 @@ public partial class DlibDotNet if (_AppSettings.MaxDegreeOfParallelism < 2) ticks = LogDelta(ticks, nameof(D_Face.SaveFaces)); if (item.Property?.Id is not null - && faces.Any(l => l.FaceEncoding is not null && l.Location is not null && l.OutputResolution is not null) && idToMappedFaceFilesCollection.TryGetValue(item.Property.Id.Value, out List<(string, int)>? collection)) _Distance.LookForMatchFacesAndPossiblyRename(_Faces.FileNameExtension, eDistanceContentDirectory, mappingFromItem, faces, collection); if (_Configuration.SaveFaceLandmarkForOutputResolutions.Contains(outputResolution)) @@ -924,13 +917,19 @@ public partial class DlibDotNet return results; } - private void DistanceThenMapLogic(string argZero, long ticks, PersonContainer[] personContainers, Container[] containers, string a2PeopleSingletonDirectory, string dResultsFullGroupDirectory, string d2FacePartsContentDirectory, string eDistanceContentDirectory, string outputResolution) + private void MapLogic(string argZero, long ticks, PersonContainer[] personContainers, Container[] containers, string a2PeopleSingletonDirectory, string dResultsFullGroupDirectory, string d2FacePartsContentDirectory, string eDistanceContentDirectory, string outputResolution) { int? useFiltersCounter = null; SortingContainer[] sortingContainers; string dFacesContentDirectory = Path.Combine(dResultsFullGroupDirectory, "()"); Shared.Models.Face[] distinctFilteredFaces = SetMappingThenGetDistinctFilteredFacesWithMapping(argZero, containers); - Mapping[] mappingCollection = E_Distance.GetSelectedMappingCollection(distinctFilteredFaces); + Mapping[] mappingCollection = MapLogicSupport.GetSelectedMappingCollection(distinctFilteredFaces); + MapLogicSupport mapLogicSupport = new( + _Configuration.FaceDistanceAreaPermilleTolerance, + _Configuration.FaceDistanceMinimumConfidence, + _Configuration.FaceDistancePermyriad, + _Configuration.SortingDaysDeltaTolerance, + _Configuration.SortingMaximumPerFaceShouldBeHigh); MapLogic mapLogic = new( _AppSettings.MaxDegreeOfParallelism, _Configuration.PropertyConfiguration, @@ -940,24 +939,24 @@ public partial class DlibDotNet a2PeopleSingletonDirectory, eDistanceContentDirectory, mappingCollection, - _Distance); + mapLogicSupport); Dictionary> idToNormalizedPixelPercentageToMapping = GetIdToNormalizedPixelPercentageToFace(mappingCollection); mapLogic.CopyManualFiles(dFacesContentDirectory, idToNormalizedPixelPercentageToMapping); int totalNotMapped = mapLogic.AddToMapping(mappingCollection); if (_Configuration.MappingSaveMapped) mapLogic.SaveMapped(dFacesContentDirectory, d2FacePartsContentDirectory, mappingCollection, idToNormalizedPixelPercentageToMapping, totalNotMapped); - E_Distance.SetFaceDistances(_AppSettings.MaxDegreeOfParallelism, ticks, distinctFilteredFaces); - sortingContainers = _Distance.SetFaceMappingSortingCollectionThenGetSortingContainers(_AppSettings.MaxDegreeOfParallelism, ticks, mapLogic, distinctFilteredFaces, useFiltersCounter); + MapLogicSupport.SetFaceDistances(_AppSettings.MaxDegreeOfParallelism, ticks, distinctFilteredFaces); + sortingContainers = mapLogicSupport.SetFaceMappingSortingCollectionThenGetSortingContainers(_AppSettings.MaxDegreeOfParallelism, ticks, mapLogic, distinctFilteredFaces, useFiltersCounter); if (!sortingContainers.Any()) { for (useFiltersCounter = 1; useFiltersCounter < 11; useFiltersCounter++) { - sortingContainers = _Distance.SetFaceMappingSortingCollectionThenGetSortingContainers(_AppSettings.MaxDegreeOfParallelism, ticks, mapLogic, distinctFilteredFaces, useFiltersCounter); + sortingContainers = mapLogicSupport.SetFaceMappingSortingCollectionThenGetSortingContainers(_AppSettings.MaxDegreeOfParallelism, ticks, mapLogic, distinctFilteredFaces, useFiltersCounter); if (sortingContainers.Any()) break; } } - E_Distance.SaveFaceDistances(_Configuration.PropertyConfiguration, sortingContainers); + MapLogicSupport.SaveFaceDistances(_Configuration.PropertyConfiguration, sortingContainers); if (totalNotMapped > 0) mapLogic.ForceSingleImageThenSaveSorting(dFacesContentDirectory, d2FacePartsContentDirectory, mappingCollection, idToNormalizedPixelPercentageToMapping, sortingContainers, useFiltersCounter, totalNotMapped); if (_Configuration.MappingSaveNotMapped) @@ -1090,7 +1089,7 @@ public partial class DlibDotNet { if (!_Configuration.LoadOrCreateThenSaveImageFacesResultsForOutputResolutions.Any()) break; - DistanceThenMapLogic(argZero, ticks, personContainers, containers, a2PeopleSingletonDirectory, dResultsFullGroupDirectory, d2FacePartsContentDirectory, eDistanceContentDirectory, outputResolution); + MapLogic(argZero, ticks, personContainers, containers, a2PeopleSingletonDirectory, dResultsFullGroupDirectory, d2FacePartsContentDirectory, eDistanceContentDirectory, outputResolution); if (_IsEnvironment.Development) continue; if (_FileKeyValuePairs.Any()) diff --git a/Map/Models/MapLogic.cs b/Map/Models/MapLogic.cs index 12a0dbd..21c5199 100644 --- a/Map/Models/MapLogic.cs +++ b/Map/Models/MapLogic.cs @@ -25,7 +25,7 @@ public class MapLogic private readonly Configuration? _Configuration; private readonly string _EDistanceContentTicksDirectory; - public MapLogic(int maxDegreeOfParallelism, Shared.Models.Properties.IPropertyConfiguration propertyConfiguration, Configuration? configuration, long ticks, PersonContainer[] personContainers, string a2PeopleSingletonDirectory, string eDistanceContentDirectory, Mapping[] mappingCollection, Shared.Models.Methods.IFaceDistance? faceDistance) + public MapLogic(int maxDegreeOfParallelism, Shared.Models.Properties.IPropertyConfiguration propertyConfiguration, Configuration? configuration, long ticks, PersonContainer[] personContainers, string a2PeopleSingletonDirectory, string eDistanceContentDirectory, Mapping[] mappingCollection, Shared.Models.Methods.IMapLogicSupport? faceDistance) { _Ticks = ticks; _Configuration = configuration; diff --git a/Map/Models/Stateless/MapLogic.cs b/Map/Models/Stateless/MapLogic.cs index 727061a..ad0ed7a 100644 --- a/Map/Models/Stateless/MapLogic.cs +++ b/Map/Models/Stateless/MapLogic.cs @@ -567,7 +567,7 @@ internal abstract class MapLogic } } - internal static void Set(Shared.Models.Properties.IPropertyConfiguration propertyConfiguration, Configuration? configuration, long ticks, List personContainers, string? a2PeopleContentDirectory, string eDistanceContentDirectory, Mapping[] mappingCollection, Shared.Models.Methods.IFaceDistance faceDistance, Dictionary personKeyToPersonContainer, Dictionary personKeyToRanges, List notMappedPersonContainers, Dictionary> skipCollection, Dictionary> idThenNormalizedPixelPercentageToPersonContainers) + internal static void Set(Shared.Models.Properties.IPropertyConfiguration propertyConfiguration, Configuration? configuration, long ticks, List personContainers, string? a2PeopleContentDirectory, string eDistanceContentDirectory, Mapping[] mappingCollection, Shared.Models.Methods.IMapLogicSupport faceDistance, Dictionary personKeyToPersonContainer, Dictionary personKeyToRanges, List notMappedPersonContainers, Dictionary> skipCollection, Dictionary> idThenNormalizedPixelPercentageToPersonContainers) { if (configuration is null) throw new NullReferenceException(nameof(configuration)); diff --git a/Shared/Models/Methods/IFaceDistance.cs b/Shared/Models/Methods/IMapLogicSupport.cs similarity index 92% rename from Shared/Models/Methods/IFaceDistance.cs rename to Shared/Models/Methods/IMapLogicSupport.cs index d22f8e9..aea0f54 100644 --- a/Shared/Models/Methods/IFaceDistance.cs +++ b/Shared/Models/Methods/IMapLogicSupport.cs @@ -1,6 +1,6 @@ namespace View_by_Distance.Shared.Models.Methods; -public interface IFaceDistance +public interface IMapLogicSupport { void SavePossiblyNewPersonContainers(Properties.IPropertyConfiguration propertyConfiguration, string personBirthdayFormat, string facesFileNameExtension, string? a2PeopleContentDirectory, Dictionary personKeyToPersonContainer, List<(string[], PersonContainer)> possiblyNewPersonDisplayDirectoryNamesAndPersonContainer);