LookForAbandoned,
DateTimeOriginalThenMinimumDateTime and IsNotUniqueAndNeedsReview
This commit is contained in:
		| @ -154,13 +154,14 @@ public class DateGroup | |||||||
|         string? check; |         string? check; | ||||||
|         string fileName; |         string fileName; | ||||||
|         string? pathRoot; |         string? pathRoot; | ||||||
|  |         DateTime dateTime; | ||||||
|         string seasonName; |         string seasonName; | ||||||
|         string weekOfYear; |         string weekOfYear; | ||||||
|         bool? isWrongYear; |         bool? isWrongYear; | ||||||
|         string seasonValue; |         string seasonValue; | ||||||
|         string directoryName; |         string directoryName; | ||||||
|         string topDirectoryName; |         string topDirectoryName; | ||||||
|         DateTime minimumDateTime; |         List<DateTime> dateTimes; | ||||||
|         string[]? matches = null; |         string[]? matches = null; | ||||||
|         string[] directorySegments; |         string[] directorySegments; | ||||||
|         List<string> destinationCollection; |         List<string> destinationCollection; | ||||||
| @ -204,12 +205,22 @@ public class DateGroup | |||||||
|             directoryNames.Clear(); |             directoryNames.Clear(); | ||||||
|             destinationCollection = new(); |             destinationCollection = new(); | ||||||
|             _ = destinationDirectoryName.Clear(); |             _ = destinationDirectoryName.Clear(); | ||||||
|             if (item.ImageFileHolder.LastWriteTime is not null && item.Property is null) |             if (item.Property is not null) | ||||||
|                 minimumDateTime = item.ImageFileHolder.LastWriteTime.Value; |                 dateTimes = item.Property.GetDateTimes(); | ||||||
|             else |             else | ||||||
|                 minimumDateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property); |             { | ||||||
|             day = minimumDateTime.ToString("MM-dd"); |                 if (item.ImageFileHolder.LastWriteTime is null) | ||||||
|             month = minimumDateTime.ToString("MMMM"); |                     throw new Exception(); | ||||||
|  |                 dateTimes = new() { item.ImageFileHolder.LastWriteTime.Value }; | ||||||
|  |             } | ||||||
|  |             if (item.ImageFileHolder.LastWriteTime is not null && item.Property is null) | ||||||
|  |                 dateTime = item.ImageFileHolder.LastWriteTime.Value; | ||||||
|  |             else if (item.Property is not null && item.Property.DateTimeOriginal is not null) | ||||||
|  |                 dateTime = item.Property.DateTimeOriginal.Value; | ||||||
|  |             else | ||||||
|  |                 dateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property); | ||||||
|  |             day = dateTime.ToString("MM-dd"); | ||||||
|  |             month = dateTime.ToString("MMMM"); | ||||||
|             if (item.Property?.Id is null) |             if (item.Property?.Id is null) | ||||||
|             { |             { | ||||||
|                 flag = '#'; |                 flag = '#'; | ||||||
| @ -217,26 +228,26 @@ public class DateGroup | |||||||
|             } |             } | ||||||
|             else |             else | ||||||
|             { |             { | ||||||
|                 (isWrongYear, _) = item.Property.IsWrongYear(item.ImageFileHolder, minimumDateTime); |                 (isWrongYear, _) = Shared.Models.Stateless.Methods.IProperty.IsWrongYear(item.ImageFileHolder, item.Property.DateTimeOriginal, dateTimes); | ||||||
|                 if (isWrongYear is null) |                 if (isWrongYear is null) | ||||||
|                     flag = '#'; |                     flag = '#'; | ||||||
|                 else if (isWrongYear.Value) |                 else if (isWrongYear.Value) | ||||||
|                     flag = '~'; |                     flag = '~'; | ||||||
|                 else |                 else | ||||||
|                 { |                 { | ||||||
|                     if (item.Property.DateTimeOriginal.HasValue && minimumDateTime.DayOfYear != item.Property.DateTimeOriginal.Value.DayOfYear && Math.Abs(new TimeSpan(minimumDateTime.Ticks - item.Property.DateTimeOriginal.Value.Ticks).TotalHours) > 8) |                     if (item.Property.DateTimeOriginal is not null && dateTime.DayOfYear != item.Property.DateTimeOriginal.Value.DayOfYear && Math.Abs(new TimeSpan(dateTime.Ticks - item.Property.DateTimeOriginal.Value.Ticks).TotalHours) > 8) | ||||||
|                         flag = '^'; |                         flag = '^'; | ||||||
|                     else |                     else | ||||||
|                         flag = '='; |                         flag = '='; | ||||||
|                 } |                 } | ||||||
|             } |             } | ||||||
|             (season, seasonName) = Shared.Models.Stateless.Methods.IProperty.GetSeason(minimumDateTime.DayOfYear); |             (season, seasonName) = Shared.Models.Stateless.Methods.IProperty.GetSeason(dateTime.DayOfYear); | ||||||
|             if ((from l in topDirectorySegments where l == "Christmas" select true).Any()) |             if ((from l in topDirectorySegments where l == "Christmas" select true).Any()) | ||||||
|                 seasonValue = string.Empty; |                 seasonValue = string.Empty; | ||||||
|             else |             else | ||||||
|                 seasonValue = $".{season}"; |                 seasonValue = $".{season}"; | ||||||
|             if (isWrongYear is null || !isWrongYear.Value) |             if (isWrongYear is null || !isWrongYear.Value) | ||||||
|                 year = $"{flag}{minimumDateTime:yyyy}{seasonValue}"; |                 year = $"{flag}{dateTime:yyyy}{seasonValue}"; | ||||||
|             else if (matches is null || matches.Length < 3) |             else if (matches is null || matches.Length < 3) | ||||||
|                 year = "----"; |                 year = "----"; | ||||||
|             else |             else | ||||||
| @ -247,7 +258,7 @@ public class DateGroup | |||||||
|                     year = $"{flag}{matches[0][1..].Split('.')[0]}{seasonValue}"; |                     year = $"{flag}{matches[0][1..].Split('.')[0]}{seasonValue}"; | ||||||
|             } |             } | ||||||
|             topDirectoryName = Path.GetFileName(topDirectory); |             topDirectoryName = Path.GetFileName(topDirectory); | ||||||
|             weekOfYear = calendar.GetWeekOfYear(minimumDateTime, CalendarWeekRule.FirstDay, DayOfWeek.Sunday).ToString("00"); |             weekOfYear = calendar.GetWeekOfYear(dateTime, CalendarWeekRule.FirstDay, DayOfWeek.Sunday).ToString("00"); | ||||||
|             if (_Configuration.ByHash) |             if (_Configuration.ByHash) | ||||||
|                 directoryNames.Add($"{year} {seasonName}"); |                 directoryNames.Add($"{year} {seasonName}"); | ||||||
|             else if (_Configuration.BySeason && topDirectoryName.Length == 1 && topDirectoryName[0] == '_') |             else if (_Configuration.BySeason && topDirectoryName.Length == 1 && topDirectoryName[0] == '_') | ||||||
| @ -296,9 +307,9 @@ public class DateGroup | |||||||
|             if (item.ImageFileHolder.LastWriteTime is null) |             if (item.ImageFileHolder.LastWriteTime is null) | ||||||
|                 continue; |                 continue; | ||||||
|             if (item.Property is not null) |             if (item.Property is not null) | ||||||
|                 results.Add(new(item, item.Property.LastWriteTime.Ticks, minimumDateTime.Ticks, destinationCollection.ToArray())); |                 results.Add(new(item, item.Property.LastWriteTime.Ticks, dateTime.Ticks, destinationCollection.ToArray())); | ||||||
|             else |             else | ||||||
|                 results.Add(new(item, item.ImageFileHolder.LastWriteTime.Value.Ticks, minimumDateTime.Ticks, destinationCollection.ToArray())); |                 results.Add(new(item, item.ImageFileHolder.LastWriteTime.Value.Ticks, dateTime.Ticks, destinationCollection.ToArray())); | ||||||
|         } |         } | ||||||
|         return results; |         return results; | ||||||
|     } |     } | ||||||
| @ -470,11 +481,11 @@ public class DateGroup | |||||||
|         string path; |         string path; | ||||||
|         string fileName; |         string fileName; | ||||||
|         string directory; |         string directory; | ||||||
|  |         DateTime dateTime; | ||||||
|         int selectedTotal; |         int selectedTotal; | ||||||
|         const int minimum = 3; |         const int minimum = 3; | ||||||
|         List<DateTime> dateTimes; |         List<DateTime> dateTimes; | ||||||
|         List<Item> selectedItems; |         List<Item> selectedItems; | ||||||
|         DateTime? minimumDateTime; |  | ||||||
|         const int maximumHours = 24; |         const int maximumHours = 24; | ||||||
|         string? relativePathDirectory; |         string? relativePathDirectory; | ||||||
|         WindowsShortcut windowsShortcut; |         WindowsShortcut windowsShortcut; | ||||||
| @ -499,9 +510,12 @@ public class DateGroup | |||||||
|                     relativePathDirectory = Path.GetDirectoryName(item.RelativePath); |                     relativePathDirectory = Path.GetDirectoryName(item.RelativePath); | ||||||
|                     if (string.IsNullOrEmpty(relativePathDirectory)) |                     if (string.IsNullOrEmpty(relativePathDirectory)) | ||||||
|                         continue; |                         continue; | ||||||
|                     minimumDateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property); |                     if (item.ImageFileHolder.LastWriteTime is not null && item.Property is null) | ||||||
|                     if (minimumDateTime is null) |                         dateTime = item.ImageFileHolder.LastWriteTime.Value; | ||||||
|                         continue; |                     else if (item.Property is not null && item.Property.DateTimeOriginal is not null) | ||||||
|  |                         dateTime = item.Property.DateTimeOriginal.Value; | ||||||
|  |                     else | ||||||
|  |                         dateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property); | ||||||
|                     path = Path.GetFullPath($"{configuration.RootDirectory}{item.RelativePath[..^5]}"); |                     path = Path.GetFullPath($"{configuration.RootDirectory}{item.RelativePath[..^5]}"); | ||||||
|                     directory = Path.Combine($"{aPropertyContentDirectory}{relativePathDirectory}", $"{dateTimes.Min():yyyy-MM-dd_HH-mm-ss}---{dateTimes.Max():yyyy-MM-dd_HH-mm-ss}"); |                     directory = Path.Combine($"{aPropertyContentDirectory}{relativePathDirectory}", $"{dateTimes.Min():yyyy-MM-dd_HH-mm-ss}---{dateTimes.Max():yyyy-MM-dd_HH-mm-ss}"); | ||||||
|                     if (!Directory.Exists(directory)) |                     if (!Directory.Exists(directory)) | ||||||
| @ -514,7 +528,7 @@ public class DateGroup | |||||||
|                     windowsShortcut.Dispose(); |                     windowsShortcut.Dispose(); | ||||||
|                     if (!File.Exists(fileName)) |                     if (!File.Exists(fileName)) | ||||||
|                         continue; |                         continue; | ||||||
|                     File.SetLastWriteTime(fileName, minimumDateTime.Value); |                     File.SetLastWriteTime(fileName, dateTime); | ||||||
|                 } |                 } | ||||||
|             } |             } | ||||||
|             if (selectedTotal < container.Items.Count && selectedTotal < (from l in container.Items where l.Property is not null select true).Count()) |             if (selectedTotal < container.Items.Count && selectedTotal < (from l in container.Items where l.Property is not null select true).Count()) | ||||||
|  | |||||||
| @ -1,353 +1,25 @@ | |||||||
| { | { | ||||||
|   "Company": "Mike Phares", |  | ||||||
|   "Linux": {}, |  | ||||||
|   "Logging": { |   "Logging": { | ||||||
|     "LogLevel": { |     "LogLevel": { | ||||||
|       "Default": "Information", |       "Log4netProvider": "Debug" | ||||||
|       "Microsoft": "Warning", |  | ||||||
|       "Log4netProvider": "Debug", |  | ||||||
|       "Microsoft.Hosting.Lifetime": "Information" |  | ||||||
|     } |     } | ||||||
|   }, |   }, | ||||||
|   "MaxDegreeOfParallelism": 6, |   "MaxDegreeOfParallelism": 6, | ||||||
|   "Serilog": { |   "Serilog": { | ||||||
|     "Using": [ |     "MinimumLevel": "Debug" | ||||||
|       "Serilog.Sinks.Console", |  | ||||||
|       "Serilog.Sinks.File" |  | ||||||
|     ], |  | ||||||
|     "MinimumLevel": "Debug", |  | ||||||
|     "WriteTo": [ |  | ||||||
|       { |  | ||||||
|         "Name": "Debug", |  | ||||||
|         "Args": { |  | ||||||
|           "outputTemplate": "{Timestamp:yyyy-MM-dd HH:mm:ss.fff zzz} [{Level}] ({SourceContext}.{MethodName}) ({InstanceId}) ({RemoteIpAddress}) {Message}{NewLine}{Exception}" |  | ||||||
|         } |  | ||||||
|       }, |  | ||||||
|       { |  | ||||||
|         "Name": "Console", |  | ||||||
|         "Args": { |  | ||||||
|           "outputTemplate": "{Timestamp:yyyy-MM-dd HH:mm:ss.fff zzz} [{Level}] ({SourceContext}.{MethodName}) ({InstanceId}) ({RemoteIpAddress}) {Message}{NewLine}{Exception}" |  | ||||||
|         } |  | ||||||
|       }, |  | ||||||
|       { |  | ||||||
|         "Name": "File", |  | ||||||
|         "Args": { |  | ||||||
|           "path": "%workingDirectory% - Log/log-.txt", |  | ||||||
|           "outputTemplate": "{Timestamp:yyyy-MM-dd HH:mm:ss.fff zzz} [{Level}] ({SourceContext}.{MethodName}) ({InstanceId}) ({RemoteIpAddress}) {Message}{NewLine}{Exception}", |  | ||||||
|           "rollingInterval": "Hour" |  | ||||||
|         } |  | ||||||
|       } |  | ||||||
|     ], |  | ||||||
|     "Enrich": [ |  | ||||||
|       "FromLogContext", |  | ||||||
|       "WithMachineName", |  | ||||||
|       "WithThreadId" |  | ||||||
|     ], |  | ||||||
|     "Properties": { |  | ||||||
|       "Application": "Sample" |  | ||||||
|     } |  | ||||||
|   }, |   }, | ||||||
|   "WorkingDirectoryName": "PharesApps", |  | ||||||
|   "Windows": { |   "Windows": { | ||||||
|     "Configuration": { |     "Configuration": { | ||||||
|       "ByCreateDateShortcut": false, |       "xByHash": false, | ||||||
|       "ByDay": false, |       "ByHash": true, | ||||||
|       "ByHash": false, |       "xPopulatePropertyId": false, | ||||||
|       "BySeason": true, |       "PopulatePropertyId": true, | ||||||
|       "ByWeek": false, |  | ||||||
|       "DateGroup": "1e85c0ba", |  | ||||||
|       "FileNameDirectorySeparator": ".Z.", |  | ||||||
|       "ForcePropertyLastWriteTimeToCreationTime": false, |  | ||||||
|       "KeepFullPath": false, |  | ||||||
|       "MaxImagesInDirectoryForTopLevelFirstPass": 10, |  | ||||||
|       "Pattern": "[^ABCDEFGHIJKLMNOPQRSTUVWXYZbcdfghjklmnpqrstvwxyz0-9]", |  | ||||||
|       "PopulatePropertyId": false, |  | ||||||
|       "PropertiesChangedForProperty": false, |  | ||||||
|       "ResultAllInOne": "_ _ _", |  | ||||||
|       "ResultCollection": "[]", |  | ||||||
|       "ResultContent": "()", |  | ||||||
|       "ResultSingleton": "{}", |  | ||||||
|       "xRootDirectory": "C:/Tmp/phares/Pictures", |       "xRootDirectory": "C:/Tmp/phares/Pictures", | ||||||
|       "xxRootDirectory": "C:/Tmp/Phares/Compare/Images-1e85c0ba", |       "xxRootDirectory": "C:/Tmp/Phares/Compare/Images-1e85c0ba", | ||||||
|       "xxxRootDirectory": "F:/Tmp/Phares/Compare/Not-Copy-Copy-1e85c0ba", |       "xxxRootDirectory": "F:/Tmp/Phares/Compare/Not-Copy-Copy-1e85c0ba", | ||||||
|       "xxxxRootDirectory": "C:/Tmp/Phares/Compare/Not-Copy-Copy-1e85c0ba", |       "xxxxRootDirectory": "C:/Tmp/Phares/Compare/Not-Copy-Copy-1e85c0ba", | ||||||
|       "xxxxxRootDirectory": "F:/Tmp/Phares/2022-11-03-DCIM/DCIM/100D3400 2022", |       "xxxxxRootDirectory": "F:/Tmp/Phares/2022-11-03-DCIM/DCIM/100D3400 2022", | ||||||
|       "xxxxxxRootDirectory": "E:/- - - Videos/-", |       "RootDirectory": "D:/1) Images A/Images-1e85c0ba/zzz Mackenzie Laptop !9/_" | ||||||
|       "RootDirectory": "D:/2) Images B/Not-Copy-Copy/New folder/-", |  | ||||||
|       "WriteBitmapDataBytes": false, |  | ||||||
|       "IgnoreExtensions": [ |  | ||||||
|         ".gif", |  | ||||||
|         ".GIF", |  | ||||||
|         ".pdf", |  | ||||||
|         ".PDF" |  | ||||||
|       ], |  | ||||||
|       "PropertyContentCollectionFiles": [], |  | ||||||
|       "ValidImageFormatExtensions": [ |  | ||||||
|         ".bmp", |  | ||||||
|         ".BMP", |  | ||||||
|         ".gif", |  | ||||||
|         ".GIF", |  | ||||||
|         ".jpeg", |  | ||||||
|         ".JPEG", |  | ||||||
|         ".jpg", |  | ||||||
|         ".JPG", |  | ||||||
|         ".png", |  | ||||||
|         ".PNG", |  | ||||||
|         ".tiff", |  | ||||||
|         ".TIFF" |  | ||||||
|       ], |  | ||||||
|       "ValidMetadataExtensions": [ |  | ||||||
|         ".3gp", |  | ||||||
|         ".3GP", |  | ||||||
|         ".avi", |  | ||||||
|         ".AVI", |  | ||||||
|         ".bmp", |  | ||||||
|         ".BMP", |  | ||||||
|         ".gif", |  | ||||||
|         ".GIF", |  | ||||||
|         ".ico", |  | ||||||
|         ".ICO", |  | ||||||
|         ".jpeg", |  | ||||||
|         ".JPEG", |  | ||||||
|         ".jpg", |  | ||||||
|         ".JPG", |  | ||||||
|         ".m4v", |  | ||||||
|         ".M4V", |  | ||||||
|         ".mov", |  | ||||||
|         ".MOV", |  | ||||||
|         ".mp4", |  | ||||||
|         ".MP4", |  | ||||||
|         ".mta", |  | ||||||
|         ".MTA", |  | ||||||
|         ".png", |  | ||||||
|         ".PNG", |  | ||||||
|         ".tiff", |  | ||||||
|         ".TIFF" |  | ||||||
|       ], |  | ||||||
|       "VerifyToSeason": [ |  | ||||||
|         ". 2000", |  | ||||||
|         ". 2001", |  | ||||||
|         ". 2002", |  | ||||||
|         ". 2003", |  | ||||||
|         ". 2004", |  | ||||||
|         ". 2005", |  | ||||||
|         ". 2006", |  | ||||||
|         ". 2007", |  | ||||||
|         ". 2008", |  | ||||||
|         ". 2009", |  | ||||||
|         ". 2010", |  | ||||||
|         ". 2011", |  | ||||||
|         ". 2012", |  | ||||||
|         ". 2013", |  | ||||||
|         ". 2014", |  | ||||||
|         ". 2015", |  | ||||||
|         ". 2016", |  | ||||||
|         ". 2017", |  | ||||||
|         ". 2018", |  | ||||||
|         ". 2019", |  | ||||||
|         ". 2020", |  | ||||||
|         ". 2021", |  | ||||||
|         ". 2022", |  | ||||||
|         ". 2023", |  | ||||||
|         ". 2024", |  | ||||||
|         ". 2025", |  | ||||||
|         ". 2026", |  | ||||||
|         ". 2027", |  | ||||||
|         ". 2028", |  | ||||||
|         ". 2029", |  | ||||||
|         "2000.0 Winter", |  | ||||||
|         "2002.1 Spring", |  | ||||||
|         "2002.4 Winter", |  | ||||||
|         "2003.0 Winter", |  | ||||||
|         "2003.1 Spring", |  | ||||||
|         "2003.3 Fall", |  | ||||||
|         "2003.4 Winter", |  | ||||||
|         "2004.0 Winter", |  | ||||||
|         "2005.1 Spring", |  | ||||||
|         "2005.2 Summer", |  | ||||||
|         "2005.3 Fall", |  | ||||||
|         "2005.4 Winter", |  | ||||||
|         "2006.0 Winter", |  | ||||||
|         "2006.1 Spring", |  | ||||||
|         "2006.3 Fall", |  | ||||||
|         "2007.0 Winter", |  | ||||||
|         "2007.2 Summer Logan Michael", |  | ||||||
|         "2007.2 Summer", |  | ||||||
|         "2007.3 Fall Logan Michael", |  | ||||||
|         "2007.4 Winter Logan Michael", |  | ||||||
|         "2008.0 Winter Logan Michael", |  | ||||||
|         "2008.1 Spring Logan Michael", |  | ||||||
|         "2008.2 Summer Logan Michael", |  | ||||||
|         "2008.2 Summer", |  | ||||||
|         "2008.3 Fall Logan Michael", |  | ||||||
|         "2009.0 Winter Logan Michael", |  | ||||||
|         "2009.0 Winter", |  | ||||||
|         "2009.1 Spring Logan Michael", |  | ||||||
|         "2009.1 Spring", |  | ||||||
|         "2009.2 Summer Logan Michael", |  | ||||||
|         "2009.2 Summer", |  | ||||||
|         "2009.3 Fall Logan Michael", |  | ||||||
|         "2009.3 Fall", |  | ||||||
|         "2009.4 Winter Logan Michael", |  | ||||||
|         "2009.4 Winter", |  | ||||||
|         "2010.0 Winter Logan Michael", |  | ||||||
|         "2010.0 Winter", |  | ||||||
|         "2010.1 Spring Logan Michael", |  | ||||||
|         "2010.1 Spring", |  | ||||||
|         "2010.2 Summer", |  | ||||||
|         "2010.3 Fall Logan Michael", |  | ||||||
|         "2010.3 Fall", |  | ||||||
|         "2010.4 Winter", |  | ||||||
|         "2011.0 Winter", |  | ||||||
|         "2011.1 Spring", |  | ||||||
|         "2011.2 Summer", |  | ||||||
|         "2011.3 Fall", |  | ||||||
|         "2011.4 Winter", |  | ||||||
|         "2012.0 Winter Chelsea 2012", |  | ||||||
|         "2012.0 Winter Chelsea", |  | ||||||
|         "2012.0 Winter", |  | ||||||
|         "2012.1 Spring Chelsea", |  | ||||||
|         "2012.1 Spring", |  | ||||||
|         "2012.2 Summer Chelsea", |  | ||||||
|         "2012.2 Summer", |  | ||||||
|         "2012.3 Fall Chelsea", |  | ||||||
|         "2012.3 Fall", |  | ||||||
|         "2012.4 Winter Chelsea", |  | ||||||
|         "2012.4 Winter", |  | ||||||
|         "2013.0 Winter Chelsea 2013", |  | ||||||
|         "2013.0 Winter Chelsea", |  | ||||||
|         "2013.0 Winter", |  | ||||||
|         "2013.1 Spring", |  | ||||||
|         "2013.2 Summer Chelsea", |  | ||||||
|         "2013.2 Summer", |  | ||||||
|         "2013.3 Fall Chelsea", |  | ||||||
|         "2013.3 Fall", |  | ||||||
|         "2013.4 Winter", |  | ||||||
|         "2014.0 Winter", |  | ||||||
|         "2014.1 Spring", |  | ||||||
|         "2014.2 Summer", |  | ||||||
|         "2014.3 Fall", |  | ||||||
|         "2014.4 Winter", |  | ||||||
|         "2015.0 Winter", |  | ||||||
|         "2015.1 Spring", |  | ||||||
|         "2015.2 Summer", |  | ||||||
|         "2015.3 Fall", |  | ||||||
|         "2015.4 Winter", |  | ||||||
|         "2016.0 Winter", |  | ||||||
|         "2016.1 Spring", |  | ||||||
|         "2016.2 Summer", |  | ||||||
|         "2016.3 Fall", |  | ||||||
|         "2016.4 Winter", |  | ||||||
|         "2017.1 Spring", |  | ||||||
|         "2017.2 Summer", |  | ||||||
|         "2017.3 Fall", |  | ||||||
|         "2017.4 Winter", |  | ||||||
|         "2018.0 Winter", |  | ||||||
|         "2018.1 Spring", |  | ||||||
|         "2018.3 Fall", |  | ||||||
|         "2018.4 Winter", |  | ||||||
|         "2019.0 Winter", |  | ||||||
|         "2019.1 Spring", |  | ||||||
|         "2019.2 Summer", |  | ||||||
|         "2019.3 Fall", |  | ||||||
|         "2019.4 Winter", |  | ||||||
|         "2020.0 Winter", |  | ||||||
|         "2020.1 Spring", |  | ||||||
|         "2020.2 Summer", |  | ||||||
|         "2020.3 Fall", |  | ||||||
|         "2020.4 Winter", |  | ||||||
|         "2021.1 Spring", |  | ||||||
|         "2021.2 Summer", |  | ||||||
|         "2021.3 Fall", |  | ||||||
|         "2021.4 Winter", |  | ||||||
|         "2022.0 Winter", |  | ||||||
|         "2022.1 Spring", |  | ||||||
|         "Anthem 2015", |  | ||||||
|         "April 2010", |  | ||||||
|         "April 2013", |  | ||||||
|         "December 2006", |  | ||||||
|         "December 2010", |  | ||||||
|         "Fall 2005", |  | ||||||
|         "Fall 2015", |  | ||||||
|         "Fall 2016", |  | ||||||
|         "Fall 2017", |  | ||||||
|         "Fall 2018", |  | ||||||
|         "Fall 2019", |  | ||||||
|         "Fall 2020", |  | ||||||
|         "Fall 2021", |  | ||||||
|         "February 2010", |  | ||||||
|         "January 2015", |  | ||||||
|         "July 2010", |  | ||||||
|         "June 2010", |  | ||||||
|         "Kids 2005", |  | ||||||
|         "March 2013", |  | ||||||
|         "May 2010", |  | ||||||
|         "May 2011", |  | ||||||
|         "May 2013", |  | ||||||
|         "October 2005", |  | ||||||
|         "October 2014", |  | ||||||
|         "Spring 2013", |  | ||||||
|         "Spring 2014", |  | ||||||
|         "Spring 2016", |  | ||||||
|         "Spring 2018", |  | ||||||
|         "Spring 2019", |  | ||||||
|         "Spring 2020", |  | ||||||
|         "Summer 2011", |  | ||||||
|         "Summer 2012", |  | ||||||
|         "Summer 2013", |  | ||||||
|         "Summer 2014", |  | ||||||
|         "Summer 2015", |  | ||||||
|         "Summer 2016", |  | ||||||
|         "Summer 2017", |  | ||||||
|         "Summer 2018", |  | ||||||
|         "Summer 2020", |  | ||||||
|         "Summer 2021", |  | ||||||
|         "Winter 2015", |  | ||||||
|         "Winter 2016", |  | ||||||
|         "Winter 2017", |  | ||||||
|         "Winter 2018", |  | ||||||
|         "Winter 2019-2020", |  | ||||||
|         "Winter 2020", |  | ||||||
|         "zzz 2005.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2005.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2005.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2005.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2005.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2006.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2007.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2007.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2008.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2008.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2009.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2009.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2009.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2009.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2010.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2010.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2010.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2010.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2011.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2011.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2011.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2011.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2011.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2012.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2012.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2012.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2012.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2012.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2013.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2013.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2013.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2013.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2013.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2014.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2014.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2014.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2014.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2014.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2015.0 Winter Tracy Pictures" |  | ||||||
|       ] |  | ||||||
|     } |     } | ||||||
|   } |   } | ||||||
| } | } | ||||||
| @ -67,10 +67,7 @@ | |||||||
|       "ResultCollection": "[]", |       "ResultCollection": "[]", | ||||||
|       "ResultContent": "()", |       "ResultContent": "()", | ||||||
|       "ResultSingleton": "{}", |       "ResultSingleton": "{}", | ||||||
|       "xRootDirectory": "C:/Tmp/phares/Pictures", |       "RootDirectory": "C:/Tmp/phares/Pictures", | ||||||
|       "xxRootDirectory": "C:/Tmp/Phares/Compare/Images-1e85c0ba", |  | ||||||
|       "RootDirectory": "F:/Tmp/Phares/Compare/Not-Copy-Copy-1e85c0ba", |  | ||||||
|       "xxxxRootDirectory": "F:/Tmp/Phares/2022-11-03-DCIM/DCIM/100D3400 2022", |  | ||||||
|       "WriteBitmapDataBytes": false, |       "WriteBitmapDataBytes": false, | ||||||
|       "IgnoreExtensions": [ |       "IgnoreExtensions": [ | ||||||
|         ".gif", |         ".gif", | ||||||
|  | |||||||
| @ -58,11 +58,11 @@ public partial class E_Distance | |||||||
|             confidencePercent = Shared.Models.Stateless.Methods.ILocation.GetConfidencePercent(_FaceConfidencePercent, _RangeFaceConfidence, face.Location.Confidence); |             confidencePercent = Shared.Models.Stateless.Methods.ILocation.GetConfidencePercent(_FaceConfidencePercent, _RangeFaceConfidence, face.Location.Confidence); | ||||||
|             normalizedRectangle = Shared.Models.Stateless.Methods.ILocation.GetNormalizedRectangle(face.Location, Shared.Models.Stateless.ILocation.Digits, face.OutputResolution); |             normalizedRectangle = Shared.Models.Stateless.Methods.ILocation.GetNormalizedRectangle(face.Location, Shared.Models.Stateless.ILocation.Digits, face.OutputResolution); | ||||||
|             if (face.FaceDistance?.Encoding is not null && face.FaceDistance.Encoding is FaceRecognitionDotNet.FaceEncoding faceEncoding) |             if (face.FaceDistance?.Encoding is not null && face.FaceDistance.Encoding is FaceRecognitionDotNet.FaceEncoding faceEncoding) | ||||||
|                 faceDistance = new(confidencePercent, faceEncoding, mappingFromItem.Id, mappingFromItem.IsWrongYear, mappingFromItem.MinimumDateTime, normalizedRectangle); |                 faceDistance = new(confidencePercent, mappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), faceEncoding, mappingFromItem.Id, mappingFromItem.IsWrongYear, normalizedRectangle); | ||||||
|             else |             else | ||||||
|             { |             { | ||||||
|                 faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); |                 faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); | ||||||
|                 faceDistance = new(confidencePercent, faceEncoding, mappingFromItem.Id, mappingFromItem.IsWrongYear, mappingFromItem.MinimumDateTime, normalizedRectangle); |                 faceDistance = new(confidencePercent, mappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), faceEncoding, mappingFromItem.Id, mappingFromItem.IsWrongYear, normalizedRectangle); | ||||||
|                 lock (intersectFaces) |                 lock (intersectFaces) | ||||||
|                     face.SetFaceDistance(faceDistance); |                     face.SetFaceDistance(faceDistance); | ||||||
|             } |             } | ||||||
| @ -347,11 +347,11 @@ public partial class E_Distance | |||||||
|                 confidencePercent = Shared.Models.Stateless.Methods.ILocation.GetConfidencePercent(_FaceConfidencePercent, _RangeFaceConfidence, face.Location.Confidence); |                 confidencePercent = Shared.Models.Stateless.Methods.ILocation.GetConfidencePercent(_FaceConfidencePercent, _RangeFaceConfidence, face.Location.Confidence); | ||||||
|                 normalizedRectangle = Shared.Models.Stateless.Methods.ILocation.GetNormalizedRectangle(face.Location, Shared.Models.Stateless.ILocation.Digits, face.OutputResolution); |                 normalizedRectangle = Shared.Models.Stateless.Methods.ILocation.GetNormalizedRectangle(face.Location, Shared.Models.Stateless.ILocation.Digits, face.OutputResolution); | ||||||
|                 if (face.FaceDistance?.Encoding is not null && face.FaceDistance.Encoding is FaceRecognitionDotNet.FaceEncoding faceEncoding) |                 if (face.FaceDistance?.Encoding is not null && face.FaceDistance.Encoding is FaceRecognitionDotNet.FaceEncoding faceEncoding) | ||||||
|                     faceDistance = new(confidencePercent, faceEncoding, id, isWrongYear, face.DateTime, normalizedRectangle); |                     faceDistance = new(confidencePercent, face.DateTime, faceEncoding, id, isWrongYear, normalizedRectangle); | ||||||
|                 else |                 else | ||||||
|                 { |                 { | ||||||
|                     faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); |                     faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); | ||||||
|                     faceDistance = new(confidencePercent, faceEncoding, id, isWrongYear, face.DateTime, normalizedRectangle); |                     faceDistance = new(confidencePercent, face.DateTime, faceEncoding, id, isWrongYear, normalizedRectangle); | ||||||
|                     face.SetFaceDistance(faceDistance); |                     face.SetFaceDistance(faceDistance); | ||||||
|                 } |                 } | ||||||
|                 faceDistanceContainer = new(face, faceDistance); |                 faceDistanceContainer = new(face, faceDistance); | ||||||
| @ -390,7 +390,7 @@ public partial class E_Distance | |||||||
|                 return; |                 return; | ||||||
|             progressBar.Tick(); |             progressBar.Tick(); | ||||||
|             faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); |             faceEncoding = FaceRecognition.LoadFaceEncoding(face.FaceEncoding.RawEncoding); | ||||||
|             FaceDistance faceDistance = new(face.Mapping.MappingFromLocation.ConfidencePercent, faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromItem.MinimumDateTime, face.Mapping.MappingFromLocation.NormalizedRectangle); |             FaceDistance faceDistance = new(face.Mapping.MappingFromLocation.ConfidencePercent, face.Mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromLocation.NormalizedRectangle); | ||||||
|             lock (face) |             lock (face) | ||||||
|                 face.SetFaceDistance(faceDistance); |                 face.SetFaceDistance(faceDistance); | ||||||
|         }); |         }); | ||||||
| @ -447,7 +447,7 @@ public partial class E_Distance | |||||||
|                 throw new NotSupportedException(); |                 throw new NotSupportedException(); | ||||||
|             if (face.FaceDistance?.Encoding is not FaceRecognitionDotNet.FaceEncoding faceEncoding) |             if (face.FaceDistance?.Encoding is not FaceRecognitionDotNet.FaceEncoding faceEncoding) | ||||||
|                 continue; |                 continue; | ||||||
|             faceDistance = new(face.Mapping.MappingFromLocation.ConfidencePercent, faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromItem.MinimumDateTime, face.Mapping.MappingFromLocation.NormalizedRectangle); |             faceDistance = new(face.Mapping.MappingFromLocation.ConfidencePercent, face.Mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), faceEncoding, face.Mapping.MappingFromItem.Id, face.Mapping.MappingFromItem.IsWrongYear, face.Mapping.MappingFromLocation.NormalizedRectangle); | ||||||
|             faceDistanceContainer = new(face, faceDistance); |             faceDistanceContainer = new(face, faceDistance); | ||||||
|             collection.Add(faceDistanceContainer); |             collection.Add(faceDistanceContainer); | ||||||
|         } |         } | ||||||
| @ -480,7 +480,7 @@ public partial class E_Distance | |||||||
|         { |         { | ||||||
|             if (faceDistanceContainer.FaceDistance is null || faceDistanceContainer.Face.Mapping?.MappingFromLocation is null) |             if (faceDistanceContainer.FaceDistance is null || faceDistanceContainer.Face.Mapping?.MappingFromLocation is null) | ||||||
|                 throw new NotSupportedException(); |                 throw new NotSupportedException(); | ||||||
|             if (skipOlderThan is not null && (faceDistanceContainer.FaceDistance.MinimumDateTime is null || faceDistanceContainer.FaceDistance.MinimumDateTime.Value.Ticks < skipOlderThan.Value)) |             if (skipOlderThan is not null && faceDistanceContainer.FaceDistance.DateTimeOriginalThenMinimumDateTime.Ticks < skipOlderThan.Value) | ||||||
|                 continue; |                 continue; | ||||||
|             if (faceDistanceContainer.Face.Mapping.MappingFromLocation.ConfidencePercent < distanceLimits.FaceConfidencePercent) |             if (faceDistanceContainer.Face.Mapping.MappingFromLocation.ConfidencePercent < distanceLimits.FaceConfidencePercent) | ||||||
|                 continue; |                 continue; | ||||||
|  | |||||||
| @ -37,6 +37,7 @@ | |||||||
|     <PackageReference Include="WindowsShortcutFactory" Version="1.1.0" /> |     <PackageReference Include="WindowsShortcutFactory" Version="1.1.0" /> | ||||||
|   </ItemGroup> |   </ItemGroup> | ||||||
|   <ItemGroup> |   <ItemGroup> | ||||||
|  |     <ProjectReference Include="..\Property\Property.csproj" /> | ||||||
|     <ProjectReference Include="..\Shared\View-by-Distance.Shared.csproj" /> |     <ProjectReference Include="..\Shared\View-by-Distance.Shared.csproj" /> | ||||||
|   </ItemGroup> |   </ItemGroup> | ||||||
|   <ItemGroup> |   <ItemGroup> | ||||||
|  | |||||||
| @ -2,9 +2,11 @@ using Microsoft.Extensions.Configuration; | |||||||
| using Phares.Shared; | using Phares.Shared; | ||||||
| using Serilog; | using Serilog; | ||||||
| using System.Diagnostics; | using System.Diagnostics; | ||||||
|  | using System.Drawing.Imaging; | ||||||
| using System.Reflection; | using System.Reflection; | ||||||
| using System.Text.Json; | using System.Text.Json; | ||||||
| using View_by_Distance.Drag_Drop_Explorer.Models; | using View_by_Distance.Drag_Drop_Explorer.Models; | ||||||
|  | using View_by_Distance.Shared.Models.Stateless; | ||||||
| using View_by_Distance.Shared.Models.Stateless.Methods; | using View_by_Distance.Shared.Models.Stateless.Methods; | ||||||
| using WindowsShortcutFactory; | using WindowsShortcutFactory; | ||||||
|  |  | ||||||
| @ -64,7 +66,7 @@ public partial class DragDropMove : Form | |||||||
|         Controls.Add(_FirstTextBox); |         Controls.Add(_FirstTextBox); | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     void Form1_Load(object? sender, EventArgs e) |     private void Form1_Load(object? sender, EventArgs e) | ||||||
|     { |     { | ||||||
|         try |         try | ||||||
|         { |         { | ||||||
| @ -73,6 +75,8 @@ public partial class DragDropMove : Form | |||||||
|             DragEnter += new DragEventHandler(Form1_DragEnter); |             DragEnter += new DragEventHandler(Form1_DragEnter); | ||||||
|             _FirstTextBox.LostFocus += new EventHandler(TextBox_LostFocus); |             _FirstTextBox.LostFocus += new EventHandler(TextBox_LostFocus); | ||||||
|             _PathTextBox.LostFocus += new EventHandler(TextBox_LostFocus); |             _PathTextBox.LostFocus += new EventHandler(TextBox_LostFocus); | ||||||
|  |             if (_WorkingDirectory is null) | ||||||
|  |             { } | ||||||
|         } |         } | ||||||
|         catch (Exception) |         catch (Exception) | ||||||
|         { |         { | ||||||
| @ -86,14 +90,14 @@ public partial class DragDropMove : Form | |||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     void TextBox_LostFocus(object? sender, EventArgs e) |     private void TextBox_LostFocus(object? sender, EventArgs e) | ||||||
|     { |     { | ||||||
|         try |         try | ||||||
|         { |         { | ||||||
|             if (sender is TextBox textBox) |             if (sender is TextBox textBox) | ||||||
|             { |             { | ||||||
|                 textBox.Text = GetConverted(textBox.Text); |                 textBox.Text = GetConverted(textBox.Text); | ||||||
|                 if (textBox.Text == "ps") |                 if (textBox.Text == "315360000000000") | ||||||
|                     throw new NotImplementedException(); |                     throw new NotImplementedException(); | ||||||
|  |  | ||||||
|             } |             } | ||||||
| @ -104,7 +108,7 @@ public partial class DragDropMove : Form | |||||||
|         } |         } | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     void Form1_DragEnter(object? sender, DragEventArgs e) |     private void Form1_DragEnter(object? sender, DragEventArgs e) | ||||||
|     { |     { | ||||||
|         try |         try | ||||||
|         { |         { | ||||||
| @ -172,12 +176,145 @@ public partial class DragDropMove : Form | |||||||
|         } |         } | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     void Form1_DragDrop(object? sender, DragEventArgs e) |     public static byte[] GetBytes(string value) | ||||||
|  |     { | ||||||
|  |         byte[] results = new byte[value.Length + 1]; | ||||||
|  |         for (int i = 0; i < value.Length; i++) | ||||||
|  |             results[i] = (byte)value[i]; | ||||||
|  |         results[value.Length] = 0x00; | ||||||
|  |         return results; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     private static PropertyItem GetPropertyItem(ConstructorInfo constructorInfo, int id, string value) | ||||||
|  |     { | ||||||
|  |         PropertyItem result = (PropertyItem)constructorInfo.Invoke(null); | ||||||
|  |         byte[] bytes = GetBytes(value); | ||||||
|  |         result.Id = id; | ||||||
|  |         result.Len = value.Length + 1; | ||||||
|  |         result.Type = 2; | ||||||
|  |         result.Value = bytes; | ||||||
|  |         return result; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     private static List<(string, int, DateTime)> GetCollection(string checkDirectory, DateTime minimumDateTime, DateTime maximumDateTime, long ticks) | ||||||
|  |     { | ||||||
|  |         List<(string, int, DateTime)> results = new(); | ||||||
|  |         DateTime dateTime; | ||||||
|  |         Shared.Models.Property property; | ||||||
|  |         string[] files = Directory.GetFiles(checkDirectory, "*", SearchOption.TopDirectoryOnly); | ||||||
|  |         foreach (string file in files) | ||||||
|  |         { | ||||||
|  |             property = Property.Models.A_Property.GetImageProperty(file); | ||||||
|  |             if (property.Id is null || property.DateTimeOriginal is null) | ||||||
|  |                 continue; | ||||||
|  |             dateTime = property.DateTimeOriginal.Value.AddTicks(ticks); | ||||||
|  |             if (dateTime < minimumDateTime) | ||||||
|  |                 continue; | ||||||
|  |             if (dateTime > maximumDateTime) | ||||||
|  |                 continue; | ||||||
|  |             results.Add((file, property.Id.Value, property.DateTimeOriginal.Value.AddTicks(ticks))); | ||||||
|  |         } | ||||||
|  |         if (files.Length != results.Count) | ||||||
|  |             throw new Exception(); | ||||||
|  |         return results; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     private static void DateFix(string sourceDirectory, string checkDirectory, DateTime minimumDateTime, DateTime maximumDateTime, long ticks) | ||||||
|  |     { | ||||||
|  |         Bitmap bitmap; | ||||||
|  |         string checkFile; | ||||||
|  |         PropertyItem? propertyItem; | ||||||
|  |         string? ticksDirectory = null; | ||||||
|  |         Shared.Models.Property property; | ||||||
|  |         int dateTimeOriginal = (int)IExif.Tags.DateTimeOriginal; | ||||||
|  |         for (int i = 0; i < int.MaxValue; i++) | ||||||
|  |         { | ||||||
|  |             ticksDirectory = Path.Combine(sourceDirectory, ticks.ToString()); | ||||||
|  |             if (!Directory.Exists(ticksDirectory)) | ||||||
|  |             { | ||||||
|  |                 _ = Directory.CreateDirectory(ticksDirectory); | ||||||
|  |                 break; | ||||||
|  |             } | ||||||
|  |             ticks++; | ||||||
|  |  | ||||||
|  |         } | ||||||
|  |         List<(string, int, DateTime)> collection = GetCollection(checkDirectory, minimumDateTime, maximumDateTime, ticks); | ||||||
|  |         ConstructorInfo? constructorInfo = typeof(PropertyItem).GetConstructor(BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Public, null, Array.Empty<Type>(), null) ?? throw new Exception(); | ||||||
|  |         foreach ((string file, int id, DateTime dateTime) in collection) | ||||||
|  |         { | ||||||
|  |             if (ticksDirectory is null) | ||||||
|  |                 throw new Exception(); | ||||||
|  |             checkFile = Path.Combine(ticksDirectory, Path.GetFileName(file)); | ||||||
|  |             if (File.Exists(checkFile)) | ||||||
|  |                 continue; | ||||||
|  |             propertyItem = GetPropertyItem(constructorInfo, dateTimeOriginal, dateTime.ToString("yyyy:MM:dd HH:mm:ss")); | ||||||
|  |             bitmap = new(file); | ||||||
|  |             bitmap.SetPropertyItem(propertyItem); | ||||||
|  |             bitmap.Save(checkFile); | ||||||
|  |             bitmap.Dispose(); | ||||||
|  |             property = Property.Models.A_Property.GetImageProperty(checkFile); | ||||||
|  |             if (property.Id is null || property.Id.Value != id) | ||||||
|  |                 throw new Exception(); | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     private void DateFix(string sourceDirectory) | ||||||
|  |     { | ||||||
|  |         string checkDirectory; | ||||||
|  |         long oneYearTicks = DateTime.MinValue.AddYears(1).Ticks; | ||||||
|  |         checkDirectory = Path.Combine(sourceDirectory, oneYearTicks.ToString()); | ||||||
|  |         if (Directory.Exists(checkDirectory)) | ||||||
|  |             DateFix(sourceDirectory, checkDirectory, DateTime.MinValue, DateTime.MaxValue, new TimeSpan(oneYearTicks - DateTime.MinValue.Ticks).Ticks); | ||||||
|  |         else | ||||||
|  |         { | ||||||
|  |             checkDirectory = Path.Combine(sourceDirectory, "1"); | ||||||
|  |             if (!Directory.Exists(checkDirectory)) | ||||||
|  |                 _Logger.Error($"<{checkDirectory}> doesn't exist!"); | ||||||
|  |             else | ||||||
|  |             { | ||||||
|  |                 string badDirectory = Path.Combine(sourceDirectory, "Bad"); | ||||||
|  |                 string targetDirectory = Path.Combine(sourceDirectory, "Target"); | ||||||
|  |                 string[] minimumDirectory = Directory.GetDirectories(targetDirectory, "*", SearchOption.TopDirectoryOnly); | ||||||
|  |                 if (minimumDirectory.Length != 1) | ||||||
|  |                     _Logger.Error($"<{checkDirectory}> doesn't exist!"); | ||||||
|  |                 else | ||||||
|  |                 { | ||||||
|  |                     string format = "yyyy-MM-dd"; | ||||||
|  |                     string[] maximumDirectory = Directory.GetDirectories(minimumDirectory.First(), "*", SearchOption.TopDirectoryOnly); | ||||||
|  |                     string[] badFiles = !Directory.Exists(badDirectory) ? Array.Empty<string>() : Directory.GetFiles(badDirectory, "*", SearchOption.TopDirectoryOnly); | ||||||
|  |                     string[] targetFiles = !Directory.Exists(targetDirectory) ? Array.Empty<string>() : Directory.GetFiles(targetDirectory, "*", SearchOption.TopDirectoryOnly); | ||||||
|  |                     if (badFiles.Length != 1 || targetFiles.Length != 1 || maximumDirectory.Length != 1) | ||||||
|  |                         _Logger.Error("bad file(s) or target file(s) or maximum directory doesn't equal 1!"); | ||||||
|  |                     else | ||||||
|  |                     { | ||||||
|  |                         DateTime minimumDateTime = DateTime.ParseExact(Path.GetFileName(minimumDirectory.First()), format, null, System.Globalization.DateTimeStyles.None); | ||||||
|  |                         DateTime maximumDateTime = DateTime.ParseExact(Path.GetFileName(maximumDirectory.First()), format, null, System.Globalization.DateTimeStyles.None).AddHours(23); | ||||||
|  |                         Shared.Models.Property badProperty = Property.Models.A_Property.GetImageProperty(badFiles.First()); | ||||||
|  |                         Shared.Models.Property targetProperty = Property.Models.A_Property.GetImageProperty(targetFiles.First()); | ||||||
|  |                         if (badProperty.DateTimeOriginal is null || targetProperty.DateTimeOriginal is null) | ||||||
|  |                             _Logger.Error("Date is null!"); | ||||||
|  |                         else | ||||||
|  |                         { | ||||||
|  |                             TimeSpan timeSpan = new(targetProperty.DateTimeOriginal.Value.Ticks - badProperty.DateTimeOriginal.Value.Ticks); | ||||||
|  |                             DateFix(sourceDirectory, checkDirectory, minimumDateTime, maximumDateTime, timeSpan.Ticks); | ||||||
|  |                         } | ||||||
|  |                     } | ||||||
|  |                 } | ||||||
|  |             } | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     private void Form1_DragDrop(object? sender, DragEventArgs e) | ||||||
|     { |     { | ||||||
|         try |         try | ||||||
|         { |         { | ||||||
|             if (e.Data is not null && e.Data.GetData(DataFormats.FileDrop) is string[] paths && paths.Any()) |             if (e.Data is not null && e.Data.GetData(DataFormats.FileDrop) is string[] paths && paths.Any()) | ||||||
|                 MovePaths(paths); |             { | ||||||
|  |                 if (paths.Length == 1 && Directory.Exists(paths.First())) | ||||||
|  |                     DateFix(paths.First()); | ||||||
|  |                 else | ||||||
|  |                     MovePaths(paths); | ||||||
|  |             } | ||||||
|             else |             else | ||||||
|             { |             { | ||||||
|                 _FirstTextBox.Text = string.Empty; |                 _FirstTextBox.Text = string.Empty; | ||||||
| @ -191,5 +328,4 @@ public partial class DragDropMove : Form | |||||||
|             throw; |             throw; | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
|  |  | ||||||
| } | } | ||||||
| @ -192,7 +192,7 @@ public class DuplicateSearch | |||||||
|                     if (mappingFromItem is not null) |                     if (mappingFromItem is not null) | ||||||
|                     { |                     { | ||||||
|                         resizedFileHolder = new(mappingFromItem.ResizedFileHolder.FullName.Replace($"0{duplicates}", $"1{duplicates}")); |                         resizedFileHolder = new(mappingFromItem.ResizedFileHolder.FullName.Replace($"0{duplicates}", $"1{duplicates}")); | ||||||
|                         collection[0] = new(mappingFromItem.ContainerDateTimes, mappingFromItem.Id, mappingFromItem.ImageFileHolder, mappingFromItem.IsWrongYear, mappingFromItem.MinimumDateTime, mappingFromItem.RelativePath, resizedFileHolder); |                         collection[0] = new(mappingFromItem.ContainerDateTimes, item.Property.DateTimeDigitized, item.Property.DateTimeOriginal, mappingFromItem.Id, mappingFromItem.ImageFileHolder, mappingFromItem.IsWrongYear, mappingFromItem.MinimumDateTime, item.Property.Model, mappingFromItem.RelativePath, resizedFileHolder); | ||||||
|                     } |                     } | ||||||
|                 } |                 } | ||||||
|                 resizedFileHolder = new(string.Concat(Path.Combine(destinationRoot, directory), item.RelativePath)); |                 resizedFileHolder = new(string.Concat(Path.Combine(destinationRoot, directory), item.RelativePath)); | ||||||
|  | |||||||
| @ -3,6 +3,7 @@ using Phares.Shared; | |||||||
| using ShellProgressBar; | using ShellProgressBar; | ||||||
| using System.Collections.ObjectModel; | using System.Collections.ObjectModel; | ||||||
| using System.Drawing.Imaging; | using System.Drawing.Imaging; | ||||||
|  | using System.Text.RegularExpressions; | ||||||
| using View_by_Distance.Distance.Models; | using View_by_Distance.Distance.Models; | ||||||
| using View_by_Distance.Face.Models; | using View_by_Distance.Face.Models; | ||||||
| using View_by_Distance.FaceParts.Models; | using View_by_Distance.FaceParts.Models; | ||||||
| @ -14,6 +15,7 @@ using View_by_Distance.Property.Models; | |||||||
| using View_by_Distance.Resize.Models; | using View_by_Distance.Resize.Models; | ||||||
| using View_by_Distance.Shared.Models; | using View_by_Distance.Shared.Models; | ||||||
| using View_by_Distance.Shared.Models.Methods; | using View_by_Distance.Shared.Models.Methods; | ||||||
|  | using WindowsShortcutFactory; | ||||||
|  |  | ||||||
| namespace View_by_Distance.Instance; | namespace View_by_Distance.Instance; | ||||||
|  |  | ||||||
| @ -267,34 +269,19 @@ public partial class DlibDotNet | |||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private bool? GetIsFocusModel(ReadOnlyDictionary<int, List<LocationContainer<MetadataExtractor.Directory>>> idToLocationContainers, MappingFromItem mappingFromItem) |     private bool? GetIsFocusModel(Shared.Models.Property? property) | ||||||
|     { |     { | ||||||
|         bool? result; |         bool? result; | ||||||
|         string? model; |  | ||||||
|         List<LocationContainer<MetadataExtractor.Directory>>? locationContainers; |  | ||||||
|         IReadOnlyList<MetadataExtractor.Directory> directories; |  | ||||||
|         if (string.IsNullOrEmpty(_Configuration.FocusModel)) |         if (string.IsNullOrEmpty(_Configuration.FocusModel)) | ||||||
|             result = null; |             result = null; | ||||||
|  |         else if (property is null || string.IsNullOrEmpty(property.Model)) | ||||||
|  |             result = null; | ||||||
|         else |         else | ||||||
|         { |             result = property.Model.Contains(_Configuration.FocusModel); | ||||||
|             if (!idToLocationContainers.TryGetValue(mappingFromItem.Id, out locationContainers) || !locationContainers.Any()) |  | ||||||
|                 result = false; |  | ||||||
|             else |  | ||||||
|             { |  | ||||||
|                 directories = locationContainers.First().Directories; |  | ||||||
|                 model = Metadata.Models.Stateless.Methods.IMetadata.GetModel(directories); |  | ||||||
|                 if (model is null) |  | ||||||
|                     directories = MetadataExtractor.ImageMetadataReader.ReadMetadata(mappingFromItem.ResizedFileHolder.FullName); |  | ||||||
|                 model = Metadata.Models.Stateless.Methods.IMetadata.GetModel(directories); |  | ||||||
|                 result = model is not null && model.Contains(_Configuration.FocusModel); |  | ||||||
|                 if (result.Value) |  | ||||||
|                     result = true; |  | ||||||
|             } |  | ||||||
|         } |  | ||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private void SetMapping(ReadOnlyDictionary<int, List<LocationContainer<MetadataExtractor.Directory>>> idToLocationContainers, MapLogic mapLogic, Item item, bool? isFocusRelativePath, bool? isIgnoreRelativePath, MappingFromItem mappingFromItem, List<MappingFromPhotoPrism>? mappingFromPhotoPrismCollection, List<Shared.Models.Face> faces) |     private void SetMapping(MapLogic mapLogic, Item item, bool? isFocusRelativePath, bool? isIgnoreRelativePath, MappingFromItem mappingFromItem, List<MappingFromPhotoPrism>? mappingFromPhotoPrismCollection, List<Shared.Models.Face> faces) | ||||||
|     { |     { | ||||||
|         Mapping mapping; |         Mapping mapping; | ||||||
|         int faceAreaPermyriad; |         int faceAreaPermyriad; | ||||||
| @ -304,7 +291,7 @@ public partial class DlibDotNet | |||||||
|         string deterministicHashCodeKey; |         string deterministicHashCodeKey; | ||||||
|         MappingFromFilter mappingFromFilter; |         MappingFromFilter mappingFromFilter; | ||||||
|         MappingFromLocation? mappingFromLocation; |         MappingFromLocation? mappingFromLocation; | ||||||
|         bool? isFocusModel = GetIsFocusModel(idToLocationContainers, mappingFromItem); |         bool? isFocusModel = GetIsFocusModel(item.Property); | ||||||
|         foreach (Shared.Models.Face face in faces) |         foreach (Shared.Models.Face face in faces) | ||||||
|         { |         { | ||||||
|             if (item.Property?.Id is null || face.FaceEncoding is null || face.Location is null || face.OutputResolution is null) |             if (item.Property?.Id is null || face.FaceEncoding is null || face.Location is null || face.OutputResolution is null) | ||||||
| @ -329,7 +316,7 @@ public partial class DlibDotNet | |||||||
|         } |         } | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private Mapping GetMapping(ReadOnlyDictionary<int, List<LocationContainer<MetadataExtractor.Directory>>> idToLocationContainers, MapLogic mapLogic, Item item, bool? isFocusRelativePath, bool? isIgnoreRelativePath, MappingFromItem mappingFromItem) |     private Mapping GetMapping(MapLogic mapLogic, Item item, bool? isFocusRelativePath, bool? isIgnoreRelativePath, MappingFromItem mappingFromItem) | ||||||
|     { |     { | ||||||
|         Mapping result; |         Mapping result; | ||||||
|         bool? inSkipCollection; |         bool? inSkipCollection; | ||||||
| @ -339,7 +326,7 @@ public partial class DlibDotNet | |||||||
|         string deterministicHashCodeKey; |         string deterministicHashCodeKey; | ||||||
|         MappingFromFilter mappingFromFilter; |         MappingFromFilter mappingFromFilter; | ||||||
|         MappingFromLocation? mappingFromLocation; |         MappingFromLocation? mappingFromLocation; | ||||||
|         bool? isFocusModel = GetIsFocusModel(idToLocationContainers, mappingFromItem); |         bool? isFocusModel = GetIsFocusModel(item.Property); | ||||||
|         if (item.Property?.Id is null) |         if (item.Property?.Id is null) | ||||||
|         { |         { | ||||||
|             inSkipCollection = null; |             inSkipCollection = null; | ||||||
| @ -461,7 +448,7 @@ public partial class DlibDotNet | |||||||
|             if (_AppSettings.MaxDegreeOfParallelism < 2) |             if (_AppSettings.MaxDegreeOfParallelism < 2) | ||||||
|                 ticks = LogDelta(ticks, nameof(D_Face.GetFaces)); |                 ticks = LogDelta(ticks, nameof(D_Face.GetFaces)); | ||||||
|             List<(Shared.Models.Face, FileInfo?, string, bool Saved)> faceCollection = _Faces.SaveFaces(_FaceParts.FileNameExtension, dResultsFullGroupDirectory, subFileTuples, parseExceptions, mappingFromItem, facesDirectory, faces); |             List<(Shared.Models.Face, FileInfo?, string, bool Saved)> faceCollection = _Faces.SaveFaces(_FaceParts.FileNameExtension, dResultsFullGroupDirectory, subFileTuples, parseExceptions, mappingFromItem, facesDirectory, faces); | ||||||
|             SetMapping(idToLocationContainers, mapLogic, item, isFocusRelativePath, isIgnoreRelativePath, mappingFromItem, mappingFromPhotoPrismCollection, faces); |             SetMapping(mapLogic, item, isFocusRelativePath, isIgnoreRelativePath, mappingFromItem, mappingFromPhotoPrismCollection, faces); | ||||||
|             if (_Configuration.CopyFacesAndSaveFaceLandmarkForOutputResolutions.Contains(outputResolution)) |             if (_Configuration.CopyFacesAndSaveFaceLandmarkForOutputResolutions.Contains(outputResolution)) | ||||||
|                 _FaceParts.CopyFacesAndSaveFaceLandmarkImage(facePartsCollectionDirectory, mappingFromItem, faceCollection); |                 _FaceParts.CopyFacesAndSaveFaceLandmarkImage(facePartsCollectionDirectory, mappingFromItem, faceCollection); | ||||||
|             if (_AppSettings.MaxDegreeOfParallelism < 2) |             if (_AppSettings.MaxDegreeOfParallelism < 2) | ||||||
| @ -663,8 +650,8 @@ public partial class DlibDotNet | |||||||
|                 if (!filteredItems.Any()) |                 if (!filteredItems.Any()) | ||||||
|                     continue; |                     continue; | ||||||
|                 sourceDirectoryChanges.Clear(); |                 sourceDirectoryChanges.Clear(); | ||||||
|  |                 anyNullOrNoIsUniqueFileName = filteredItems.Any(l => !l.IsUniqueFileName); | ||||||
|                 totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); |                 totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); | ||||||
|                 anyNullOrNoIsUniqueFileName = filteredItems.Any(l => l.IsUniqueFileName is null || !l.IsUniqueFileName.Value); |  | ||||||
|                 message = $"{i + 1:000} [{filteredItems.Length:000} collectionB] / {containersLength:000} - {total} / {t} total collectionB - {totalSeconds} total second(s) - {outputResolution} - {container.SourceDirectory}"; |                 message = $"{i + 1:000} [{filteredItems.Length:000} collectionB] / {containersLength:000} - {total} / {t} total collectionB - {totalSeconds} total second(s) - {outputResolution} - {container.SourceDirectory}"; | ||||||
|                 if (_Configuration.LoadOrCreateThenSaveImageFacesResultsForOutputResolutions.Contains(outputResolution)) |                 if (_Configuration.LoadOrCreateThenSaveImageFacesResultsForOutputResolutions.Contains(outputResolution)) | ||||||
|                     _Faces.SetAngleBracketCollection(dResultsFullGroupDirectory, container.SourceDirectory); |                     _Faces.SetAngleBracketCollection(dResultsFullGroupDirectory, container.SourceDirectory); | ||||||
| @ -929,7 +916,7 @@ public partial class DlibDotNet | |||||||
|         } |         } | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private Mapping[] GetMappings(Property.Models.Configuration propertyConfiguration, Container[] containers, MapLogic mapLogic, ReadOnlyDictionary<int, List<LocationContainer<MetadataExtractor.Directory>>> idToLocationContainers, bool distinctItems) |     private Mapping[] GetMappings(Property.Models.Configuration propertyConfiguration, Container[] containers, MapLogic mapLogic, bool distinctItems) | ||||||
|     { |     { | ||||||
|         Mapping[] results; |         Mapping[] results; | ||||||
|         int count = 0; |         int count = 0; | ||||||
| @ -976,7 +963,7 @@ public partial class DlibDotNet | |||||||
|                 } |                 } | ||||||
|                 if (!anyValidFaces) |                 if (!anyValidFaces) | ||||||
|                 { |                 { | ||||||
|                     mapping = GetMapping(idToLocationContainers, mapLogic, item, isFocusRelativePath, isIgnoreRelativePath, mappingFromItem); |                     mapping = GetMapping(mapLogic, item, isFocusRelativePath, isIgnoreRelativePath, mappingFromItem); | ||||||
|                     mappingCollection.Add(mapping); |                     mappingCollection.Add(mapping); | ||||||
|                 } |                 } | ||||||
|             } |             } | ||||||
| @ -985,6 +972,95 @@ public partial class DlibDotNet | |||||||
|         return results; |         return results; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|  |     private static void Verify(string eDistanceContentDirectory, List<Item> distinctFilteredItems) | ||||||
|  |     { | ||||||
|  | #if VerifyItem | ||||||
|  |         bool found; | ||||||
|  |         List<Item> notFound = new(); | ||||||
|  |         foreach (Item item in distinctFilteredItems) | ||||||
|  |         { | ||||||
|  |             found = false; | ||||||
|  |             if (item.Property?.Id is null) | ||||||
|  |                 continue; | ||||||
|  |             foreach (Mapping mapping in distinctFilteredMappingCollection) | ||||||
|  |             { | ||||||
|  |                 if (mapping.MappingFromItem.Id != item.Property.Id.Value) | ||||||
|  |                     continue; | ||||||
|  |                 found = true; | ||||||
|  |                 break; | ||||||
|  |             } | ||||||
|  |             if (!found) | ||||||
|  |                 notFound.Add(item); | ||||||
|  |         } | ||||||
|  |         if (notFound.Any()) | ||||||
|  |             throw new NotSupportedException(); | ||||||
|  | #endif | ||||||
|  |         string model; | ||||||
|  |         string fileName; | ||||||
|  |         string directory; | ||||||
|  |         bool? isWrongYear; | ||||||
|  |         List<DateTime> dateTimes; | ||||||
|  |         List<string> distinct = new(); | ||||||
|  |         WindowsShortcut windowsShortcut; | ||||||
|  |         List<(string, string, string)> collection = new(); | ||||||
|  |         foreach (Item item in distinctFilteredItems) | ||||||
|  |         { | ||||||
|  |             if (item.Property?.Id is null || item.ImageFileHolder.LastWriteTime is null) | ||||||
|  |                 continue; | ||||||
|  |             if (item.IsNotUniqueAndNeedsReview is null || !item.IsNotUniqueAndNeedsReview.Value) | ||||||
|  |                 continue; | ||||||
|  |             directory = Path.Combine($"{eDistanceContentDirectory[..^1]}{nameof(item.IsNotUniqueAndNeedsReview)})", item.ImageFileHolder.NameWithoutExtension); | ||||||
|  |             fileName = Path.Combine(directory, $"{item.ImageFileHolder.Length} {item.ImageFileHolder.LastWriteTime.Value.Ticks}.lnk"); | ||||||
|  |             collection.Add((item.ImageFileHolder.FullName, directory, fileName)); | ||||||
|  |             if (distinct.Contains(directory)) | ||||||
|  |                 continue; | ||||||
|  |             distinct.Add(directory); | ||||||
|  |         } | ||||||
|  |         foreach (Item item in distinctFilteredItems) | ||||||
|  |         { | ||||||
|  |             if (item.Property?.Id is null || item.Property.DateTimeOriginal is null) | ||||||
|  |                 continue; | ||||||
|  |             dateTimes = item.Property.GetDateTimes(); | ||||||
|  |             (isWrongYear, _) = Shared.Models.Stateless.Methods.IProperty.IsWrongYear(item.ImageFileHolder, item.Property.DateTimeOriginal, dateTimes); | ||||||
|  |             if (isWrongYear is null || !isWrongYear.Value) | ||||||
|  |                 continue; | ||||||
|  |             // Remove-Item -LiteralPath "\\?\D:\Tmp\a\EX-Z70     " | ||||||
|  |             model = string.IsNullOrEmpty(item.Property.Model) ? "Unknown" : Regex.Replace(item.Property.Model.Trim(), @"[\\,\/,\:,\*,\?,\"",\<,\>,\|]", "_"); | ||||||
|  |             directory = Path.Combine($"{eDistanceContentDirectory[..^1]}{nameof(Item)})", item.Property.DateTimeOriginal.Value.Year.ToString(), model); | ||||||
|  |             fileName = item.IsNotUniqueAndNeedsReview is not null && item.IsNotUniqueAndNeedsReview.Value ? Path.Combine(directory, $"{item.ImageFileHolder.Name} {item.ImageFileHolder.Length}.lnk") : Path.Combine(directory, $"{item.ImageFileHolder.Name}.lnk"); | ||||||
|  |             collection.Add((item.ImageFileHolder.FullName, directory, fileName)); | ||||||
|  |             if (distinct.Contains(directory)) | ||||||
|  |                 continue; | ||||||
|  |             distinct.Add(directory); | ||||||
|  |         } | ||||||
|  | #if Mapping | ||||||
|  |         foreach (Mapping mapping in distinctFilteredMappingCollection) | ||||||
|  |         { | ||||||
|  |             if (mapping.MappingFromItem.IsWrongYear is null || !mapping.MappingFromItem.IsWrongYear.Value) | ||||||
|  |                 continue; | ||||||
|  |             directory = Path.Combine($"{eDistanceContentDirectory[..^1]}{nameof(Mapping)})", mapping.MappingFromItem.MinimumDateTime.Year.ToString()); | ||||||
|  |             fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ResizedFileHolder.Name}.lnk"); | ||||||
|  |             collection.Add((mapping.MappingFromItem.ResizedFileHolder.FullName, directory, fileName)); | ||||||
|  |             if (distinct.Contains(directory)) | ||||||
|  |                 continue; | ||||||
|  |             distinct.Add(directory); | ||||||
|  |         } | ||||||
|  | #endif | ||||||
|  |         foreach (string distinctDirectory in distinct) | ||||||
|  |         { | ||||||
|  |             if (!Directory.Exists(distinctDirectory)) | ||||||
|  |                 _ = Directory.CreateDirectory(distinctDirectory); | ||||||
|  |         } | ||||||
|  |         foreach ((string path, string checkDirectory, string checkFile) in collection) | ||||||
|  |         { | ||||||
|  |             if (File.Exists(checkFile)) | ||||||
|  |                 continue; | ||||||
|  |             windowsShortcut = new() { Path = path }; | ||||||
|  |             windowsShortcut.Save(checkFile); | ||||||
|  |             windowsShortcut.Dispose(); | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  |  | ||||||
|     private void Search(long ticks, string argZero, string propertyRoot) |     private void Search(long ticks, string argZero, string propertyRoot) | ||||||
|     { |     { | ||||||
|         int t; |         int t; | ||||||
| @ -1048,13 +1124,15 @@ public partial class DlibDotNet | |||||||
|         ReadOnlyDictionary<int, List<LocationContainer<MetadataExtractor.Directory>>> idToLocationContainers = mapLogic.GetIdToLocationContainers(); |         ReadOnlyDictionary<int, List<LocationContainer<MetadataExtractor.Directory>>> idToLocationContainers = mapLogic.GetIdToLocationContainers(); | ||||||
|         fileNameToCollection = !Directory.Exists(fPhotoPrismSingletonDirectory) ? fileNameToCollection = new() : F_PhotoPrism.GetFileNameToCollection(fPhotoPrismSingletonDirectory); |         fileNameToCollection = !Directory.Exists(fPhotoPrismSingletonDirectory) ? fileNameToCollection = new() : F_PhotoPrism.GetFileNameToCollection(fPhotoPrismSingletonDirectory); | ||||||
|         FullDoWork(argZero, propertyRoot, ticks, aResultsFullGroupDirectory, bResultsFullGroupDirectory, t, containers, propertyLogic, metadata, eDistanceContentDirectory, fileNameToCollection, idToLocationContainers, mapLogic); |         FullDoWork(argZero, propertyRoot, ticks, aResultsFullGroupDirectory, bResultsFullGroupDirectory, t, containers, propertyLogic, metadata, eDistanceContentDirectory, fileNameToCollection, idToLocationContainers, mapLogic); | ||||||
|         LookForAbandoned(bResultsFullGroupDirectory, containers, idToLocationContainers); |         if (_Configuration.LookForAbandoned) | ||||||
|  |             LookForAbandoned(bResultsFullGroupDirectory, containers, idToLocationContainers); | ||||||
|         _Distance.Clear(); |         _Distance.Clear(); | ||||||
|         if (!personKeyToIds.Any()) |         if (!personKeyToIds.Any()) | ||||||
|             personKeyToIds = mapLogic.GetPersonKeyToIds(); |             personKeyToIds = mapLogic.GetPersonKeyToIds(); | ||||||
|         Mapping[] distinctFilteredMappingCollection = GetMappings(_Configuration.PropertyConfiguration, containers, mapLogic, idToLocationContainers, distinctItems: true); |  | ||||||
|         List<Item> distinctFilteredItems = Shared.Models.Stateless.Methods.IContainer.GetItems(_Configuration.PropertyConfiguration, containers, distinctItems: true, filterItems: true); |         List<Item> distinctFilteredItems = Shared.Models.Stateless.Methods.IContainer.GetItems(_Configuration.PropertyConfiguration, containers, distinctItems: true, filterItems: true); | ||||||
|  |         Verify(eDistanceContentDirectory, distinctFilteredItems); | ||||||
|         List<Shared.Models.Face> distinctFilteredFaces = Map.Models.Stateless.Methods.IMapLogic.GetFaces(distinctFilteredItems); |         List<Shared.Models.Face> distinctFilteredFaces = Map.Models.Stateless.Methods.IMapLogic.GetFaces(distinctFilteredItems); | ||||||
|  |         Mapping[] distinctFilteredMappingCollection = GetMappings(_Configuration.PropertyConfiguration, containers, mapLogic, distinctItems: true); | ||||||
|         int totalNotMapped = mapLogic.UpdateMappingFromPerson(distinctFilteredMappingCollection); |         int totalNotMapped = mapLogic.UpdateMappingFromPerson(distinctFilteredMappingCollection); | ||||||
|         string json = System.Text.Json.JsonSerializer.Serialize(distinctFilteredMappingCollection); |         string json = System.Text.Json.JsonSerializer.Serialize(distinctFilteredMappingCollection); | ||||||
|         File.WriteAllText(Path.Combine(eDistanceContentDirectory, $"{ticks}.json"), json); |         File.WriteAllText(Path.Combine(eDistanceContentDirectory, $"{ticks}.json"), json); | ||||||
|  | |||||||
| @ -36,6 +36,7 @@ public class Configuration | |||||||
|     [Display(Name = "Load Or Create Then Save Image Faces Results"), Required] public string[] LoadOrCreateThenSaveImageFacesResultsForOutputResolutions { get; set; } |     [Display(Name = "Load Or Create Then Save Image Faces Results"), Required] public string[] LoadOrCreateThenSaveImageFacesResultsForOutputResolutions { get; set; } | ||||||
|     [Display(Name = "Location Digits"), Required] public int? LocationDigits { get; set; } |     [Display(Name = "Location Digits"), Required] public int? LocationDigits { get; set; } | ||||||
|     [Display(Name = "Location Factor"), Required] public int? LocationFactor { get; set; } |     [Display(Name = "Location Factor"), Required] public int? LocationFactor { get; set; } | ||||||
|  |     [Display(Name = "Look for Abandoned"), Required] public bool? LookForAbandoned { get; set; } | ||||||
|     [Display(Name = "Mapping Default Name"), Required] public string MappingDefaultName { get; set; } |     [Display(Name = "Mapping Default Name"), Required] public string MappingDefaultName { get; set; } | ||||||
|     [Display(Name = "Mapping Use Deterministic Hash Code Unknown Face Key Value Pairs for Add to Mapping"), Required] public bool? MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping { get; set; } |     [Display(Name = "Mapping Use Deterministic Hash Code Unknown Face Key Value Pairs for Add to Mapping"), Required] public bool? MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping { get; set; } | ||||||
|     [Display(Name = "Mapping Use Deterministic Hash Code Unknown Face Key Value Pairs for Save Mapping"), Required] public bool? MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping { get; set; } |     [Display(Name = "Mapping Use Deterministic Hash Code Unknown Face Key Value Pairs for Save Mapping"), Required] public bool? MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping { get; set; } | ||||||
| @ -146,6 +147,8 @@ public class Configuration | |||||||
|             throw new NullReferenceException(nameof(configuration.LocationDigits)); |             throw new NullReferenceException(nameof(configuration.LocationDigits)); | ||||||
|         if (configuration.LocationFactor is null) |         if (configuration.LocationFactor is null) | ||||||
|             throw new NullReferenceException(nameof(configuration.LocationFactor)); |             throw new NullReferenceException(nameof(configuration.LocationFactor)); | ||||||
|  |         if (configuration.LookForAbandoned is null) | ||||||
|  |             throw new NullReferenceException(nameof(configuration.LookForAbandoned)); | ||||||
|         if (configuration.MappingDefaultName is null) |         if (configuration.MappingDefaultName is null) | ||||||
|             throw new NullReferenceException(nameof(configuration.MappingDefaultName)); |             throw new NullReferenceException(nameof(configuration.MappingDefaultName)); | ||||||
|         if (configuration.MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping is null) |         if (configuration.MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping is null) | ||||||
| @ -256,6 +259,7 @@ public class Configuration | |||||||
|                      configuration.LoadOrCreateThenSaveImageFacesResultsForOutputResolutions, |                      configuration.LoadOrCreateThenSaveImageFacesResultsForOutputResolutions, | ||||||
|                      configuration.LocationDigits.Value, |                      configuration.LocationDigits.Value, | ||||||
|                      configuration.LocationFactor.Value, |                      configuration.LocationFactor.Value, | ||||||
|  |                      configuration.LookForAbandoned.Value, | ||||||
|                      configuration.MappingDefaultName, |                      configuration.MappingDefaultName, | ||||||
|                      configuration.MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping.Value, |                      configuration.MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping.Value, | ||||||
|                      configuration.MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping.Value, |                      configuration.MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping.Value, | ||||||
|  | |||||||
| @ -35,6 +35,7 @@ public class Configuration | |||||||
|     public string[] LoadOrCreateThenSaveImageFacesResultsForOutputResolutions { init; get; } |     public string[] LoadOrCreateThenSaveImageFacesResultsForOutputResolutions { init; get; } | ||||||
|     public int LocationDigits { init; get; } |     public int LocationDigits { init; get; } | ||||||
|     public int LocationFactor { init; get; } |     public int LocationFactor { init; get; } | ||||||
|  |     public bool LookForAbandoned { init; get; } | ||||||
|     public string MappingDefaultName { init; get; } |     public string MappingDefaultName { init; get; } | ||||||
|     public bool MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping { init; get; } |     public bool MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping { init; get; } | ||||||
|     public bool MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping { init; get; } |     public bool MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping { init; get; } | ||||||
| @ -111,6 +112,7 @@ public class Configuration | |||||||
|                          string[] loadOrCreateThenSaveImageFacesResultsForOutputResolutions, |                          string[] loadOrCreateThenSaveImageFacesResultsForOutputResolutions, | ||||||
|                          int locationDigits, |                          int locationDigits, | ||||||
|                          int locationFactor, |                          int locationFactor, | ||||||
|  |                          bool lookForAbandoned, | ||||||
|                          string mappingDefaultName, |                          string mappingDefaultName, | ||||||
|                          bool mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping, |                          bool mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping, | ||||||
|                          bool mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping, |                          bool mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping, | ||||||
| @ -186,6 +188,7 @@ public class Configuration | |||||||
|         LoadOrCreateThenSaveImageFacesResultsForOutputResolutions = loadOrCreateThenSaveImageFacesResultsForOutputResolutions; |         LoadOrCreateThenSaveImageFacesResultsForOutputResolutions = loadOrCreateThenSaveImageFacesResultsForOutputResolutions; | ||||||
|         LocationDigits = locationDigits; |         LocationDigits = locationDigits; | ||||||
|         LocationFactor = locationFactor; |         LocationFactor = locationFactor; | ||||||
|  |         LookForAbandoned = lookForAbandoned; | ||||||
|         MappingDefaultName = mappingDefaultName; |         MappingDefaultName = mappingDefaultName; | ||||||
|         MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping = mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping; |         MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping = mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping; | ||||||
|         MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping = mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping; |         MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping = mappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping; | ||||||
|  | |||||||
| @ -20,6 +20,7 @@ | |||||||
|       "xFocusDirectory": "/Hawaii 2022", |       "xFocusDirectory": "/Hawaii 2022", | ||||||
|       "FocusModel": "", |       "FocusModel": "", | ||||||
|       "xFocusModel": "NIKON D3400", |       "xFocusModel": "NIKON D3400", | ||||||
|  |       "LookForAbandoned": false, | ||||||
|       "xGenealogicalDataCommunicationFile": "", |       "xGenealogicalDataCommunicationFile": "", | ||||||
|       "GenealogicalDataCommunicationFile": "D:/5) Other Small/RootsMagic/Code-638160743318283885/638160743318283885-Export.ged.cln", |       "GenealogicalDataCommunicationFile": "D:/5) Other Small/RootsMagic/Code-638160743318283885/638160743318283885-Export.ged.cln", | ||||||
|       "PersonCharactersCopyCount": 0, |       "PersonCharactersCopyCount": 0, | ||||||
| @ -110,230 +111,6 @@ | |||||||
|         "Scanned Prints", |         "Scanned Prints", | ||||||
|         "Slide in Name Order Originals (622)", |         "Slide in Name Order Originals (622)", | ||||||
|         "Slides Pictures" |         "Slides Pictures" | ||||||
|       ], |  | ||||||
|       "VerifyToSeason": [ |  | ||||||
|         ". 2000", |  | ||||||
|         ". 2001", |  | ||||||
|         ". 2002", |  | ||||||
|         ". 2003", |  | ||||||
|         ". 2004", |  | ||||||
|         ". 2005", |  | ||||||
|         ". 2006", |  | ||||||
|         ". 2007", |  | ||||||
|         ". 2008", |  | ||||||
|         ". 2009", |  | ||||||
|         ". 2010", |  | ||||||
|         ". 2011", |  | ||||||
|         ". 2012", |  | ||||||
|         ". 2013", |  | ||||||
|         ". 2014", |  | ||||||
|         ". 2015", |  | ||||||
|         ". 2016", |  | ||||||
|         ". 2017", |  | ||||||
|         ". 2018", |  | ||||||
|         ". 2019", |  | ||||||
|         ". 2020", |  | ||||||
|         ". 2021", |  | ||||||
|         ". 2022", |  | ||||||
|         ". 2023", |  | ||||||
|         ". 2024", |  | ||||||
|         ". 2025", |  | ||||||
|         ". 2026", |  | ||||||
|         ". 2027", |  | ||||||
|         ". 2028", |  | ||||||
|         ". 2029", |  | ||||||
|         "2000.0 Winter", |  | ||||||
|         "2002.1 Spring", |  | ||||||
|         "2002.4 Winter", |  | ||||||
|         "2003.0 Winter", |  | ||||||
|         "2003.1 Spring", |  | ||||||
|         "2003.3 Fall", |  | ||||||
|         "2003.4 Winter", |  | ||||||
|         "2004.0 Winter", |  | ||||||
|         "2005.1 Spring", |  | ||||||
|         "2005.2 Summer", |  | ||||||
|         "2005.3 Fall", |  | ||||||
|         "2005.4 Winter", |  | ||||||
|         "2006.0 Winter", |  | ||||||
|         "2006.1 Spring", |  | ||||||
|         "2006.3 Fall", |  | ||||||
|         "2007.0 Winter", |  | ||||||
|         "2007.2 Summer Logan Michael", |  | ||||||
|         "2007.2 Summer", |  | ||||||
|         "2007.3 Fall Logan Michael", |  | ||||||
|         "2007.4 Winter Logan Michael", |  | ||||||
|         "2008.0 Winter Logan Michael", |  | ||||||
|         "2008.1 Spring Logan Michael", |  | ||||||
|         "2008.2 Summer Logan Michael", |  | ||||||
|         "2008.2 Summer", |  | ||||||
|         "2008.3 Fall Logan Michael", |  | ||||||
|         "2009.0 Winter Logan Michael", |  | ||||||
|         "2009.0 Winter", |  | ||||||
|         "2009.1 Spring Logan Michael", |  | ||||||
|         "2009.1 Spring", |  | ||||||
|         "2009.2 Summer Logan Michael", |  | ||||||
|         "2009.2 Summer", |  | ||||||
|         "2009.3 Fall Logan Michael", |  | ||||||
|         "2009.3 Fall", |  | ||||||
|         "2009.4 Winter Logan Michael", |  | ||||||
|         "2009.4 Winter", |  | ||||||
|         "2010.0 Winter Logan Michael", |  | ||||||
|         "2010.0 Winter", |  | ||||||
|         "2010.1 Spring Logan Michael", |  | ||||||
|         "2010.1 Spring", |  | ||||||
|         "2010.2 Summer", |  | ||||||
|         "2010.3 Fall Logan Michael", |  | ||||||
|         "2010.3 Fall", |  | ||||||
|         "2010.4 Winter", |  | ||||||
|         "2011.0 Winter", |  | ||||||
|         "2011.1 Spring", |  | ||||||
|         "2011.2 Summer", |  | ||||||
|         "2011.3 Fall", |  | ||||||
|         "2011.4 Winter", |  | ||||||
|         "2012.0 Winter Chelsea 2012", |  | ||||||
|         "2012.0 Winter Chelsea", |  | ||||||
|         "2012.0 Winter", |  | ||||||
|         "2012.1 Spring Chelsea", |  | ||||||
|         "2012.1 Spring", |  | ||||||
|         "2012.2 Summer Chelsea", |  | ||||||
|         "2012.2 Summer", |  | ||||||
|         "2012.3 Fall Chelsea", |  | ||||||
|         "2012.3 Fall", |  | ||||||
|         "2012.4 Winter Chelsea", |  | ||||||
|         "2012.4 Winter", |  | ||||||
|         "2013.0 Winter Chelsea 2013", |  | ||||||
|         "2013.0 Winter Chelsea", |  | ||||||
|         "2013.0 Winter", |  | ||||||
|         "2013.1 Spring", |  | ||||||
|         "2013.2 Summer Chelsea", |  | ||||||
|         "2013.2 Summer", |  | ||||||
|         "2013.3 Fall Chelsea", |  | ||||||
|         "2013.3 Fall", |  | ||||||
|         "2013.4 Winter", |  | ||||||
|         "2014.0 Winter", |  | ||||||
|         "2014.1 Spring", |  | ||||||
|         "2014.2 Summer", |  | ||||||
|         "2014.3 Fall", |  | ||||||
|         "2014.4 Winter", |  | ||||||
|         "2015.0 Winter", |  | ||||||
|         "2015.1 Spring", |  | ||||||
|         "2015.2 Summer", |  | ||||||
|         "2015.3 Fall", |  | ||||||
|         "2015.4 Winter", |  | ||||||
|         "2016.0 Winter", |  | ||||||
|         "2016.1 Spring", |  | ||||||
|         "2016.2 Summer", |  | ||||||
|         "2016.3 Fall", |  | ||||||
|         "2016.4 Winter", |  | ||||||
|         "2017.1 Spring", |  | ||||||
|         "2017.2 Summer", |  | ||||||
|         "2017.3 Fall", |  | ||||||
|         "2017.4 Winter", |  | ||||||
|         "2018.0 Winter", |  | ||||||
|         "2018.1 Spring", |  | ||||||
|         "2018.3 Fall", |  | ||||||
|         "2018.4 Winter", |  | ||||||
|         "2019.0 Winter", |  | ||||||
|         "2019.1 Spring", |  | ||||||
|         "2019.2 Summer", |  | ||||||
|         "2019.3 Fall", |  | ||||||
|         "2019.4 Winter", |  | ||||||
|         "2020.0 Winter", |  | ||||||
|         "2020.1 Spring", |  | ||||||
|         "2020.2 Summer", |  | ||||||
|         "2020.3 Fall", |  | ||||||
|         "2020.4 Winter", |  | ||||||
|         "2021.1 Spring", |  | ||||||
|         "2021.2 Summer", |  | ||||||
|         "2021.3 Fall", |  | ||||||
|         "2021.4 Winter", |  | ||||||
|         "2022.0 Winter", |  | ||||||
|         "2022.1 Spring", |  | ||||||
|         "Anthem 2015", |  | ||||||
|         "April 2010", |  | ||||||
|         "April 2013", |  | ||||||
|         "December 2006", |  | ||||||
|         "December 2010", |  | ||||||
|         "Fall 2005", |  | ||||||
|         "Fall 2015", |  | ||||||
|         "Fall 2016", |  | ||||||
|         "Fall 2017", |  | ||||||
|         "Fall 2018", |  | ||||||
|         "Fall 2019", |  | ||||||
|         "Fall 2020", |  | ||||||
|         "Fall 2021", |  | ||||||
|         "February 2010", |  | ||||||
|         "January 2015", |  | ||||||
|         "July 2010", |  | ||||||
|         "June 2010", |  | ||||||
|         "Kids 2005", |  | ||||||
|         "March 2013", |  | ||||||
|         "May 2010", |  | ||||||
|         "May 2011", |  | ||||||
|         "May 2013", |  | ||||||
|         "October 2005", |  | ||||||
|         "October 2014", |  | ||||||
|         "Spring 2013", |  | ||||||
|         "Spring 2014", |  | ||||||
|         "Spring 2016", |  | ||||||
|         "Spring 2018", |  | ||||||
|         "Spring 2019", |  | ||||||
|         "Spring 2020", |  | ||||||
|         "Summer 2011", |  | ||||||
|         "Summer 2012", |  | ||||||
|         "Summer 2013", |  | ||||||
|         "Summer 2014", |  | ||||||
|         "Summer 2015", |  | ||||||
|         "Summer 2016", |  | ||||||
|         "Summer 2017", |  | ||||||
|         "Summer 2018", |  | ||||||
|         "Summer 2020", |  | ||||||
|         "Summer 2021", |  | ||||||
|         "Winter 2015", |  | ||||||
|         "Winter 2016", |  | ||||||
|         "Winter 2017", |  | ||||||
|         "Winter 2018", |  | ||||||
|         "Winter 2019-2020", |  | ||||||
|         "Winter 2020", |  | ||||||
|         "zzz 2005.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2005.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2005.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2005.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2005.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2006.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2007.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2007.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2008.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2008.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2009.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2009.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2009.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2009.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2010.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2010.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2010.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2010.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2011.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2011.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2011.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2011.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2011.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2012.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2012.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2012.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2012.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2012.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2013.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2013.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2013.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2013.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2013.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2014.0 Winter Tracy Pictures", |  | ||||||
|         "zzz 2014.1 Spring Tracy Pictures", |  | ||||||
|         "zzz 2014.2 Summer Tracy Pictures", |  | ||||||
|         "zzz 2014.3 Fall Tracy Pictures", |  | ||||||
|         "zzz 2014.4 Winter Tracy Pictures", |  | ||||||
|         "zzz 2015.0 Winter Tracy Pictures" |  | ||||||
|       ] |       ] | ||||||
|     } |     } | ||||||
|   } |   } | ||||||
|  | |||||||
| @ -73,6 +73,7 @@ | |||||||
|       "GenealogicalDataCommunicationFile": "", |       "GenealogicalDataCommunicationFile": "", | ||||||
|       "LocationDigits": 9, |       "LocationDigits": 9, | ||||||
|       "LocationFactor": 10000, |       "LocationFactor": 10000, | ||||||
|  |       "LookForAbandoned": true, | ||||||
|       "MappingDefaultName": "John Doe~25", |       "MappingDefaultName": "John Doe~25", | ||||||
|       "MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping": false, |       "MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForAddToMapping": false, | ||||||
|       "MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping": false, |       "MappingUseDeterministicHashCodeUnknownFaceKeyValuePairsForSaveMapping": false, | ||||||
|  | |||||||
| @ -37,8 +37,6 @@ public class MapLogic : Shared.Models.Methods.IMapLogic | |||||||
|         _PropertyConfiguration = propertyConfiguration; |         _PropertyConfiguration = propertyConfiguration; | ||||||
|         if (_Log is null) |         if (_Log is null) | ||||||
|         { } |         { } | ||||||
|         if (propertyConfiguration.VerifyToSeason is null || !propertyConfiguration.VerifyToSeason.Any()) |  | ||||||
|             throw new NullReferenceException(nameof(propertyConfiguration.VerifyToSeason)); |  | ||||||
|         string json; |         string json; | ||||||
|         string fullPath; |         string fullPath; | ||||||
|         List<KeyValuePair<int, int[]>>? collection; |         List<KeyValuePair<int, int[]>>? collection; | ||||||
| @ -812,7 +810,7 @@ public class MapLogic : Shared.Models.Methods.IMapLogic | |||||||
|                 windowsShortcut.Dispose(); |                 windowsShortcut.Dispose(); | ||||||
|                 if (!File.Exists(shortcutFile)) |                 if (!File.Exists(shortcutFile)) | ||||||
|                     continue; |                     continue; | ||||||
|                 File.SetLastWriteTime(shortcutFile, mapping.MappingFromItem.MinimumDateTime); |                 File.SetLastWriteTime(shortcutFile, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime()); | ||||||
|             } |             } | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| @ -1129,45 +1127,35 @@ public class MapLogic : Shared.Models.Methods.IMapLogic | |||||||
|         if (_Configuration is null) |         if (_Configuration is null) | ||||||
|             throw new NullReferenceException(nameof(_Configuration)); |             throw new NullReferenceException(nameof(_Configuration)); | ||||||
|         int season; |         int season; | ||||||
|         string? model; |  | ||||||
|         long personKey; |         long personKey; | ||||||
|         string fileName; |         string fileName; | ||||||
|         string directory; |         string directory; | ||||||
|         int dateCount = 0; |  | ||||||
|         string weekOfYear; |         string weekOfYear; | ||||||
|  |         DateTime dateTime; | ||||||
|         string description; |         string description; | ||||||
|         DateTime? dateTime; |  | ||||||
|         string directoryName; |         string directoryName; | ||||||
|         List<long>? personKeys; |         List<long>? personKeys; | ||||||
|         string personKeyFormatted; |         string personKeyFormatted; | ||||||
|         Calendar calendar = new CultureInfo("en-US").Calendar; |         Calendar calendar = new CultureInfo("en-US").Calendar; | ||||||
|         IReadOnlyList<MetadataExtractor.Directory> directories; |  | ||||||
|         Dictionary<int, List<long>> idToPersonKeys = Stateless.Methods.IMapLogic.GetIdToPersonKeys(personKeyToIds); |         Dictionary<int, List<long>> idToPersonKeys = Stateless.Methods.IMapLogic.GetIdToPersonKeys(personKeyToIds); | ||||||
|         foreach (Mapping mapping in mappingCollection) |         foreach (Mapping mapping in mappingCollection) | ||||||
|         { |         { | ||||||
|             directories = MetadataExtractor.ImageMetadataReader.ReadMetadata(mapping.MappingFromItem.ResizedFileHolder.FullName); |             dateTime = mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(); | ||||||
|             dateTime = Metadata.Models.Stateless.Methods.IMetadata.GetMinimumDateTime(directories); |  | ||||||
|             description = mapping.MappingFromLocation is null ? mapping.MappingFromItem.Id.ToString() : mapping.MappingFromLocation.DeterministicHashCodeKey; |             description = mapping.MappingFromLocation is null ? mapping.MappingFromItem.Id.ToString() : mapping.MappingFromLocation.DeterministicHashCodeKey; | ||||||
|             if (dateTime is not null) |             (season, _) = IProperty.GetSeason(dateTime.DayOfYear); | ||||||
|             { |             weekOfYear = calendar.GetWeekOfYear(dateTime, CalendarWeekRule.FirstDay, DayOfWeek.Sunday).ToString("00"); | ||||||
|                 dateCount++; |             directory = Path.Combine($"{eDistanceContentDirectory}---", "Date Shortcuts", $"{dateTime.Year}.{season}-MM{dateTime.Month:00}-WW{weekOfYear}"); | ||||||
|                 (season, _) = IProperty.GetSeason(dateTime.Value.DayOfYear); |             fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); | ||||||
|                 weekOfYear = calendar.GetWeekOfYear(dateTime.Value, CalendarWeekRule.FirstDay, DayOfWeek.Sunday).ToString("00"); |             results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, dateTime, fileName, description, MakeAllHidden: false)); | ||||||
|                 directory = Path.Combine($"{eDistanceContentDirectory}---", "Date Shortcuts", $"{dateTime.Value.Year}.{season}-MM{dateTime.Value.Month:00}-WW{weekOfYear}"); |  | ||||||
|                 fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); |  | ||||||
|                 results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.MinimumDateTime, fileName, description, MakeAllHidden: false)); |  | ||||||
|             } |  | ||||||
|             model = Metadata.Models.Stateless.Methods.IMetadata.GetModel(directories); |  | ||||||
|             if (mapping.MappingFromItem.ImageFileHolder.DirectoryName is null) |             if (mapping.MappingFromItem.ImageFileHolder.DirectoryName is null) | ||||||
|                 continue; |                 continue; | ||||||
|             directoryName = Path.GetFileName(mapping.MappingFromItem.ImageFileHolder.DirectoryName); |             directoryName = Path.GetFileName(mapping.MappingFromItem.ImageFileHolder.DirectoryName); | ||||||
|             if (!string.IsNullOrEmpty(model) && !string.IsNullOrEmpty(model.Trim())) |             if (!string.IsNullOrEmpty(mapping.MappingFromItem.Model) && !string.IsNullOrEmpty(mapping.MappingFromItem.Model.Trim())) | ||||||
|             { |             { | ||||||
|                 // Remove-Item -LiteralPath "\\?\D:\Tmp\a\EX-Z70     " |                 // Remove-Item -LiteralPath "\\?\D:\Tmp\a\EX-Z70     " | ||||||
|                 model = Regex.Replace(model.Trim(), @"[\\,\/,\:,\*,\?,\"",\<,\>,\|]", "_"); |                 directory = Path.Combine($"{eDistanceContentDirectory}---", "Model Shortcuts", Regex.Replace(mapping.MappingFromItem.Model.Trim(), @"[\\,\/,\:,\*,\?,\"",\<,\>,\|]", "_"), directoryName); | ||||||
|                 directory = Path.Combine($"{eDistanceContentDirectory}---", "Model Shortcuts", model, directoryName); |  | ||||||
|                 fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); |                 fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); | ||||||
|                 results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.MinimumDateTime, fileName, description, MakeAllHidden: false)); |                 results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, dateTime, fileName, description, MakeAllHidden: false)); | ||||||
|             } |             } | ||||||
|             if (mapping.MappingFromPerson is null) |             if (mapping.MappingFromPerson is null) | ||||||
|                 continue; |                 continue; | ||||||
| @ -1179,12 +1167,12 @@ public class MapLogic : Shared.Models.Methods.IMapLogic | |||||||
|             personKeyFormatted = IPersonBirthday.GetFormatted(_Configuration.PersonBirthdayFormat, mapping.MappingFromPerson.PersonBirthday); |             personKeyFormatted = IPersonBirthday.GetFormatted(_Configuration.PersonBirthdayFormat, mapping.MappingFromPerson.PersonBirthday); | ||||||
|             directory = Path.Combine($"{eDistanceContentDirectory}---", "Person Key Shortcuts", personKeyFormatted, directoryName); |             directory = Path.Combine($"{eDistanceContentDirectory}---", "Person Key Shortcuts", personKeyFormatted, directoryName); | ||||||
|             fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); |             fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); | ||||||
|             results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.MinimumDateTime, fileName, description, MakeAllHidden: false)); |             results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, description, MakeAllHidden: false)); | ||||||
|             if (IPerson.IsDefaultName(_Configuration.MappingDefaultName, mapping.MappingFromPerson.DisplayDirectoryName)) |             if (IPerson.IsDefaultName(_Configuration.MappingDefaultName, mapping.MappingFromPerson.DisplayDirectoryName)) | ||||||
|                 continue; |                 continue; | ||||||
|             directory = Path.Combine($"{eDistanceContentDirectory}---", "Name Shortcuts", mapping.MappingFromPerson.DisplayDirectoryName, directoryName); |             directory = Path.Combine($"{eDistanceContentDirectory}---", "Name Shortcuts", mapping.MappingFromPerson.DisplayDirectoryName, directoryName); | ||||||
|             fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); |             fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk"); | ||||||
|             results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.MinimumDateTime, fileName, description, MakeAllHidden: false)); |             results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, description, MakeAllHidden: false)); | ||||||
|         } |         } | ||||||
|         return results; |         return results; | ||||||
|     } |     } | ||||||
| @ -1286,13 +1274,13 @@ public class MapLogic : Shared.Models.Methods.IMapLogic | |||||||
|                 directory = Path.Combine(mapping.MappingFromItem.ResizedFileHolder.DirectoryName, $"{_PropertyConfiguration.ResultAllInOne}Shortcuts", _PropertyConfiguration.ResultAllInOne); |                 directory = Path.Combine(mapping.MappingFromItem.ResizedFileHolder.DirectoryName, $"{_PropertyConfiguration.ResultAllInOne}Shortcuts", _PropertyConfiguration.ResultAllInOne); | ||||||
|                 personDirectory = Path.Combine(directory, "Unknown"); |                 personDirectory = Path.Combine(directory, "Unknown"); | ||||||
|                 fileName = Path.Combine(personDirectory, $"{mapping.MappingFromItem.ResizedFileHolder.Name}.lnk"); |                 fileName = Path.Combine(personDirectory, $"{mapping.MappingFromItem.ResizedFileHolder.Name}.lnk"); | ||||||
|                 collection.Add(new(mapping.MappingFromItem.ResizedFileHolder.FullName, personDirectory, mapping.MappingFromItem.MinimumDateTime, fileName, mapping.MappingFromLocation?.DeterministicHashCodeKey, MakeAllHidden: false)); |                 collection.Add(new(mapping.MappingFromItem.ResizedFileHolder.FullName, personDirectory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, mapping.MappingFromLocation?.DeterministicHashCodeKey, MakeAllHidden: false)); | ||||||
|                 facesDirectory = Stateless.MapLogic.GetFacesDirectory(dFacesContentDirectory, mapping.MappingFromItem); |                 facesDirectory = Stateless.MapLogic.GetFacesDirectory(dFacesContentDirectory, mapping.MappingFromItem); | ||||||
|                 if (facesDirectory is null || mapping.MappingFromLocation is null) |                 if (facesDirectory is null || mapping.MappingFromLocation is null) | ||||||
|                     continue; |                     continue; | ||||||
|                 fullName = Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}"); |                 fullName = Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}"); | ||||||
|                 fileName = Path.Combine(personDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ResizedFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}.lnk"); |                 fileName = Path.Combine(personDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ResizedFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}.lnk"); | ||||||
|                 collection.Add(new(fullName, personDirectory, mapping.MappingFromItem.MinimumDateTime, fileName, mapping.MappingFromLocation.DeterministicHashCodeKey, MakeAllHidden: true)); |                 collection.Add(new(fullName, personDirectory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, mapping.MappingFromLocation.DeterministicHashCodeKey, MakeAllHidden: true)); | ||||||
|             } |             } | ||||||
|             else |             else | ||||||
|             { |             { | ||||||
| @ -1313,7 +1301,7 @@ public class MapLogic : Shared.Models.Methods.IMapLogic | |||||||
|                 else |                 else | ||||||
|                     personDirectory = Path.Combine(directory, mapping.MappingFromPerson.DisplayDirectoryName, $"{personKeyToIds[personKey].Count} Face(s)"); |                     personDirectory = Path.Combine(directory, mapping.MappingFromPerson.DisplayDirectoryName, $"{personKeyToIds[personKey].Count} Face(s)"); | ||||||
|                 fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ResizedFileHolder.Name}.lnk"); |                 fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ResizedFileHolder.Name}.lnk"); | ||||||
|                 collection.Add(new(mapping.MappingFromItem.ResizedFileHolder.FullName, personDirectory, mapping.MappingFromItem.MinimumDateTime, fileName, mapping.MappingFromLocation?.DeterministicHashCodeKey, MakeAllHidden: false)); |                 collection.Add(new(mapping.MappingFromItem.ResizedFileHolder.FullName, personDirectory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, mapping.MappingFromLocation?.DeterministicHashCodeKey, MakeAllHidden: false)); | ||||||
|             } |             } | ||||||
|         } |         } | ||||||
|         return new(directoriesAndDateTimes, collection); |         return new(directoriesAndDateTimes, collection); | ||||||
|  | |||||||
| @ -765,41 +765,41 @@ internal abstract class MapLogic | |||||||
|             SavePossiblyNewPersonContainers(configuration.PersonBirthdayFormat, configuration.FacesFileNameExtension, a2PeopleSingletonDirectory, possiblyNewPersonDisplayDirectoryNamesAndPersonContainer); |             SavePossiblyNewPersonContainers(configuration.PersonBirthdayFormat, configuration.FacesFileNameExtension, a2PeopleSingletonDirectory, possiblyNewPersonDisplayDirectoryNamesAndPersonContainer); | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private static string GetMappingSegmentB(long ticks, PersonBirthday personBirthday, int? approximateYears, long minimumDateTimeTicks, bool? isWrongYear) |     private static string GetMappingSegmentB(long ticks, PersonBirthday personBirthday, int? approximateYears, long dateTimeOriginalThenMinimumDateTimeTicks, bool? isWrongYear) | ||||||
|     { |     { | ||||||
|         int years; |         int years; | ||||||
|         string result; |         string result; | ||||||
|         TimeSpan? timeSpan = IPersonBirthday.GetTimeSpan(minimumDateTimeTicks, isWrongYear, personBirthday); |         TimeSpan? timeSpan = IPersonBirthday.GetTimeSpan(dateTimeOriginalThenMinimumDateTimeTicks, isWrongYear, personBirthday); | ||||||
|         if (timeSpan.HasValue && timeSpan.Value.Ticks < 0) |         if (timeSpan.HasValue && timeSpan.Value.Ticks < 0) | ||||||
|             result = "!---"; |             result = "!---"; | ||||||
|         else if (timeSpan.HasValue) |         else if (timeSpan.HasValue) | ||||||
|         { |         { | ||||||
|             (years, _) = IPersonBirthday.GetAge(minimumDateTimeTicks, personBirthday); |             (years, _) = IPersonBirthday.GetAge(dateTimeOriginalThenMinimumDateTimeTicks, personBirthday); | ||||||
|             result = $"^{years:000}"; |             result = $"^{years:000}"; | ||||||
|         } |         } | ||||||
|         else if (approximateYears.HasValue) |         else if (approximateYears.HasValue) | ||||||
|         { |         { | ||||||
|             DateTime dateTime = new(ticks); |             DateTime dateTime = new(ticks); | ||||||
|             (years, _) = IAge.GetAge(minimumDateTimeTicks, dateTime.AddYears(-approximateYears.Value)); |             (years, _) = IAge.GetAge(dateTimeOriginalThenMinimumDateTimeTicks, dateTime.AddYears(-approximateYears.Value)); | ||||||
|             result = $"~{years:000}"; |             result = $"~{years:000}"; | ||||||
|         } |         } | ||||||
|         else |         else | ||||||
|         { |         { | ||||||
|             string isWrongYearFlag = IItem.GetWrongYearFlag(isWrongYear); |             string isWrongYearFlag = IItem.GetWrongYearFlag(isWrongYear); | ||||||
|             result = $"{isWrongYearFlag}{new DateTime(minimumDateTimeTicks):yyyy}"; |             result = $"{isWrongYearFlag}{new DateTime(dateTimeOriginalThenMinimumDateTimeTicks):yyyy}"; | ||||||
|         } |         } | ||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     internal static string GetMappingSegmentB(long ticks, PersonBirthday personBirthday, int? approximateYears, DateTime minimumDateTime, bool? isWrongYear) |     internal static string GetMappingSegmentB(long ticks, PersonBirthday personBirthday, int? approximateYears, DateTime dateTimeOriginalThenMinimumDateTime, bool? isWrongYear) | ||||||
|     { |     { | ||||||
|         string result = GetMappingSegmentB(ticks, personBirthday, approximateYears, minimumDateTime.Ticks, isWrongYear); |         string result = GetMappingSegmentB(ticks, personBirthday, approximateYears, dateTimeOriginalThenMinimumDateTime.Ticks, isWrongYear); | ||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     internal static string GetMappingSegmentB(long ticks, PersonBirthday personBirthday, int? approximateYears, MappingFromItem mappingFromItem) |     internal static string GetMappingSegmentB(long ticks, PersonBirthday personBirthday, int? approximateYears, MappingFromItem mappingFromItem) | ||||||
|     { |     { | ||||||
|         string result = GetMappingSegmentB(ticks, personBirthday, approximateYears, mappingFromItem.MinimumDateTime, mappingFromItem.IsWrongYear); |         string result = GetMappingSegmentB(ticks, personBirthday, approximateYears, mappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), mappingFromItem.IsWrongYear); | ||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|  | |||||||
| @ -1,5 +1,4 @@ | |||||||
| using ShellProgressBar; | using ShellProgressBar; | ||||||
| using System.Diagnostics; |  | ||||||
| using System.Drawing; | using System.Drawing; | ||||||
| using System.Drawing.Imaging; | using System.Drawing.Imaging; | ||||||
| using System.Globalization; | using System.Globalization; | ||||||
| @ -22,7 +21,6 @@ public class A_Property | |||||||
|  |  | ||||||
|     private readonly Serilog.ILogger? _Log; |     private readonly Serilog.ILogger? _Log; | ||||||
|     private readonly string _OutputExtension; |     private readonly string _OutputExtension; | ||||||
|     private readonly string[] _VerifyToSeason; |  | ||||||
|     private readonly int _MaxDegreeOfParallelism; |     private readonly int _MaxDegreeOfParallelism; | ||||||
|     private readonly ASCIIEncoding _ASCIIEncoding; |     private readonly ASCIIEncoding _ASCIIEncoding; | ||||||
|     private readonly Configuration _Configuration; |     private readonly Configuration _Configuration; | ||||||
| @ -41,9 +39,6 @@ public class A_Property | |||||||
|         _AngleBracketCollection = new List<string>(); |         _AngleBracketCollection = new List<string>(); | ||||||
|         _MaxDegreeOfParallelism = maxDegreeOfParallelism; |         _MaxDegreeOfParallelism = maxDegreeOfParallelism; | ||||||
|         _WriteIndentedJsonSerializerOptions = new JsonSerializerOptions { WriteIndented = true }; |         _WriteIndentedJsonSerializerOptions = new JsonSerializerOptions { WriteIndented = true }; | ||||||
|         if (configuration.VerifyToSeason is null || !configuration.VerifyToSeason.Any()) |  | ||||||
|             throw new Exception(); |  | ||||||
|         _VerifyToSeason = configuration.VerifyToSeason.Select(l => Path.Combine(configuration.RootDirectory, l)).ToArray(); |  | ||||||
|         string checkDirectory; |         string checkDirectory; | ||||||
|         List<string> collection = new(); |         List<string> collection = new(); | ||||||
|         for (int i = 0; i < 12; i++) |         for (int i = 0; i < 12; i++) | ||||||
| @ -107,27 +102,23 @@ public class A_Property | |||||||
|         return results; |         return results; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private Shared.Models.Property GetImageProperty(FileHolder fileHolder, Shared.Models.Property? property, bool populateId, bool isIgnoreExtension, bool isValidImageFormatExtension, bool isValidMetadataExtensions, int? id) |     private static Shared.Models.Property GetImageProperty(FileHolder fileHolder, Shared.Models.Property? property, bool populateId, bool isIgnoreExtension, bool isValidImageFormatExtension, bool isValidMetadataExtensions, int? id, ASCIIEncoding asciiEncoding, bool writeBitmapDataBytes, string? angleBracket) | ||||||
|     { |     { | ||||||
|         Shared.Models.Property result; |         Shared.Models.Property result; | ||||||
|         if (_Log is null) |  | ||||||
|             throw new NullReferenceException(nameof(_Log)); |  | ||||||
|         long ticks; |  | ||||||
|         byte[] bytes; |         byte[] bytes; | ||||||
|         string value; |         string value; | ||||||
|         long fileLength; |         long fileLength; | ||||||
|         int encodingHash; |  | ||||||
|         int? width = null; |         int? width = null; | ||||||
|         int? height = null; |         int? height = null; | ||||||
|  |         string? make = null; | ||||||
|  |         string? model = null; | ||||||
|         string dateTimeFormat; |         string dateTimeFormat; | ||||||
|         DateTime checkDateTime; |         DateTime checkDateTime; | ||||||
|         DateTime? dateTime = null; |         DateTime? dateTime = null; | ||||||
|         PropertyItem? propertyItem; |         PropertyItem? propertyItem; | ||||||
|         string make = string.Empty; |         string? orientation = null; | ||||||
|         string model = string.Empty; |  | ||||||
|         DateTime? gpsDateStamp = null; |         DateTime? gpsDateStamp = null; | ||||||
|         DateTime? dateTimeOriginal = null; |         DateTime? dateTimeOriginal = null; | ||||||
|         string orientation = string.Empty; |  | ||||||
|         DateTime? dateTimeDigitized = null; |         DateTime? dateTimeDigitized = null; | ||||||
|         DateTime? dateTimeFromName = Shared.Models.Stateless.Methods.IProperty.GetDateTimeFromName(fileHolder); |         DateTime? dateTimeFromName = Shared.Models.Stateless.Methods.IProperty.GetDateTimeFromName(fileHolder); | ||||||
|         if (!isValidImageFormatExtension && isValidMetadataExtensions && fileHolder.Exists) |         if (!isValidImageFormatExtension && isValidMetadataExtensions && fileHolder.Exists) | ||||||
| @ -145,7 +136,6 @@ public class A_Property | |||||||
|                 if (populateId && id is null) |                 if (populateId && id is null) | ||||||
|                 { |                 { | ||||||
|                     using Bitmap bitmap = new(image); |                     using Bitmap bitmap = new(image); | ||||||
|                     string angleBracket = _AngleBracketCollection[0]; |  | ||||||
|                     Rectangle rectangle = new(0, 0, image.Width, image.Height); |                     Rectangle rectangle = new(0, 0, image.Width, image.Height); | ||||||
|                     BitmapData bitmapData = bitmap.LockBits(rectangle, ImageLockMode.ReadOnly, bitmap.PixelFormat); |                     BitmapData bitmapData = bitmap.LockBits(rectangle, ImageLockMode.ReadOnly, bitmap.PixelFormat); | ||||||
|                     IntPtr intPtr = bitmapData.Scan0; |                     IntPtr intPtr = bitmapData.Scan0; | ||||||
| @ -153,25 +143,12 @@ public class A_Property | |||||||
|                     bytes = new byte[length]; |                     bytes = new byte[length]; | ||||||
|                     Marshal.Copy(intPtr, bytes, 0, length); |                     Marshal.Copy(intPtr, bytes, 0, length); | ||||||
|                     bitmap.UnlockBits(bitmapData); |                     bitmap.UnlockBits(bitmapData); | ||||||
|                     if (id is null) |                     id ??= Shared.Models.Stateless.Methods.IProperty.GetDeterministicHashCode(bytes); | ||||||
|                     { |                     if (writeBitmapDataBytes && !string.IsNullOrEmpty(angleBracket)) | ||||||
|                         ticks = DateTime.Now.Ticks; |  | ||||||
|                         id = Shared.Models.Stateless.Methods.IProperty.GetDeterministicHashCode(bytes); |  | ||||||
|                         if (_MaxDegreeOfParallelism < 2) |  | ||||||
|                             ticks = LogDelta(ticks, nameof(Shared.Models.Stateless.Methods.IProperty.GetDeterministicHashCode)); |  | ||||||
|                     } |  | ||||||
|                     if (_Configuration.WriteBitmapDataBytes) |  | ||||||
|                     { |                     { | ||||||
|                         FileInfo contentFileInfo = new(Path.Combine(angleBracket.Replace("<>", "()"), fileHolder.Name)); |                         FileInfo contentFileInfo = new(Path.Combine(angleBracket.Replace("<>", "()"), fileHolder.Name)); | ||||||
|                         File.WriteAllBytes(Path.ChangeExtension(contentFileInfo.FullName, string.Empty), bytes); |                         File.WriteAllBytes(Path.ChangeExtension(contentFileInfo.FullName, string.Empty), bytes); | ||||||
|                     } |                     } | ||||||
|                     ticks = DateTime.Now.Ticks; |  | ||||||
|                     string encoding = Encoding.Default.GetString(bytes); |  | ||||||
|                     if (_MaxDegreeOfParallelism < 2) |  | ||||||
|                         ticks = LogDelta(ticks, nameof(Encoding.Default.GetString)); |  | ||||||
|                     encodingHash = Shared.Models.Stateless.Methods.IProperty.GetDeterministicHashCode(encoding); |  | ||||||
|                     if (_MaxDegreeOfParallelism < 2) |  | ||||||
|                         ticks = LogDelta(ticks, nameof(Shared.Models.Stateless.Methods.IProperty.GetDeterministicHashCode)); |  | ||||||
|                 } |                 } | ||||||
|                 width = image.Width; |                 width = image.Width; | ||||||
|                 height = image.Height; |                 height = image.Height; | ||||||
| @ -181,7 +158,7 @@ public class A_Property | |||||||
|                     propertyItem = image.GetPropertyItem((int)IExif.Tags.DateTime); |                     propertyItem = image.GetPropertyItem((int)IExif.Tags.DateTime); | ||||||
|                     if (propertyItem?.Value is not null) |                     if (propertyItem?.Value is not null) | ||||||
|                     { |                     { | ||||||
|                         value = _ASCIIEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); |                         value = asciiEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); | ||||||
|                         if (value.Length > dateTimeFormat.Length) |                         if (value.Length > dateTimeFormat.Length) | ||||||
|                             value = value[..dateTimeFormat.Length]; |                             value = value[..dateTimeFormat.Length]; | ||||||
|                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) |                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) | ||||||
| @ -193,7 +170,7 @@ public class A_Property | |||||||
|                     propertyItem = image.GetPropertyItem((int)IExif.Tags.DateTimeDigitized); |                     propertyItem = image.GetPropertyItem((int)IExif.Tags.DateTimeDigitized); | ||||||
|                     if (propertyItem?.Value is not null) |                     if (propertyItem?.Value is not null) | ||||||
|                     { |                     { | ||||||
|                         value = _ASCIIEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); |                         value = asciiEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); | ||||||
|                         if (value.Length > dateTimeFormat.Length) |                         if (value.Length > dateTimeFormat.Length) | ||||||
|                             value = value[..dateTimeFormat.Length]; |                             value = value[..dateTimeFormat.Length]; | ||||||
|                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) |                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) | ||||||
| @ -205,7 +182,7 @@ public class A_Property | |||||||
|                     propertyItem = image.GetPropertyItem((int)IExif.Tags.DateTimeOriginal); |                     propertyItem = image.GetPropertyItem((int)IExif.Tags.DateTimeOriginal); | ||||||
|                     if (propertyItem?.Value is not null) |                     if (propertyItem?.Value is not null) | ||||||
|                     { |                     { | ||||||
|                         value = _ASCIIEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); |                         value = asciiEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); | ||||||
|                         if (value.Length > dateTimeFormat.Length) |                         if (value.Length > dateTimeFormat.Length) | ||||||
|                             value = value[..dateTimeFormat.Length]; |                             value = value[..dateTimeFormat.Length]; | ||||||
|                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) |                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) | ||||||
| @ -217,7 +194,7 @@ public class A_Property | |||||||
|                     propertyItem = image.GetPropertyItem((int)IExif.Tags.GPSDateStamp); |                     propertyItem = image.GetPropertyItem((int)IExif.Tags.GPSDateStamp); | ||||||
|                     if (propertyItem?.Value is not null) |                     if (propertyItem?.Value is not null) | ||||||
|                     { |                     { | ||||||
|                         value = _ASCIIEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); |                         value = asciiEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); | ||||||
|                         if (value.Length > dateTimeFormat.Length) |                         if (value.Length > dateTimeFormat.Length) | ||||||
|                             value = value[..dateTimeFormat.Length]; |                             value = value[..dateTimeFormat.Length]; | ||||||
|                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) |                         if (value.Length == dateTimeFormat.Length && DateTime.TryParseExact(value, dateTimeFormat, CultureInfo.InvariantCulture, DateTimeStyles.None, out checkDateTime)) | ||||||
| @ -229,7 +206,7 @@ public class A_Property | |||||||
|                     propertyItem = image.GetPropertyItem((int)IExif.Tags.Make); |                     propertyItem = image.GetPropertyItem((int)IExif.Tags.Make); | ||||||
|                     if (propertyItem?.Value is not null) |                     if (propertyItem?.Value is not null) | ||||||
|                     { |                     { | ||||||
|                         value = _ASCIIEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); |                         value = asciiEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); | ||||||
|                         make = value; |                         make = value; | ||||||
|                     } |                     } | ||||||
|                 } |                 } | ||||||
| @ -238,7 +215,7 @@ public class A_Property | |||||||
|                     propertyItem = image.GetPropertyItem((int)IExif.Tags.Model); |                     propertyItem = image.GetPropertyItem((int)IExif.Tags.Model); | ||||||
|                     if (propertyItem?.Value is not null) |                     if (propertyItem?.Value is not null) | ||||||
|                     { |                     { | ||||||
|                         value = _ASCIIEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); |                         value = asciiEncoding.GetString(propertyItem.Value, 0, propertyItem.Len - 1); | ||||||
|                         model = value; |                         model = value; | ||||||
|                     } |                     } | ||||||
|                 } |                 } | ||||||
| @ -252,10 +229,7 @@ public class A_Property | |||||||
|                     } |                     } | ||||||
|                 } |                 } | ||||||
|             } |             } | ||||||
|             catch (Exception) |             catch (Exception) { } | ||||||
|             { |  | ||||||
|                 _Log.Info(string.Concat(new StackFrame().GetMethod()?.Name, " <", fileHolder.Name, ">")); |  | ||||||
|             } |  | ||||||
|         } |         } | ||||||
|         else |         else | ||||||
|             dateTimeOriginal = null; |             dateTimeOriginal = null; | ||||||
| @ -276,6 +250,22 @@ public class A_Property | |||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|  |     public static Shared.Models.Property GetImageProperty(string fileName) | ||||||
|  |     { | ||||||
|  |         int? id = null; | ||||||
|  |         bool populateId = true; | ||||||
|  |         string? angleBracket = null; | ||||||
|  |         bool isIgnoreExtension = false; | ||||||
|  |         bool writeBitmapDataBytes = false; | ||||||
|  |         ASCIIEncoding asciiEncoding = new(); | ||||||
|  |         bool isValidMetadataExtensions = true; | ||||||
|  |         FileHolder fileHolder = new(fileName); | ||||||
|  |         bool isValidImageFormatExtension = true; | ||||||
|  |         Shared.Models.Property? property = null; | ||||||
|  |         Shared.Models.Property result = GetImageProperty(fileHolder, property, populateId, isIgnoreExtension, isValidImageFormatExtension, isValidMetadataExtensions, id, asciiEncoding, writeBitmapDataBytes, angleBracket); | ||||||
|  |         return result; | ||||||
|  |     } | ||||||
|  |  | ||||||
| #pragma warning restore CA1416 | #pragma warning restore CA1416 | ||||||
|  |  | ||||||
|     private Shared.Models.Property GetPropertyOfPrivate(Item item, List<Tuple<string, DateTime>> sourceDirectoryFileTuples, List<string> parseExceptions, bool isIgnoreExtension, bool isValidMetadataExtensions) |     private Shared.Models.Property GetPropertyOfPrivate(Item item, List<Tuple<string, DateTime>> sourceDirectoryFileTuples, List<string> parseExceptions, bool isIgnoreExtension, bool isValidMetadataExtensions) | ||||||
| @ -290,7 +280,7 @@ public class A_Property | |||||||
|         bool populateId = _Configuration.PopulatePropertyId; |         bool populateId = _Configuration.PopulatePropertyId; | ||||||
|         char directory = Shared.Models.Stateless.Methods.IDirectory.GetDirectory(item.ImageFileHolder.Name); |         char directory = Shared.Models.Stateless.Methods.IDirectory.GetDirectory(item.ImageFileHolder.Name); | ||||||
|         int directoryIndex = Shared.Models.Stateless.Methods.IDirectory.GetDirectory(directory); |         int directoryIndex = Shared.Models.Stateless.Methods.IDirectory.GetDirectory(directory); | ||||||
|         if (item.IsUniqueFileName is null || !item.IsUniqueFileName.Value) |         if (!item.IsUniqueFileName) | ||||||
|             fileInfo = new(Path.Combine(angleBracket.Replace("<>", "{}"), $"{item.ImageFileHolder.NameWithoutExtension}{item.ImageFileHolder.ExtensionLowered}.json")); |             fileInfo = new(Path.Combine(angleBracket.Replace("<>", "{}"), $"{item.ImageFileHolder.NameWithoutExtension}{item.ImageFileHolder.ExtensionLowered}.json")); | ||||||
|         else |         else | ||||||
|             fileInfo = new(Path.Combine(_JsonGroups["{}"][directoryIndex], $"{item.ImageFileHolder.NameWithoutExtension}{item.ImageFileHolder.ExtensionLowered}.json")); |             fileInfo = new(Path.Combine(_JsonGroups["{}"][directoryIndex], $"{item.ImageFileHolder.NameWithoutExtension}{item.ImageFileHolder.ExtensionLowered}.json")); | ||||||
| @ -369,7 +359,7 @@ public class A_Property | |||||||
|         if (result is null) |         if (result is null) | ||||||
|         { |         { | ||||||
|             id ??= item.ImageFileHolder.Id; |             id ??= item.ImageFileHolder.Id; | ||||||
|             result = GetImageProperty(item.ImageFileHolder, result, populateId, isIgnoreExtension, item.IsValidImageFormatExtension, isValidMetadataExtensions, id); |             result = GetImageProperty(item.ImageFileHolder, result, populateId, isIgnoreExtension, item.IsValidImageFormatExtension, isValidMetadataExtensions, id, _ASCIIEncoding, _Configuration.WriteBitmapDataBytes, angleBracket); | ||||||
|             json = JsonSerializer.Serialize(result, _WriteIndentedJsonSerializerOptions); |             json = JsonSerializer.Serialize(result, _WriteIndentedJsonSerializerOptions); | ||||||
|             if (populateId && Shared.Models.Stateless.Methods.IPath.WriteAllText(fileInfo.FullName, json, updateDateWhenMatches: true, compareBeforeWrite: true)) |             if (populateId && Shared.Models.Stateless.Methods.IPath.WriteAllText(fileInfo.FullName, json, updateDateWhenMatches: true, compareBeforeWrite: true)) | ||||||
|             { |             { | ||||||
| @ -398,106 +388,6 @@ public class A_Property | |||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private bool AnyFilesMoved(string sourceDirectory, List<Item> items) |  | ||||||
|     { |  | ||||||
|         bool result = false; |  | ||||||
|         if (_Log is null) |  | ||||||
|             throw new NullReferenceException(nameof(_Log)); |  | ||||||
|         int season; |  | ||||||
|         string[] matches; |  | ||||||
|         string deleteFile; |  | ||||||
|         bool? isWrongYear; |  | ||||||
|         string seasonName; |  | ||||||
|         DateTime dateTime; |  | ||||||
|         string destinationFile; |  | ||||||
|         DateTime minimumDateTime; |  | ||||||
|         string destinationDirectory; |  | ||||||
|         string[] sourceDirectorySegments; |  | ||||||
|         DateTime directoryMaximumOfMinimumDateTime = DateTime.MinValue; |  | ||||||
|         foreach (Item item in items) |  | ||||||
|         { |  | ||||||
|             if (!item.IsValidImageFormatExtension || item.Property is null || !item.ImageFileHolder.Exists) |  | ||||||
|                 continue; |  | ||||||
|             minimumDateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property); |  | ||||||
|             if (minimumDateTime > directoryMaximumOfMinimumDateTime) |  | ||||||
|                 directoryMaximumOfMinimumDateTime = minimumDateTime; |  | ||||||
|             if (minimumDateTime != item.ImageFileHolder.CreationTime) |  | ||||||
|             { |  | ||||||
|                 (isWrongYear, matches) = item.Property.IsWrongYear(item.ImageFileHolder, minimumDateTime); |  | ||||||
|                 if (isWrongYear is null || !isWrongYear.Value) |  | ||||||
|                     dateTime = minimumDateTime; |  | ||||||
|                 else |  | ||||||
|                 { |  | ||||||
|                     if (!matches.Any()) |  | ||||||
|                         continue; |  | ||||||
|                     if (!DateTime.TryParseExact(matches[0], "yyyy", CultureInfo.InvariantCulture, DateTimeStyles.None, out dateTime)) |  | ||||||
|                         continue; |  | ||||||
|                 } |  | ||||||
|                 try |  | ||||||
|                 { File.SetCreationTime(item.ImageFileHolder.FullName, dateTime); } |  | ||||||
|                 catch (Exception) |  | ||||||
|                 { } |  | ||||||
|             } |  | ||||||
|             if (!_VerifyToSeason.Contains(sourceDirectory)) |  | ||||||
|                 continue; |  | ||||||
|             if (!item.ImageFileHolder.FullName.Contains("zzz ") && !item.ImageFileHolder.FullName.Contains("Camera ") && item.Property.DateTimeOriginal.HasValue) |  | ||||||
|             { |  | ||||||
|                 TimeSpan timeSpan = new(item.Property.DateTimeOriginal.Value.Ticks - item.Property.LastWriteTime.Ticks); |  | ||||||
|                 if (timeSpan.TotalHours > 7.2f) |  | ||||||
|                 { |  | ||||||
|                     _Log.Warning($"*** propertyHolder.FileInfo.FullName <{item.ImageFileHolder.FullName}>"); |  | ||||||
|                     _Log.Warning($"*** DateTimeOriginal <{item.Property.DateTimeOriginal.Value}>"); |  | ||||||
|                     _Log.Warning($"*** LastWriteTime <{item.Property.LastWriteTime}>"); |  | ||||||
|                     _Log.Warning($"*** TotalHours <{timeSpan.TotalHours}>"); |  | ||||||
|                 } |  | ||||||
|             } |  | ||||||
|             sourceDirectorySegments = Path.GetFileName(sourceDirectory).Split(' '); |  | ||||||
|             (season, seasonName) = Shared.Models.Stateless.Methods.IProperty.GetSeason(minimumDateTime.DayOfYear); |  | ||||||
|             if (sourceDirectorySegments[0] == "zzz") |  | ||||||
|                 destinationDirectory = Path.Combine(_Configuration.RootDirectory, $"zzz ={minimumDateTime:yyyy}.{season} {seasonName} {string.Join(' ', sourceDirectorySegments.Skip(3))}"); |  | ||||||
|             else if (sourceDirectorySegments.Length > 2) |  | ||||||
|                 destinationDirectory = Path.Combine(_Configuration.RootDirectory, $"={minimumDateTime:yyyy}.{season} {seasonName} {string.Join(' ', sourceDirectorySegments.Skip(2))}"); |  | ||||||
|             else |  | ||||||
|                 destinationDirectory = Path.Combine(_Configuration.RootDirectory, $"={minimumDateTime:yyyy}.{season} {seasonName}"); |  | ||||||
|             if (destinationDirectory == sourceDirectory) |  | ||||||
|                 continue; |  | ||||||
|             lock (item) |  | ||||||
|                 item.SetMoved(true); |  | ||||||
|             if (!result) |  | ||||||
|                 result = true; |  | ||||||
|             if (!Directory.Exists(destinationDirectory)) |  | ||||||
|                 _ = Directory.CreateDirectory(destinationDirectory); |  | ||||||
|             destinationFile = Path.Combine(destinationDirectory, item.ImageFileHolder.Name); |  | ||||||
|             if (File.Exists(destinationFile)) |  | ||||||
|             { |  | ||||||
|                 if (_OutputExtension is not ".jpg" and not ".jpeg") |  | ||||||
|                     throw new Exception(); |  | ||||||
|                 if (destinationFile.EndsWith(".jpg", ignoreCase: true, CultureInfo.CurrentCulture)) |  | ||||||
|                     destinationFile = Path.Combine(destinationDirectory, Path.ChangeExtension(item.ImageFileHolder.Name, ".jpeg")); |  | ||||||
|                 else if (destinationFile.EndsWith(".jpeg", ignoreCase: true, CultureInfo.CurrentCulture)) |  | ||||||
|                     destinationFile = Path.Combine(destinationDirectory, Path.ChangeExtension(item.ImageFileHolder.Name, ".jpg")); |  | ||||||
|             } |  | ||||||
|             _Log.Information($"*** source <{item.ImageFileHolder.FullName}>"); |  | ||||||
|             _Log.Information($"*** destination <{destinationFile}>"); |  | ||||||
|             if (!File.Exists(destinationFile)) |  | ||||||
|                 File.Move(item.ImageFileHolder.FullName, destinationFile); |  | ||||||
|             else |  | ||||||
|             { |  | ||||||
|                 deleteFile = Path.ChangeExtension(item.ImageFileHolder.FullName, ".delete"); |  | ||||||
|                 if (File.Exists(deleteFile)) |  | ||||||
|                     File.Delete(deleteFile); |  | ||||||
|                 File.Move(item.ImageFileHolder.FullName, destinationFile); |  | ||||||
|             } |  | ||||||
|         } |  | ||||||
|         if (directoryMaximumOfMinimumDateTime != DateTime.MinValue) |  | ||||||
|         { |  | ||||||
|             DirectoryInfo directoryInfo = new(sourceDirectory); |  | ||||||
|             if (directoryInfo.LastWriteTime != directoryMaximumOfMinimumDateTime) |  | ||||||
|                 Directory.SetLastWriteTime(sourceDirectory, directoryMaximumOfMinimumDateTime); |  | ||||||
|         } |  | ||||||
|         return result; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     private void SavePropertyParallelForWork(string sourceDirectory, List<Tuple<string, DateTime>> sourceDirectoryFileTuples, List<Tuple<string, DateTime>> sourceDirectoryChanges, Item item) |     private void SavePropertyParallelForWork(string sourceDirectory, List<Tuple<string, DateTime>> sourceDirectoryFileTuples, List<Tuple<string, DateTime>> sourceDirectoryChanges, Item item) | ||||||
|     { |     { | ||||||
|         Shared.Models.Property property; |         Shared.Models.Property property; | ||||||
| @ -579,7 +469,6 @@ public class A_Property | |||||||
|             throw new NullReferenceException(nameof(_Log)); |             throw new NullReferenceException(nameof(_Log)); | ||||||
|         string message; |         string message; | ||||||
|         int totalSeconds; |         int totalSeconds; | ||||||
|         bool? anyFilesMoved; |  | ||||||
|         Container container; |         Container container; | ||||||
|         bool anyNullOrNoIsUniqueFileName; |         bool anyNullOrNoIsUniqueFileName; | ||||||
|         List<Exception> exceptions = new(); |         List<Exception> exceptions = new(); | ||||||
| @ -594,7 +483,7 @@ public class A_Property | |||||||
|             sourceDirectoryChanges.Clear(); |             sourceDirectoryChanges.Clear(); | ||||||
|             if (!container.Items.Any()) |             if (!container.Items.Any()) | ||||||
|                 continue; |                 continue; | ||||||
|             anyNullOrNoIsUniqueFileName = container.Items.Any(l => l.IsUniqueFileName is null || !l.IsUniqueFileName.Value); |             anyNullOrNoIsUniqueFileName = container.Items.Any(l => !l.IsUniqueFileName); | ||||||
|             SetAngleBracketCollection(container.SourceDirectory, anyNullOrNoIsUniqueFileName); |             SetAngleBracketCollection(container.SourceDirectory, anyNullOrNoIsUniqueFileName); | ||||||
|             totalSeconds = (int)Math.Truncate(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); |             totalSeconds = (int)Math.Truncate(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds); | ||||||
|             message = $"{i + 1:000} / {containersCount:000}) {container.Items.Count:000} file(s) - {totalSeconds} total second(s) - {container.SourceDirectory}"; |             message = $"{i + 1:000} / {containersCount:000}) {container.Items.Count:000} file(s) - {totalSeconds} total second(s) - {container.SourceDirectory}"; | ||||||
| @ -605,10 +494,6 @@ public class A_Property | |||||||
|                 throw new Exception(string.Concat("All in [", container.SourceDirectory, "]failed!")); |                 throw new Exception(string.Concat("All in [", container.SourceDirectory, "]failed!")); | ||||||
|             if (exceptions.Count != 0) |             if (exceptions.Count != 0) | ||||||
|                 _ExceptionsDirectories.Add(container.SourceDirectory); |                 _ExceptionsDirectories.Add(container.SourceDirectory); | ||||||
|             if (exceptions.Count != 0) |  | ||||||
|                 anyFilesMoved = null; |  | ||||||
|             else |  | ||||||
|                 anyFilesMoved = AnyFilesMoved(container.SourceDirectory, container.Items); |  | ||||||
|             if (Directory.GetFiles(propertyRoot, "*.txt", SearchOption.TopDirectoryOnly).Any()) |             if (Directory.GetFiles(propertyRoot, "*.txt", SearchOption.TopDirectoryOnly).Any()) | ||||||
|             { |             { | ||||||
|                 for (int y = 0; y < int.MaxValue; y++) |                 for (int y = 0; y < int.MaxValue; y++) | ||||||
| @ -630,8 +515,7 @@ public class A_Property | |||||||
|         { |         { | ||||||
|             if (item.ImageFileHolder.DirectoryName is null) |             if (item.ImageFileHolder.DirectoryName is null) | ||||||
|                 throw new NullReferenceException(nameof(item.ImageFileHolder.DirectoryName)); |                 throw new NullReferenceException(nameof(item.ImageFileHolder.DirectoryName)); | ||||||
|             bool anyNullOrNoIsUniqueFileName = item.IsUniqueFileName is null || !item.IsUniqueFileName.Value; |             SetAngleBracketCollection(item.ImageFileHolder.DirectoryName, !item.IsUniqueFileName); | ||||||
|             SetAngleBracketCollection(item.ImageFileHolder.DirectoryName, anyNullOrNoIsUniqueFileName); |  | ||||||
|         } |         } | ||||||
|         bool isValidMetadataExtensions = _Configuration.ValidMetadataExtensions.Contains(item.ImageFileHolder.ExtensionLowered); |         bool isValidMetadataExtensions = _Configuration.ValidMetadataExtensions.Contains(item.ImageFileHolder.ExtensionLowered); | ||||||
|         bool isIgnoreExtension = item.IsValidImageFormatExtension && _Configuration.IgnoreExtensions.Contains(item.ImageFileHolder.ExtensionLowered); |         bool isIgnoreExtension = item.IsValidImageFormatExtension && _Configuration.IgnoreExtensions.Contains(item.ImageFileHolder.ExtensionLowered); | ||||||
|  | |||||||
| @ -34,7 +34,6 @@ public class Configuration : Shared.Models.Properties.IPropertyConfiguration | |||||||
|     public string ResultSingleton { init; get; } |     public string ResultSingleton { init; get; } | ||||||
|     public string[] ValidImageFormatExtensions { init; get; } |     public string[] ValidImageFormatExtensions { init; get; } | ||||||
|     public string[] ValidMetadataExtensions { init; get; } |     public string[] ValidMetadataExtensions { init; get; } | ||||||
|     public string[] VerifyToSeason { init; get; } |  | ||||||
|     public bool WriteBitmapDataBytes { init; get; } |     public bool WriteBitmapDataBytes { init; get; } | ||||||
|  |  | ||||||
|     [JsonConstructor] |     [JsonConstructor] | ||||||
| @ -75,7 +74,6 @@ public class Configuration : Shared.Models.Properties.IPropertyConfiguration | |||||||
|         _RootDirectory = rootDirectory; |         _RootDirectory = rootDirectory; | ||||||
|         ValidImageFormatExtensions = validImageFormatExtensions; |         ValidImageFormatExtensions = validImageFormatExtensions; | ||||||
|         ValidMetadataExtensions = validMetadataExtensions; |         ValidMetadataExtensions = validMetadataExtensions; | ||||||
|         VerifyToSeason = verifyToSeason; |  | ||||||
|         WriteBitmapDataBytes = writeBitmapDataBytes; |         WriteBitmapDataBytes = writeBitmapDataBytes; | ||||||
|     } |     } | ||||||
|  |  | ||||||
| @ -110,8 +108,6 @@ public class Configuration : Shared.Models.Properties.IPropertyConfiguration | |||||||
|             throw new NullReferenceException(nameof(propertyConfiguration.ValidImageFormatExtensions)); |             throw new NullReferenceException(nameof(propertyConfiguration.ValidImageFormatExtensions)); | ||||||
|         if (propertyConfiguration.ValidMetadataExtensions is null || !propertyConfiguration.ValidMetadataExtensions.Any()) |         if (propertyConfiguration.ValidMetadataExtensions is null || !propertyConfiguration.ValidMetadataExtensions.Any()) | ||||||
|             throw new NullReferenceException(nameof(propertyConfiguration.ValidMetadataExtensions)); |             throw new NullReferenceException(nameof(propertyConfiguration.ValidMetadataExtensions)); | ||||||
|         if (propertyConfiguration.VerifyToSeason is null || !propertyConfiguration.VerifyToSeason.Any()) |  | ||||||
|             throw new NullReferenceException(nameof(propertyConfiguration.VerifyToSeason)); |  | ||||||
|         if (propertyConfiguration is null) |         if (propertyConfiguration is null) | ||||||
|             throw new NullReferenceException(nameof(propertyConfiguration)); |             throw new NullReferenceException(nameof(propertyConfiguration)); | ||||||
|         if (string.IsNullOrEmpty(propertyConfiguration.DateGroup)) |         if (string.IsNullOrEmpty(propertyConfiguration.DateGroup)) | ||||||
|  | |||||||
| @ -284,7 +284,7 @@ public class C_Resize | |||||||
|     { |     { | ||||||
|         // string subFile, Shared.Models.Property property, Shared.Models.FileHolder? fileHolder |         // string subFile, Shared.Models.Property property, Shared.Models.FileHolder? fileHolder | ||||||
|         string dateTimeFormat = Shared.Models.Stateless.Methods.IProperty.DateTimeFormat(); |         string dateTimeFormat = Shared.Models.Stateless.Methods.IProperty.DateTimeFormat(); | ||||||
|         DateTime dateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(property); |         DateTime dateTime = property.DateTimeOriginal is not null ? property.DateTimeOriginal.Value : Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(property); | ||||||
|         string dateTimeValue = dateTime.ToString(dateTimeFormat); |         string dateTimeValue = dateTime.ToString(dateTimeFormat); | ||||||
|         byte[] bytes = _ASCIIEncoding.GetBytes(dateTimeValue); |         byte[] bytes = _ASCIIEncoding.GetBytes(dateTimeValue); | ||||||
|         if (_ASCIIEncoding.GetString(bytes, 0, bytes.Length) != dateTimeValue) |         if (_ASCIIEncoding.GetString(bytes, 0, bytes.Length) != dateTimeValue) | ||||||
|  | |||||||
| @ -7,31 +7,31 @@ public record class FaceDistance : Properties.IFaceDistance | |||||||
| { | { | ||||||
|  |  | ||||||
|     public int? ConfidencePercent { init; get; } |     public int? ConfidencePercent { init; get; } | ||||||
|  |     public DateTime DateTimeOriginalThenMinimumDateTime { init; get; } | ||||||
|     public object? Encoding { init; get; } |     public object? Encoding { init; get; } | ||||||
|     public int Id { init; get; } |     public int Id { init; get; } | ||||||
|     public bool? IsWrongYear { init; get; } |     public bool? IsWrongYear { init; get; } | ||||||
|     public double? Length { init; get; } |     public double? Length { init; get; } | ||||||
|     public DateTime? MinimumDateTime { init; get; } |  | ||||||
|     public int? NormalizedRectangle { init; get; } |     public int? NormalizedRectangle { init; get; } | ||||||
|  |  | ||||||
|     [JsonConstructor] |     [JsonConstructor] | ||||||
|     public FaceDistance(int? confidencePercent, object? encoding, int id, bool? isWrongYear, double? length, DateTime? minimumDateTime, int? normalizedRectangle) |     public FaceDistance(int? confidencePercent, DateTime dateTimeOriginalThenMinimumDateTime, object? encoding, int id, bool? isWrongYear, double? length, int? normalizedRectangle) | ||||||
|     { |     { | ||||||
|         ConfidencePercent = confidencePercent; |         ConfidencePercent = confidencePercent; | ||||||
|  |         DateTimeOriginalThenMinimumDateTime = dateTimeOriginalThenMinimumDateTime; | ||||||
|         Encoding = encoding; |         Encoding = encoding; | ||||||
|         Id = id; |         Id = id; | ||||||
|         IsWrongYear = isWrongYear; |         IsWrongYear = isWrongYear; | ||||||
|         Length = length; |         Length = length; | ||||||
|         MinimumDateTime = minimumDateTime; |  | ||||||
|         NormalizedRectangle = normalizedRectangle; |         NormalizedRectangle = normalizedRectangle; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     public FaceDistance(int? confidencePercent, object? encoding, int id, bool? isWrongYear, DateTime? minimumDateTime, int? normalizedRectangle) : |     public FaceDistance(int? confidencePercent, DateTime dateTimeOriginalThenMinimumDateTime, object? encoding, int id, bool? isWrongYear, int? normalizedRectangle) : | ||||||
|         this(confidencePercent, encoding, id, isWrongYear, null, minimumDateTime, normalizedRectangle) |         this(confidencePercent, dateTimeOriginalThenMinimumDateTime, encoding, id, isWrongYear, null, normalizedRectangle) | ||||||
|     { } |     { } | ||||||
|  |  | ||||||
|     public FaceDistance(FaceDistance faceDistance, double length) : |     public FaceDistance(FaceDistance faceDistance, double length) : | ||||||
|         this(faceDistance.ConfidencePercent, null, faceDistance.Id, faceDistance.IsWrongYear, length, faceDistance.MinimumDateTime, faceDistance.NormalizedRectangle) |         this(faceDistance.ConfidencePercent, faceDistance.DateTimeOriginalThenMinimumDateTime, null, faceDistance.Id, faceDistance.IsWrongYear, length, faceDistance.NormalizedRectangle) | ||||||
|     { } |     { } | ||||||
|  |  | ||||||
|     public FaceDistance(object encoding) => Encoding = encoding; |     public FaceDistance(object encoding) => Encoding = encoding; | ||||||
|  | |||||||
| @ -1,3 +1,3 @@ | |||||||
| namespace View_by_Distance.Shared.Models; | namespace View_by_Distance.Shared.Models; | ||||||
|  |  | ||||||
| public record FilePair(string Path, bool IsUnique, List<string> Collection, string? Match) { } | public record FilePair(string Path, bool IsUnique, bool? IsNotUniqueAndNeedsReview, List<string> Collection, string? Match) { } | ||||||
| @ -9,7 +9,8 @@ public class Item : Properties.IItem | |||||||
|     protected List<Face> _Faces; |     protected List<Face> _Faces; | ||||||
|     protected readonly bool? _FileSizeChanged; |     protected readonly bool? _FileSizeChanged; | ||||||
|     protected readonly FileHolder _ImageFileHolder; |     protected readonly FileHolder _ImageFileHolder; | ||||||
|     protected bool? _IsUniqueFileName; |     protected bool? _IsNotUniqueAndNeedsReview; | ||||||
|  |     protected bool _IsUniqueFileName; | ||||||
|     protected bool _IsValidImageFormatExtension; |     protected bool _IsValidImageFormatExtension; | ||||||
|     protected bool? _LastWriteTimeChanged; |     protected bool? _LastWriteTimeChanged; | ||||||
|     protected bool? _Moved; |     protected bool? _Moved; | ||||||
| @ -20,7 +21,8 @@ public class Item : Properties.IItem | |||||||
|     public List<Face> Faces => _Faces; |     public List<Face> Faces => _Faces; | ||||||
|     public bool? FileSizeChanged => _FileSizeChanged; |     public bool? FileSizeChanged => _FileSizeChanged; | ||||||
|     public FileHolder ImageFileHolder => _ImageFileHolder; |     public FileHolder ImageFileHolder => _ImageFileHolder; | ||||||
|     public bool? IsUniqueFileName => _IsUniqueFileName; |     public bool? IsNotUniqueAndNeedsReview => _IsNotUniqueAndNeedsReview; | ||||||
|  |     public bool IsUniqueFileName => _IsUniqueFileName; | ||||||
|     public bool IsValidImageFormatExtension => _IsValidImageFormatExtension; |     public bool IsValidImageFormatExtension => _IsValidImageFormatExtension; | ||||||
|     public bool? LastWriteTimeChanged => _LastWriteTimeChanged; |     public bool? LastWriteTimeChanged => _LastWriteTimeChanged; | ||||||
|     public bool? Moved => _Moved; |     public bool? Moved => _Moved; | ||||||
| @ -30,11 +32,12 @@ public class Item : Properties.IItem | |||||||
|     public FileHolder SourceDirectoryFileHolder => _SourceDirectoryFileHolder; |     public FileHolder SourceDirectoryFileHolder => _SourceDirectoryFileHolder; | ||||||
|  |  | ||||||
|     [JsonConstructor] |     [JsonConstructor] | ||||||
|     public Item(List<Face> faces, bool? fileSizeChanged, FileHolder imageFileHolder, bool? isUniqueFileName, bool isValidImageFormatExtension, bool? lastWriteTimeChanged, bool? moved, Property? property, string relativePath, FileHolder? resizedFileHolder, FileHolder sourceDirectoryFileHolder) |     public Item(List<Face> faces, bool? fileSizeChanged, FileHolder imageFileHolder, bool? isNotUniqueAndNeedsReview, bool isUniqueFileName, bool isValidImageFormatExtension, bool? lastWriteTimeChanged, bool? moved, Property? property, string relativePath, FileHolder? resizedFileHolder, FileHolder sourceDirectoryFileHolder) | ||||||
|     { |     { | ||||||
|         _Faces = faces; |         _Faces = faces; | ||||||
|         _FileSizeChanged = fileSizeChanged; |         _FileSizeChanged = fileSizeChanged; | ||||||
|         _ImageFileHolder = imageFileHolder; |         _ImageFileHolder = imageFileHolder; | ||||||
|  |         _IsNotUniqueAndNeedsReview = isNotUniqueAndNeedsReview; | ||||||
|         _IsUniqueFileName = isUniqueFileName; |         _IsUniqueFileName = isUniqueFileName; | ||||||
|         _IsValidImageFormatExtension = isValidImageFormatExtension; |         _IsValidImageFormatExtension = isValidImageFormatExtension; | ||||||
|         _LastWriteTimeChanged = lastWriteTimeChanged; |         _LastWriteTimeChanged = lastWriteTimeChanged; | ||||||
| @ -45,8 +48,8 @@ public class Item : Properties.IItem | |||||||
|         _SourceDirectoryFileHolder = sourceDirectoryFileHolder; |         _SourceDirectoryFileHolder = sourceDirectoryFileHolder; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     public Item(FileHolder sourceDirectoryFileHolder, string relativePath, FileHolder imageFileInfo, bool? isUniqueFileName, bool isValidImageFormatExtension, Property? property, bool? abandoned, bool? fileSizeChanged, bool? lastWriteTimeChanged) : |     public Item(FileHolder sourceDirectoryFileHolder, string relativePath, FileHolder imageFileInfo, bool? isNotUniqueAndNeedsReview, bool isUniqueFileName, bool isValidImageFormatExtension, Property? property, bool? abandoned, bool? fileSizeChanged, bool? lastWriteTimeChanged) : | ||||||
|         this(new(), fileSizeChanged, imageFileInfo, isUniqueFileName, isValidImageFormatExtension, lastWriteTimeChanged, null, property, relativePath, null, sourceDirectoryFileHolder) |         this(new(), fileSizeChanged, imageFileInfo, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, lastWriteTimeChanged, null, property, relativePath, null, sourceDirectoryFileHolder) | ||||||
|     { |     { | ||||||
|         if (relativePath.EndsWith(".json")) |         if (relativePath.EndsWith(".json")) | ||||||
|             throw new ArgumentException("Can not be a *.json file!"); |             throw new ArgumentException("Can not be a *.json file!"); | ||||||
| @ -55,7 +58,7 @@ public class Item : Properties.IItem | |||||||
|     } |     } | ||||||
|  |  | ||||||
|     public Item(FileHolder sourceDirectoryFileHolder, string relativePath, bool isValidImageFormatExtension) : |     public Item(FileHolder sourceDirectoryFileHolder, string relativePath, bool isValidImageFormatExtension) : | ||||||
|         this(sourceDirectoryFileHolder, relativePath, sourceDirectoryFileHolder, null, isValidImageFormatExtension, null, null, null, null) |         this(sourceDirectoryFileHolder, relativePath, sourceDirectoryFileHolder, null, false, isValidImageFormatExtension, null, null, null, null) | ||||||
|     { } |     { } | ||||||
|  |  | ||||||
|     public override string ToString() |     public override string ToString() | ||||||
|  | |||||||
| @ -3,142 +3,6 @@ using System.Text.Json.Serialization; | |||||||
|  |  | ||||||
| namespace View_by_Distance.Shared.Models; | namespace View_by_Distance.Shared.Models; | ||||||
|  |  | ||||||
| public class MappingFromItem : Properties.IMappingFromItem |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public DateTime[] ContainerDateTimes { init; get; } |  | ||||||
|     public int Id { init; get; } |  | ||||||
|     public FileHolder ImageFileHolder { init; get; } |  | ||||||
|     public bool? IsWrongYear { init; get; } |  | ||||||
|     public DateTime MinimumDateTime { init; get; } |  | ||||||
|     public string RelativePath { init; get; } |  | ||||||
|     public FileHolder ResizedFileHolder { init; get; } |  | ||||||
|  |  | ||||||
|     [JsonConstructor] |  | ||||||
|     public MappingFromItem(DateTime[] containerDateTimes, int id, FileHolder imageFileHolder, bool? isWrongYear, DateTime minimumDateTime, string relativePath, FileHolder resizedFileHolder) |  | ||||||
|     { |  | ||||||
|         ContainerDateTimes = containerDateTimes; |  | ||||||
|         Id = id; |  | ||||||
|         ImageFileHolder = imageFileHolder; |  | ||||||
|         IsWrongYear = isWrongYear; |  | ||||||
|         MinimumDateTime = minimumDateTime; |  | ||||||
|         RelativePath = relativePath; |  | ||||||
|         ResizedFileHolder = resizedFileHolder; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     public override string ToString() |  | ||||||
|     { |  | ||||||
|         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); |  | ||||||
|         return result; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     internal static MappingFromItem GetMappingFromItem(DateTime[] containerDateTimes, Item item, FileHolder? resizedFileHolder) |  | ||||||
|     { |  | ||||||
|         MappingFromItem result; |  | ||||||
|         bool? isWrongYear; |  | ||||||
|         DateTime minimumDateTime; |  | ||||||
|         if (item.Property?.Id is null) |  | ||||||
|             throw new NotSupportedException(); |  | ||||||
|         if (resizedFileHolder is null) |  | ||||||
|             throw new NotSupportedException(); |  | ||||||
|         minimumDateTime = Stateless.Methods.IProperty.GetMinimumDateTime(item.Property); |  | ||||||
|         (isWrongYear, _) = item.Property.IsWrongYear(item.ImageFileHolder, minimumDateTime); |  | ||||||
|         result = new(containerDateTimes, item.Property.Id.Value, item.ImageFileHolder, isWrongYear, minimumDateTime, item.RelativePath, resizedFileHolder); |  | ||||||
|         return result; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public class MappingFromLocation : Properties.IMappingFromLocation |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public int AreaPermyriad { init; get; } |  | ||||||
|     public int ConfidencePercent { init; get; } |  | ||||||
|     public string DeterministicHashCodeKey { init; get; } |  | ||||||
|     public int NormalizedRectangle { init; get; } |  | ||||||
|  |  | ||||||
|     [JsonConstructor] |  | ||||||
|     public MappingFromLocation(int areaPermyriad, int confidencePercent, string deterministicHashCodeKey, int normalizedRectangle) |  | ||||||
|     { |  | ||||||
|         AreaPermyriad = areaPermyriad; |  | ||||||
|         ConfidencePercent = confidencePercent; |  | ||||||
|         DeterministicHashCodeKey = deterministicHashCodeKey; |  | ||||||
|         NormalizedRectangle = normalizedRectangle; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     public override string ToString() |  | ||||||
|     { |  | ||||||
|         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); |  | ||||||
|         return result; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public class MappingFromFilter : Properties.IMappingFromFilter |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public bool? IsFocusModel { init; get; } |  | ||||||
|     public bool? IsFocusRelativePath { init; get; } |  | ||||||
|     public bool? IsIgnoreRelativePath { init; get; } |  | ||||||
|     public bool? InSkipCollection { init; get; } |  | ||||||
|  |  | ||||||
|     [JsonConstructor] |  | ||||||
|     public MappingFromFilter(bool? isFocusModel, bool? isFocusRelativePath, bool? isIgnoreRelativePath, bool? inSkipCollection) |  | ||||||
|     { |  | ||||||
|         IsFocusModel = isFocusModel; |  | ||||||
|         IsFocusRelativePath = isFocusRelativePath; |  | ||||||
|         IsIgnoreRelativePath = isIgnoreRelativePath; |  | ||||||
|         InSkipCollection = inSkipCollection; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     public override string ToString() |  | ||||||
|     { |  | ||||||
|         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); |  | ||||||
|         return result; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public class MappingFromPhotoPrism : Properties.IMappingFromPhotoPrism |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public DatabaseFile DatabaseFile { init; get; } |  | ||||||
|     public List<Marker> Markers { init; get; } |  | ||||||
|  |  | ||||||
|     [JsonConstructor] |  | ||||||
|     public MappingFromPhotoPrism(DatabaseFile databaseFile, List<Marker> markers) |  | ||||||
|     { |  | ||||||
|         DatabaseFile = databaseFile; |  | ||||||
|         Markers = markers; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public class MappingFromPerson : Properties.IMappingFromPerson |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public int? ApproximateYears { init; get; } |  | ||||||
|     public string DisplayDirectoryName { init; get; } |  | ||||||
|     public PersonBirthday PersonBirthday { init; get; } |  | ||||||
|     public string SegmentB { init; get; } |  | ||||||
|  |  | ||||||
|     [JsonConstructor] |  | ||||||
|     public MappingFromPerson(int? approximateYears, string displayDirectoryName, PersonBirthday personBirthday, string segmentB) |  | ||||||
|     { |  | ||||||
|         ApproximateYears = approximateYears; |  | ||||||
|         DisplayDirectoryName = displayDirectoryName; |  | ||||||
|         PersonBirthday = personBirthday; |  | ||||||
|         SegmentB = segmentB; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     public override string ToString() |  | ||||||
|     { |  | ||||||
|         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); |  | ||||||
|         return result; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public class Mapping : Properties.IMapping | public class Mapping : Properties.IMapping | ||||||
| { | { | ||||||
|  |  | ||||||
|  | |||||||
							
								
								
									
										29
									
								
								Shared/Models/MappingFromFilter.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										29
									
								
								Shared/Models/MappingFromFilter.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,29 @@ | |||||||
|  | using System.Text.Json; | ||||||
|  | using System.Text.Json.Serialization; | ||||||
|  |  | ||||||
|  | namespace View_by_Distance.Shared.Models; | ||||||
|  |  | ||||||
|  | public class MappingFromFilter : Properties.IMappingFromFilter | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public bool? IsFocusModel { init; get; } | ||||||
|  |     public bool? IsFocusRelativePath { init; get; } | ||||||
|  |     public bool? IsIgnoreRelativePath { init; get; } | ||||||
|  |     public bool? InSkipCollection { init; get; } | ||||||
|  |  | ||||||
|  |     [JsonConstructor] | ||||||
|  |     public MappingFromFilter(bool? isFocusModel, bool? isFocusRelativePath, bool? isIgnoreRelativePath, bool? inSkipCollection) | ||||||
|  |     { | ||||||
|  |         IsFocusModel = isFocusModel; | ||||||
|  |         IsFocusRelativePath = isFocusRelativePath; | ||||||
|  |         IsIgnoreRelativePath = isIgnoreRelativePath; | ||||||
|  |         InSkipCollection = inSkipCollection; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     public override string ToString() | ||||||
|  |     { | ||||||
|  |         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); | ||||||
|  |         return result; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										58
									
								
								Shared/Models/MappingFromItem.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										58
									
								
								Shared/Models/MappingFromItem.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,58 @@ | |||||||
|  | using System.Text.Json; | ||||||
|  | using System.Text.Json.Serialization; | ||||||
|  |  | ||||||
|  | namespace View_by_Distance.Shared.Models; | ||||||
|  |  | ||||||
|  | public class MappingFromItem : Properties.IMappingFromItem | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public DateTime[] ContainerDateTimes { init; get; } | ||||||
|  |     public DateTime? DateTimeDigitized { init; get; } | ||||||
|  |     public DateTime? DateTimeOriginal { init; get; } | ||||||
|  |     public int Id { init; get; } | ||||||
|  |     public FileHolder ImageFileHolder { init; get; } | ||||||
|  |     public bool? IsWrongYear { init; get; } | ||||||
|  |     public DateTime MinimumDateTime { init; get; } | ||||||
|  |     public string? Model { init; get; } | ||||||
|  |     public string RelativePath { init; get; } | ||||||
|  |     public FileHolder ResizedFileHolder { init; get; } | ||||||
|  |  | ||||||
|  |     [JsonConstructor] | ||||||
|  |     public MappingFromItem(DateTime[] containerDateTimes, DateTime? dateTimeDigitized, DateTime? dateTimeOriginal, int id, FileHolder imageFileHolder, bool? isWrongYear, DateTime minimumDateTime, string? model, string relativePath, FileHolder resizedFileHolder) | ||||||
|  |     { | ||||||
|  |         ContainerDateTimes = containerDateTimes; | ||||||
|  |         DateTimeDigitized = dateTimeDigitized; | ||||||
|  |         DateTimeOriginal = dateTimeOriginal; | ||||||
|  |         Id = id; | ||||||
|  |         ImageFileHolder = imageFileHolder; | ||||||
|  |         IsWrongYear = isWrongYear; | ||||||
|  |         MinimumDateTime = minimumDateTime; | ||||||
|  |         Model = model; | ||||||
|  |         RelativePath = relativePath; | ||||||
|  |         ResizedFileHolder = resizedFileHolder; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     public override string ToString() | ||||||
|  |     { | ||||||
|  |         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); | ||||||
|  |         return result; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     public DateTime GetDateTimeOriginalThenMinimumDateTime() => | ||||||
|  |         DateTimeOriginal is not null ? DateTimeOriginal.Value : MinimumDateTime; | ||||||
|  |  | ||||||
|  |     internal static MappingFromItem GetMappingFromItem(DateTime[] containerDateTimes, Item item, FileHolder? resizedFileHolder) | ||||||
|  |     { | ||||||
|  |         MappingFromItem result; | ||||||
|  |         if (item.Property?.Id is null) | ||||||
|  |             throw new NotSupportedException(); | ||||||
|  |         if (resizedFileHolder is null) | ||||||
|  |             throw new NotSupportedException(); | ||||||
|  |         List<DateTime> dateTimes = item.Property.GetDateTimes(); | ||||||
|  |         DateTime minimumDateTime = Stateless.Methods.IProperty.GetMinimumDateTime(item.Property); | ||||||
|  |         (bool? isWrongYear, _) = Stateless.Methods.IProperty.IsWrongYear(item.ImageFileHolder, item.Property.DateTimeOriginal, dateTimes); | ||||||
|  |         result = new(containerDateTimes, item.Property.DateTimeDigitized, item.Property.DateTimeOriginal, item.Property.Id.Value, item.ImageFileHolder, isWrongYear, minimumDateTime, item.Property.Model, item.RelativePath, resizedFileHolder); | ||||||
|  |         return result; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										29
									
								
								Shared/Models/MappingFromLocation.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										29
									
								
								Shared/Models/MappingFromLocation.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,29 @@ | |||||||
|  | using System.Text.Json; | ||||||
|  | using System.Text.Json.Serialization; | ||||||
|  |  | ||||||
|  | namespace View_by_Distance.Shared.Models; | ||||||
|  |  | ||||||
|  | public class MappingFromLocation : Properties.IMappingFromLocation | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public int AreaPermyriad { init; get; } | ||||||
|  |     public int ConfidencePercent { init; get; } | ||||||
|  |     public string DeterministicHashCodeKey { init; get; } | ||||||
|  |     public int NormalizedRectangle { init; get; } | ||||||
|  |  | ||||||
|  |     [JsonConstructor] | ||||||
|  |     public MappingFromLocation(int areaPermyriad, int confidencePercent, string deterministicHashCodeKey, int normalizedRectangle) | ||||||
|  |     { | ||||||
|  |         AreaPermyriad = areaPermyriad; | ||||||
|  |         ConfidencePercent = confidencePercent; | ||||||
|  |         DeterministicHashCodeKey = deterministicHashCodeKey; | ||||||
|  |         NormalizedRectangle = normalizedRectangle; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     public override string ToString() | ||||||
|  |     { | ||||||
|  |         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); | ||||||
|  |         return result; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										29
									
								
								Shared/Models/MappingFromPerson.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										29
									
								
								Shared/Models/MappingFromPerson.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,29 @@ | |||||||
|  | using System.Text.Json; | ||||||
|  | using System.Text.Json.Serialization; | ||||||
|  |  | ||||||
|  | namespace View_by_Distance.Shared.Models; | ||||||
|  |  | ||||||
|  | public class MappingFromPerson : Properties.IMappingFromPerson | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public int? ApproximateYears { init; get; } | ||||||
|  |     public string DisplayDirectoryName { init; get; } | ||||||
|  |     public PersonBirthday PersonBirthday { init; get; } | ||||||
|  |     public string SegmentB { init; get; } | ||||||
|  |  | ||||||
|  |     [JsonConstructor] | ||||||
|  |     public MappingFromPerson(int? approximateYears, string displayDirectoryName, PersonBirthday personBirthday, string segmentB) | ||||||
|  |     { | ||||||
|  |         ApproximateYears = approximateYears; | ||||||
|  |         DisplayDirectoryName = displayDirectoryName; | ||||||
|  |         PersonBirthday = personBirthday; | ||||||
|  |         SegmentB = segmentB; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     public override string ToString() | ||||||
|  |     { | ||||||
|  |         string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true }); | ||||||
|  |         return result; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										18
									
								
								Shared/Models/MappingFromPhotoPrism.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										18
									
								
								Shared/Models/MappingFromPhotoPrism.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,18 @@ | |||||||
|  | using System.Text.Json.Serialization; | ||||||
|  |  | ||||||
|  | namespace View_by_Distance.Shared.Models; | ||||||
|  |  | ||||||
|  | public class MappingFromPhotoPrism : Properties.IMappingFromPhotoPrism | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public DatabaseFile DatabaseFile { init; get; } | ||||||
|  |     public List<Marker> Markers { init; get; } | ||||||
|  |  | ||||||
|  |     [JsonConstructor] | ||||||
|  |     public MappingFromPhotoPrism(DatabaseFile databaseFile, List<Marker> markers) | ||||||
|  |     { | ||||||
|  |         DatabaseFile = databaseFile; | ||||||
|  |         Markers = markers; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  | } | ||||||
| @ -4,11 +4,11 @@ public interface IFaceDistance | |||||||
| { | { | ||||||
|  |  | ||||||
|     public int? ConfidencePercent { init; get; } |     public int? ConfidencePercent { init; get; } | ||||||
|  |     public DateTime DateTimeOriginalThenMinimumDateTime { init; get; } | ||||||
|     public object? Encoding { init; get; } |     public object? Encoding { init; get; } | ||||||
|     public int Id { init; get; } |     public int Id { init; get; } | ||||||
|     public bool? IsWrongYear { init; get; } |     public bool? IsWrongYear { init; get; } | ||||||
|     public double? Length { init; get; } |     public double? Length { init; get; } | ||||||
|     public DateTime? MinimumDateTime { init; get; } |  | ||||||
|     public int? NormalizedRectangle { init; get; } |     public int? NormalizedRectangle { init; get; } | ||||||
|  |  | ||||||
| } | } | ||||||
| @ -6,7 +6,8 @@ public interface IItem | |||||||
|     public bool? FileSizeChanged { get; } |     public bool? FileSizeChanged { get; } | ||||||
|     public List<Face> Faces { get; } |     public List<Face> Faces { get; } | ||||||
|     public FileHolder ImageFileHolder { get; } |     public FileHolder ImageFileHolder { get; } | ||||||
|     public bool? IsUniqueFileName { get; } |     public bool? IsNotUniqueAndNeedsReview { get; } | ||||||
|  |     public bool IsUniqueFileName { get; } | ||||||
|     public bool IsValidImageFormatExtension { get; } |     public bool IsValidImageFormatExtension { get; } | ||||||
|     public bool? Moved { get; } |     public bool? Moved { get; } | ||||||
|     public Property? Property { get; } |     public Property? Property { get; } | ||||||
|  | |||||||
| @ -1,56 +1,5 @@ | |||||||
| namespace View_by_Distance.Shared.Models.Properties; | namespace View_by_Distance.Shared.Models.Properties; | ||||||
|  |  | ||||||
| public interface IMappingFromItem |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public DateTime[] ContainerDateTimes { init; get; } |  | ||||||
|     public int Id { init; get; } |  | ||||||
|     public FileHolder ImageFileHolder { init; get; } |  | ||||||
|     public bool? IsWrongYear { init; get; } |  | ||||||
|     public DateTime MinimumDateTime { init; get; } |  | ||||||
|     public string RelativePath { init; get; } |  | ||||||
|     public FileHolder ResizedFileHolder { init; get; } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public interface IMappingFromFilter |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public bool? IsFocusModel { init; get; } |  | ||||||
|     public bool? IsFocusRelativePath { init; get; } |  | ||||||
|     public bool? IsIgnoreRelativePath { init; get; } |  | ||||||
|     public bool? InSkipCollection { init; get; } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public interface IMappingFromLocation |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public int AreaPermyriad { init; get; } |  | ||||||
|     public int ConfidencePercent { init; get; } |  | ||||||
|     public string DeterministicHashCodeKey { init; get; } |  | ||||||
|     public int NormalizedRectangle { init; get; } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public interface IMappingFromPhotoPrism |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public DatabaseFile DatabaseFile { init; get; } |  | ||||||
|     public List<Marker> Markers { init; get; } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public interface IMappingFromPerson |  | ||||||
| { |  | ||||||
|  |  | ||||||
|     public int? ApproximateYears { init; get; } |  | ||||||
|     public string DisplayDirectoryName { init; get; } |  | ||||||
|     public PersonBirthday PersonBirthday { init; get; } |  | ||||||
|     public string SegmentB { init; get; } |  | ||||||
|  |  | ||||||
| } |  | ||||||
|  |  | ||||||
| public interface IMapping | public interface IMapping | ||||||
| { | { | ||||||
|  |  | ||||||
|  | |||||||
							
								
								
									
										11
									
								
								Shared/Models/Properties/IMappingFromFilter.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								Shared/Models/Properties/IMappingFromFilter.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,11 @@ | |||||||
|  | namespace View_by_Distance.Shared.Models.Properties; | ||||||
|  |  | ||||||
|  | public interface IMappingFromFilter | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public bool? IsFocusModel { init; get; } | ||||||
|  |     public bool? IsFocusRelativePath { init; get; } | ||||||
|  |     public bool? IsIgnoreRelativePath { init; get; } | ||||||
|  |     public bool? InSkipCollection { init; get; } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										17
									
								
								Shared/Models/Properties/IMappingFromItem.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										17
									
								
								Shared/Models/Properties/IMappingFromItem.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,17 @@ | |||||||
|  | namespace View_by_Distance.Shared.Models.Properties; | ||||||
|  |  | ||||||
|  | public interface IMappingFromItem | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public DateTime[] ContainerDateTimes { init; get; } | ||||||
|  |     public DateTime? DateTimeDigitized { init; get; } | ||||||
|  |     public DateTime? DateTimeOriginal { init; get; } | ||||||
|  |     public int Id { init; get; } | ||||||
|  |     public FileHolder ImageFileHolder { init; get; } | ||||||
|  |     public bool? IsWrongYear { init; get; } | ||||||
|  |     public DateTime MinimumDateTime { init; get; } | ||||||
|  |     public string? Model { init; get; } | ||||||
|  |     public string RelativePath { init; get; } | ||||||
|  |     public FileHolder ResizedFileHolder { init; get; } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										11
									
								
								Shared/Models/Properties/IMappingFromLocation.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								Shared/Models/Properties/IMappingFromLocation.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,11 @@ | |||||||
|  | namespace View_by_Distance.Shared.Models.Properties; | ||||||
|  |  | ||||||
|  | public interface IMappingFromLocation | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public int AreaPermyriad { init; get; } | ||||||
|  |     public int ConfidencePercent { init; get; } | ||||||
|  |     public string DeterministicHashCodeKey { init; get; } | ||||||
|  |     public int NormalizedRectangle { init; get; } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										11
									
								
								Shared/Models/Properties/IMappingFromPerson.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								Shared/Models/Properties/IMappingFromPerson.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,11 @@ | |||||||
|  | namespace View_by_Distance.Shared.Models.Properties; | ||||||
|  |  | ||||||
|  | public interface IMappingFromPerson | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public int? ApproximateYears { init; get; } | ||||||
|  |     public string DisplayDirectoryName { init; get; } | ||||||
|  |     public PersonBirthday PersonBirthday { init; get; } | ||||||
|  |     public string SegmentB { init; get; } | ||||||
|  |  | ||||||
|  | } | ||||||
							
								
								
									
										9
									
								
								Shared/Models/Properties/IMappingFromPhotoPrism.cs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										9
									
								
								Shared/Models/Properties/IMappingFromPhotoPrism.cs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,9 @@ | |||||||
|  | namespace View_by_Distance.Shared.Models.Properties; | ||||||
|  |  | ||||||
|  | public interface IMappingFromPhotoPrism | ||||||
|  | { | ||||||
|  |  | ||||||
|  |     public DatabaseFile DatabaseFile { init; get; } | ||||||
|  |     public List<Marker> Markers { init; get; } | ||||||
|  |  | ||||||
|  | } | ||||||
| @ -3,19 +3,19 @@ namespace View_by_Distance.Shared.Models.Properties; | |||||||
| public interface IProperty | public interface IProperty | ||||||
| { | { | ||||||
|  |  | ||||||
|     public DateTime CreationTime { get; } |     public DateTime CreationTime { init; get; } | ||||||
|     public DateTime? DateTime { get; } |     public DateTime? DateTime { init; get; } | ||||||
|     public DateTime? DateTimeDigitized { get; } |     public DateTime? DateTimeDigitized { init; get; } | ||||||
|     public DateTime? DateTimeFromName { get; } |     public DateTime? DateTimeFromName { init; get; } | ||||||
|     public DateTime? DateTimeOriginal { get; } |     public DateTime? DateTimeOriginal { init; get; } | ||||||
|     public long FileSize { get; } |     public long FileSize { init; get; } | ||||||
|     public DateTime? GPSDateStamp { get; } |     public DateTime? GPSDateStamp { init; get; } | ||||||
|     public int? Height { get; } |     public int? Height { init; get; } | ||||||
|     public int? Id { get; } |     public int? Id { init; get; } | ||||||
|     public DateTime LastWriteTime { get; } |     public DateTime LastWriteTime { init; get; } | ||||||
|     public string Make { get; } |     public string? Make { init; get; } | ||||||
|     public string Model { get; } |     public string? Model { init; get; } | ||||||
|     public string Orientation { get; } |     public string? Orientation { init; get; } | ||||||
|     public int? Width { get; } |     public int? Width { init; get; } | ||||||
|  |  | ||||||
| } | } | ||||||
| @ -13,7 +13,6 @@ public interface IPropertyConfiguration | |||||||
|     public string ResultContent { init; get; } |     public string ResultContent { init; get; } | ||||||
|     public string ResultSingleton { init; get; } |     public string ResultSingleton { init; get; } | ||||||
|     public string[] ValidImageFormatExtensions { init; get; } |     public string[] ValidImageFormatExtensions { init; get; } | ||||||
|     public string[] VerifyToSeason { init; get; } |  | ||||||
|     public string? ModelName { get; } |     public string? ModelName { get; } | ||||||
|     public int? NumberOfJitters { get; } |     public int? NumberOfJitters { get; } | ||||||
|     public int? NumberOfTimesToUpsample { get; } |     public int? NumberOfTimesToUpsample { get; } | ||||||
|  | |||||||
| @ -6,52 +6,38 @@ namespace View_by_Distance.Shared.Models; | |||||||
| public class Property : Properties.IProperty | public class Property : Properties.IProperty | ||||||
| { | { | ||||||
|  |  | ||||||
|     protected DateTime _CreationTime; |     public DateTime CreationTime { init; get; } | ||||||
|     protected DateTime? _DateTime; |     public DateTime? DateTime { init; get; } | ||||||
|     protected DateTime? _DateTimeDigitized; |     public DateTime? DateTimeDigitized { init; get; } | ||||||
|     protected DateTime? _DateTimeFromName; |     public DateTime? DateTimeFromName { init; get; } | ||||||
|     protected DateTime? _DateTimeOriginal; |     public DateTime? DateTimeOriginal { init; get; } | ||||||
|     protected long _FileSize; |     public long FileSize { init; get; } | ||||||
|     protected DateTime? _GPSDateStamp; |     public DateTime? GPSDateStamp { init; get; } | ||||||
|     protected int? _Height; |     public int? Height { init; get; } | ||||||
|     protected int? _Id; |     public int? Id { init; get; } | ||||||
|     protected DateTime _LastWriteTime; |     public DateTime LastWriteTime { init; get; } | ||||||
|     protected string _Make; |     public string? Make { init; get; } | ||||||
|     protected string _Model; |     public string? Model { init; get; } | ||||||
|     protected string _Orientation; |     public string? Orientation { init; get; } | ||||||
|     protected int? _Width; |     public int? Width { init; get; } | ||||||
|     public DateTime CreationTime => _CreationTime; |  | ||||||
|     public DateTime? DateTime => _DateTime; |  | ||||||
|     public DateTime? DateTimeDigitized => _DateTimeDigitized; |  | ||||||
|     public DateTime? DateTimeFromName => _DateTimeFromName; |  | ||||||
|     public DateTime? DateTimeOriginal => _DateTimeOriginal; |  | ||||||
|     public long FileSize => _FileSize; |  | ||||||
|     public DateTime? GPSDateStamp => _GPSDateStamp; |  | ||||||
|     public int? Height => _Height; |  | ||||||
|     public int? Id => _Id; |  | ||||||
|     public DateTime LastWriteTime => _LastWriteTime; |  | ||||||
|     public string Make => _Make; |  | ||||||
|     public string Model => _Model; |  | ||||||
|     public string Orientation => _Orientation; |  | ||||||
|     public int? Width => _Width; |  | ||||||
|  |  | ||||||
|     [JsonConstructor] |     [JsonConstructor] | ||||||
|     public Property(DateTime creationTime, DateTime? dateTime, DateTime? dateTimeDigitized, DateTime? dateTimeFromName, DateTime? dateTimeOriginal, long fileSize, DateTime? gpsDateStamp, int? height, int? id, DateTime lastWriteTime, string make, string model, string orientation, int? width) |     public Property(DateTime creationTime, DateTime? dateTime, DateTime? dateTimeDigitized, DateTime? dateTimeFromName, DateTime? dateTimeOriginal, long fileSize, DateTime? gpsDateStamp, int? height, int? id, DateTime lastWriteTime, string? make, string? model, string? orientation, int? width) | ||||||
|     { |     { | ||||||
|         _DateTimeFromName = dateTimeFromName; |         DateTimeFromName = dateTimeFromName; | ||||||
|         _CreationTime = creationTime; |         CreationTime = creationTime; | ||||||
|         _DateTime = dateTime; |         DateTime = dateTime; | ||||||
|         _DateTimeDigitized = dateTimeDigitized; |         DateTimeDigitized = dateTimeDigitized; | ||||||
|         _DateTimeOriginal = dateTimeOriginal; |         DateTimeOriginal = dateTimeOriginal; | ||||||
|         _FileSize = fileSize; |         FileSize = fileSize; | ||||||
|         _GPSDateStamp = gpsDateStamp; |         GPSDateStamp = gpsDateStamp; | ||||||
|         _Height = height; |         Height = height; | ||||||
|         _Id = id; |         Id = id; | ||||||
|         _LastWriteTime = lastWriteTime; |         LastWriteTime = lastWriteTime; | ||||||
|         _Make = make; |         Make = make; | ||||||
|         _Model = model; |         Model = model; | ||||||
|         _Orientation = orientation; |         Orientation = orientation; | ||||||
|         _Width = width; |         Width = width; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     public override string ToString() |     public override string ToString() | ||||||
| @ -60,38 +46,6 @@ public class Property : Properties.IProperty | |||||||
|         return result; |         return result; | ||||||
|     } // ... |     } // ... | ||||||
|  |  | ||||||
|     public List<DateTime> GetDateTimes() => Stateless.Methods.Property.GetDateTimes(_CreationTime, _LastWriteTime, _DateTime, _DateTimeDigitized, _DateTimeFromName, _DateTimeOriginal, _GPSDateStamp); |     public List<DateTime> GetDateTimes() => Stateless.Methods.Property.GetDateTimes(CreationTime, LastWriteTime, DateTime, DateTimeDigitized, DateTimeFromName, DateTimeOriginal, GPSDateStamp); | ||||||
|  |  | ||||||
|     public (bool?, string[]) IsWrongYear(FileHolder fileHolder, DateTime? minimumDateTime) |  | ||||||
|     { |  | ||||||
|         string[] results = Array.Empty<string>(); |  | ||||||
|         bool? result = null; |  | ||||||
|         string year; |  | ||||||
|         string directoryName; |  | ||||||
|         string[] directorySegments; |  | ||||||
|         string? check = Path.GetFullPath(fileHolder.FullName); |  | ||||||
|         string? pathRoot = Path.GetPathRoot(fileHolder.FullName); |  | ||||||
|         if (string.IsNullOrEmpty(pathRoot)) |  | ||||||
|             throw new Exception(); |  | ||||||
|         if (minimumDateTime.HasValue) |  | ||||||
|             year = minimumDateTime.Value.ToString("yyyy"); |  | ||||||
|         else |  | ||||||
|         { |  | ||||||
|             List<DateTime> dateTimes = GetDateTimes(); |  | ||||||
|             year = dateTimes.Min().ToString("yyyy"); |  | ||||||
|         } |  | ||||||
|         for (int i = 0; i < int.MaxValue; i++) |  | ||||||
|         { |  | ||||||
|             check = Path.GetDirectoryName(check); |  | ||||||
|             if (string.IsNullOrEmpty(check) || check == pathRoot) |  | ||||||
|                 break; |  | ||||||
|             directoryName = Path.GetFileName(check); |  | ||||||
|             directorySegments = directoryName.Split(' '); |  | ||||||
|             (result, results) = Stateless.Methods.Property.IsWrongYear(directorySegments, year); |  | ||||||
|             if (result.HasValue) |  | ||||||
|                 break; |  | ||||||
|         } |  | ||||||
|         return new(result, results); |  | ||||||
|     } |  | ||||||
|  |  | ||||||
| } | } | ||||||
| @ -144,7 +144,7 @@ internal abstract class Container | |||||||
|             File.SetCreationTime(sourceDirectoryFileHolder.FullName, imageFileInfo.LastWriteTime.Value); |             File.SetCreationTime(sourceDirectoryFileHolder.FullName, imageFileInfo.LastWriteTime.Value); | ||||||
|             File.SetLastWriteTime(sourceDirectoryFileHolder.FullName, sourceDirectoryFileHolder.LastWriteTime.Value); |             File.SetLastWriteTime(sourceDirectoryFileHolder.FullName, sourceDirectoryFileHolder.LastWriteTime.Value); | ||||||
|         } |         } | ||||||
|         Models.Item item = new(sourceDirectoryFileHolder, relativePath, imageFileInfo, filePair.IsUnique, isValidImageFormatExtension, property, abandoned, fileSizeChanged, lastWriteTimeChanged); |         Models.Item item = new(sourceDirectoryFileHolder, relativePath, imageFileInfo, filePair.IsNotUniqueAndNeedsReview, filePair.IsUnique, isValidImageFormatExtension, property, abandoned, fileSizeChanged, lastWriteTimeChanged); | ||||||
|         lock (results) |         lock (results) | ||||||
|             results.Add(new(filePair.Path, imageFileInfo.DirectoryName, filePair.IsUnique, filePair.Collection, item)); |             results.Add(new(filePair.Path, imageFileInfo.DirectoryName, filePair.IsUnique, filePair.Collection, item)); | ||||||
|     } |     } | ||||||
|  | |||||||
| @ -11,11 +11,6 @@ public interface IProperty | |||||||
|     static int GetDeterministicHashCode(byte[] value) => |     static int GetDeterministicHashCode(byte[] value) => | ||||||
|         Property.GetDeterministicHashCode(value); |         Property.GetDeterministicHashCode(value); | ||||||
|  |  | ||||||
|     int TestStatic_GetDeterministicHashCode(string value) => |  | ||||||
|         GetDeterministicHashCode(value); |  | ||||||
|     static int GetDeterministicHashCode(string value) => |  | ||||||
|         Property.GetDeterministicHashCode(value); |  | ||||||
|  |  | ||||||
|     DateTime TestStatic_GetDateTime(Models.Property? property) => |     DateTime TestStatic_GetDateTime(Models.Property? property) => | ||||||
|         GetDateTime(property); |         GetDateTime(property); | ||||||
|     static DateTime GetDateTime(Models.Property? property) => |     static DateTime GetDateTime(Models.Property? property) => | ||||||
| @ -46,6 +41,11 @@ public interface IProperty | |||||||
|     static (bool?, string[]) IsWrongYear(string[] segments, string year) => |     static (bool?, string[]) IsWrongYear(string[] segments, string year) => | ||||||
|         Property.IsWrongYear(segments, year); |         Property.IsWrongYear(segments, year); | ||||||
|  |  | ||||||
|  |     (bool?, string[]) TestStatic_IsWrongYear(Models.FileHolder fileHolder, DateTime? dateTimeOriginal, List<DateTime> dateTimes) => | ||||||
|  |         IsWrongYear(fileHolder, dateTimeOriginal, dateTimes); | ||||||
|  |     static (bool?, string[]) IsWrongYear(Models.FileHolder fileHolder, DateTime? dateTimeOriginal, List<DateTime> dateTimes) => | ||||||
|  |         Property.IsWrongYear(fileHolder, dateTimeOriginal, dateTimes); | ||||||
|  |  | ||||||
|     (DateTime?[], int?, string?) TestStatic_Get(Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension) => |     (DateTime?[], int?, string?) TestStatic_Get(Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension) => | ||||||
|         Get(fileHolder, isIgnoreExtension, isValidImageFormatExtension); |         Get(fileHolder, isIgnoreExtension, isValidImageFormatExtension); | ||||||
|     static (DateTime?[], int?, string?) Get(Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension) => |     static (DateTime?[], int?, string?) Get(Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension) => | ||||||
|  | |||||||
| @ -42,25 +42,6 @@ internal abstract class Property | |||||||
|         return result; |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     internal static int GetDeterministicHashCode(string value) |  | ||||||
|     { |  | ||||||
|         int result; |  | ||||||
|         unchecked |  | ||||||
|         { |  | ||||||
|             int hash1 = (5381 << 16) + 5381; |  | ||||||
|             int hash2 = hash1; |  | ||||||
|             for (int i = 0; i < value.Length; i += 2) |  | ||||||
|             { |  | ||||||
|                 hash1 = ((hash1 << 5) + hash1) ^ value[i]; |  | ||||||
|                 if (i == value.Length - 1) |  | ||||||
|                     break; |  | ||||||
|                 hash2 = ((hash2 << 5) + hash2) ^ value[i + 1]; |  | ||||||
|             } |  | ||||||
|             result = hash1 + (hash2 * 1566083941); |  | ||||||
|         } |  | ||||||
|         return result; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     internal static (bool?, string[]) IsWrongYear(string[] segments, string year) |     internal static (bool?, string[]) IsWrongYear(string[] segments, string year) | ||||||
|     { |     { | ||||||
|         bool? result; |         bool? result; | ||||||
| @ -92,6 +73,45 @@ internal abstract class Property | |||||||
|         return new(result, results); |         return new(result, results); | ||||||
|     } |     } | ||||||
|  |  | ||||||
|  |     internal static (bool?, string[]) IsWrongYear(Models.FileHolder fileHolder, DateTime? dateTimeOriginal, List<DateTime> dateTimes) | ||||||
|  |     { | ||||||
|  |         string[] results = Array.Empty<string>(); | ||||||
|  |         bool? result = null; | ||||||
|  |         string year; | ||||||
|  |         string directoryName; | ||||||
|  |         string[] directorySegments; | ||||||
|  |         List<DateTime> collection = new(); | ||||||
|  |         string? check = Path.GetFullPath(fileHolder.FullName); | ||||||
|  |         string? pathRoot = Path.GetPathRoot(fileHolder.FullName); | ||||||
|  |         if (string.IsNullOrEmpty(pathRoot)) | ||||||
|  |             throw new Exception(); | ||||||
|  |         if (dateTimeOriginal is not null) | ||||||
|  |             collection.Add(dateTimeOriginal.Value); | ||||||
|  |         else | ||||||
|  |         { | ||||||
|  |             foreach (DateTime dateTime in dateTimes) | ||||||
|  |                 collection.Add(dateTime); | ||||||
|  |         } | ||||||
|  |         foreach (DateTime dateTime in collection) | ||||||
|  |         { | ||||||
|  |             year = dateTime.ToString("yyyy"); | ||||||
|  |             for (int i = 0; i < int.MaxValue; i++) | ||||||
|  |             { | ||||||
|  |                 check = Path.GetDirectoryName(check); | ||||||
|  |                 if (string.IsNullOrEmpty(check) || check == pathRoot) | ||||||
|  |                     break; | ||||||
|  |                 directoryName = Path.GetFileName(check); | ||||||
|  |                 directorySegments = directoryName.Split(' '); | ||||||
|  |                 (result, results) = IsWrongYear(directorySegments, year); | ||||||
|  |                 if (result is not null) | ||||||
|  |                     break; | ||||||
|  |             } | ||||||
|  |             if (result is not null && result.Value) | ||||||
|  |                 break; | ||||||
|  |         } | ||||||
|  |         return new(result, results); | ||||||
|  |     } | ||||||
|  |  | ||||||
|     internal static DateTime? GetDateTimeFromName(Models.FileHolder fileHolder) |     internal static DateTime? GetDateTimeFromName(Models.FileHolder fileHolder) | ||||||
|     { |     { | ||||||
|         DateTime? result = null; |         DateTime? result = null; | ||||||
|  | |||||||
| @ -10,10 +10,7 @@ internal abstract class Sorting | |||||||
|             throw new NotSupportedException(); |             throw new NotSupportedException(); | ||||||
|         if (faceDistanceLength.NormalizedRectangle is null) |         if (faceDistanceLength.NormalizedRectangle is null) | ||||||
|             throw new NotSupportedException(); |             throw new NotSupportedException(); | ||||||
|         if (faceDistanceEncoding.MinimumDateTime is null || faceDistanceLength.MinimumDateTime is null) |         TimeSpan timeSpan = new(faceDistanceLength.DateTimeOriginalThenMinimumDateTime.Ticks - faceDistanceEncoding.DateTimeOriginalThenMinimumDateTime.Ticks); | ||||||
|             throw new NotSupportedException(); |  | ||||||
|         long ticks = faceDistanceEncoding.MinimumDateTime.Value.Ticks; |  | ||||||
|         TimeSpan timeSpan = new(faceDistanceLength.MinimumDateTime.Value.Ticks - ticks); |  | ||||||
|         bool older = timeSpan.TotalMilliseconds < 0; |         bool older = timeSpan.TotalMilliseconds < 0; | ||||||
|         int daysDelta = (int)Math.Round(Math.Abs(timeSpan.TotalDays), 0); |         int daysDelta = (int)Math.Round(Math.Abs(timeSpan.TotalDays), 0); | ||||||
|         int distancePermyriad = (int)(faceDistanceLength.Length.Value / rangeDistanceTolerance * faceDistancePermyriad); |         int distancePermyriad = (int)(faceDistanceLength.Length.Value / rangeDistanceTolerance * faceDistancePermyriad); | ||||||
|  | |||||||
| @ -95,9 +95,9 @@ internal abstract partial class XDirectory | |||||||
|         return renameCollection.Count; |         return renameCollection.Count; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private static void IsNotUniqueLoop(string file, List<string> collection) |     private static bool GetIsNotUniqueAndNeedsReview(string file, List<string> collection) | ||||||
|     { |     { | ||||||
|         TimeSpan timeSpan; |         bool result = false; | ||||||
|         FileInfo possibleFileInfo; |         FileInfo possibleFileInfo; | ||||||
|         FileInfo fileInfo = new(file); |         FileInfo fileInfo = new(file); | ||||||
|         foreach (string possible in collection) |         foreach (string possible in collection) | ||||||
| @ -105,18 +105,14 @@ internal abstract partial class XDirectory | |||||||
|             if (possible == file) |             if (possible == file) | ||||||
|                 continue; |                 continue; | ||||||
|             possibleFileInfo = new(possible); |             possibleFileInfo = new(possible); | ||||||
|  |             if (possibleFileInfo.LastWriteTime != fileInfo.LastWriteTime) | ||||||
|  |                 File.SetLastWriteTime(file, new DateTime[] { possibleFileInfo.LastWriteTime, fileInfo.LastWriteTime }.Max()); | ||||||
|             if (possibleFileInfo.LastWriteTime == fileInfo.LastWriteTime && possibleFileInfo.Length == fileInfo.Length) |             if (possibleFileInfo.LastWriteTime == fileInfo.LastWriteTime && possibleFileInfo.Length == fileInfo.Length) | ||||||
|                 continue; |                 continue; | ||||||
|             timeSpan = new(possibleFileInfo.LastWriteTime.Ticks - fileInfo.LastWriteTime.Ticks); |             if (!result) | ||||||
|             if (possibleFileInfo.Length != fileInfo.Length) |                 result = true; | ||||||
|                 throw new Exception(Path.GetFileNameWithoutExtension(file)); |  | ||||||
|             if (timeSpan.TotalMinutes < 61) |  | ||||||
|             { |  | ||||||
|                 File.SetLastWriteTime(file, new DateTime[] { possibleFileInfo.LastWriteTime, fileInfo.LastWriteTime }.Min()); |  | ||||||
|                 continue; |  | ||||||
|             } |  | ||||||
|             throw new Exception(Path.GetFileNameWithoutExtension(file)); |  | ||||||
|         } |         } | ||||||
|  |         return result; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     private static string? GetMatch(string file, List<string> collection) |     private static string? GetMatch(string file, List<string> collection) | ||||||
| @ -148,28 +144,30 @@ internal abstract partial class XDirectory | |||||||
|         string fileName; |         string fileName; | ||||||
|         bool uniqueFileName; |         bool uniqueFileName; | ||||||
|         List<string>? collection; |         List<string>? collection; | ||||||
|  |         bool? isNotUniqueAndNeedsReview; | ||||||
|         foreach (string[] files in filesCollection) |         foreach (string[] files in filesCollection) | ||||||
|         { |         { | ||||||
|             foreach (string file in files) |             foreach (string file in files) | ||||||
|             { |             { | ||||||
|  |                 isNotUniqueAndNeedsReview = null; | ||||||
|                 fileName = Path.GetFileName(file); |                 fileName = Path.GetFileName(file); | ||||||
|                 if (!fileNamesToFiles.TryGetValue(fileName, out collection)) |                 if (!fileNamesToFiles.TryGetValue(fileName, out collection)) | ||||||
|                     throw new Exception(); |                     throw new Exception(); | ||||||
|                 uniqueFileName = collection.Count == 1; |                 uniqueFileName = collection.Count == 1; | ||||||
|                 if (!uniqueFileName) |                 if (!uniqueFileName) | ||||||
|                     IsNotUniqueLoop(file, collection); |                     isNotUniqueAndNeedsReview = GetIsNotUniqueAndNeedsReview(file, collection); | ||||||
|                 if (!compareFileNamesToFiles.TryGetValue(string.Concat(fileName, extension), out collection)) |                 if (!compareFileNamesToFiles.TryGetValue(string.Concat(fileName, extension), out collection)) | ||||||
|                     results.Add(new(file, uniqueFileName, new(), null)); |                     results.Add(new(file, uniqueFileName, isNotUniqueAndNeedsReview, new(), null)); | ||||||
|                 else |                 else | ||||||
|                 { |                 { | ||||||
|                     if (!collection.Any()) |                     if (!collection.Any()) | ||||||
|                         results.Add(new(file, uniqueFileName, collection, null)); |                         results.Add(new(file, uniqueFileName, isNotUniqueAndNeedsReview, collection, null)); | ||||||
|                     else if (uniqueFileName && collection.Count == 1) |                     else if (uniqueFileName && collection.Count == 1) | ||||||
|                         results.Add(new(file, uniqueFileName, collection, collection.First())); |                         results.Add(new(file, uniqueFileName, isNotUniqueAndNeedsReview, collection, collection.First())); | ||||||
|                     else |                     else | ||||||
|                     { |                     { | ||||||
|                         match = GetMatch(file, collection); |                         match = GetMatch(file, collection); | ||||||
|                         results.Add(new(file, uniqueFileName, collection, match)); |                         results.Add(new(file, uniqueFileName, isNotUniqueAndNeedsReview, collection, match)); | ||||||
|                     } |                     } | ||||||
|                 } |                 } | ||||||
|             } |             } | ||||||
|  | |||||||
| @ -762,13 +762,13 @@ public partial class UnitTestHardCoded | |||||||
|     public void TestMethodRename() |     public void TestMethodRename() | ||||||
|     { |     { | ||||||
|         // string[] directories = Directory.GetDirectories(@"D:\2) Images B\Not-Copy-Copy-1e85c0ba", "*;*", SearchOption.AllDirectories); |         // string[] directories = Directory.GetDirectories(@"D:\2) Images B\Not-Copy-Copy-1e85c0ba", "*;*", SearchOption.AllDirectories); | ||||||
|         // string[] directories = Directory.GetDirectories(@"D:\1) Images A\Images-1e85c0ba", "*;*", SearchOption.AllDirectories); |         string[] directories = Directory.GetDirectories(@"D:\1) Images A\Images-1e85c0ba", "*;*", SearchOption.AllDirectories); | ||||||
|         string[] directories = Directory.GetDirectories(@"D:\2) Images B\Not-Copy-Copy-1e85c0ba", "*", SearchOption.AllDirectories); |         // string[] directories = Directory.GetDirectories(@"D:\2) Images B\Not-Copy-Copy-1e85c0ba", "*", SearchOption.AllDirectories); | ||||||
|         foreach (string directory in directories.OrderByDescending(l => l.Length - l.Replace(@"\", string.Empty).Length)) |         foreach (string directory in directories.OrderByDescending(l => l.Length - l.Replace(@"\", string.Empty).Length)) | ||||||
|         { |         { | ||||||
|             if (directory.EndsWith(";9")) |             if (!directory.EndsWith(";9")) | ||||||
|                 continue; |                 continue; | ||||||
|             Directory.Move(directory, $"{directory};9"); |             Directory.Move(directory, $"{directory[..^2]} !9"); | ||||||
|         } |         } | ||||||
|         NonThrowTryCatch(); |         NonThrowTryCatch(); | ||||||
|     } |     } | ||||||
|  | |||||||
| @ -157,14 +157,15 @@ public class UnitTestResize | |||||||
|         _ = metadata.ToString(); |         _ = metadata.ToString(); | ||||||
|         C_Resize resize = new(_Configuration.ForceResizeLastWriteTimeToCreationTime, _Configuration.OverrideForResizeImages, _Configuration.PropertiesChangedForResize, _Configuration.ValidResolutions, imageCodecInfo, encoderParameters, filenameExtension); |         C_Resize resize = new(_Configuration.ForceResizeLastWriteTimeToCreationTime, _Configuration.OverrideForResizeImages, _Configuration.PropertiesChangedForResize, _Configuration.ValidResolutions, imageCodecInfo, encoderParameters, filenameExtension); | ||||||
|         _ = resize.ToString(); |         _ = resize.ToString(); | ||||||
|         bool? isUniqueFileName = null; |         bool isUniqueFileName = false; | ||||||
|  |         bool? isNotUniqueAndNeedsReview = null; | ||||||
|         FileHolder sourceDirectoryFileHolder = new(".json"); |         FileHolder sourceDirectoryFileHolder = new(".json"); | ||||||
|         FileHolder fileHolder = new(Path.Combine(sourceDirectory, sourceFileName)); |         FileHolder fileHolder = new(Path.Combine(sourceDirectory, sourceFileName)); | ||||||
|         string relativePath = IPath.GetRelativePath(fileHolder.FullName, length); |         string relativePath = IPath.GetRelativePath(fileHolder.FullName, length); | ||||||
|         sourceDirectory = Path.Combine(aPropertySingletonDirectory, sourceDirectoryName); |         sourceDirectory = Path.Combine(aPropertySingletonDirectory, sourceDirectoryName); | ||||||
|         propertyLogic.SetAngleBracketCollection(aResultsFullGroupDirectory, sourceDirectory); |         propertyLogic.SetAngleBracketCollection(aResultsFullGroupDirectory, sourceDirectory); | ||||||
|         resize.SetAngleBracketCollection(_Configuration.PropertyConfiguration, cResultsFullGroupDirectory, sourceDirectory); |         resize.SetAngleBracketCollection(_Configuration.PropertyConfiguration, cResultsFullGroupDirectory, sourceDirectory); | ||||||
|         item = new(sourceDirectoryFileHolder, relativePath, fileHolder, isUniqueFileName, isValidImageFormatExtension, property, false, false, false); |         item = new(sourceDirectoryFileHolder, relativePath, fileHolder, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, property, false, false, false); | ||||||
|         Assert.IsNotNull(item.ImageFileHolder); |         Assert.IsNotNull(item.ImageFileHolder); | ||||||
|         if (item.Property is null) |         if (item.Property is null) | ||||||
|         { |         { | ||||||
|  | |||||||
| @ -232,7 +232,8 @@ public class UnitTestFace | |||||||
|         _ = metadata.ToString(); |         _ = metadata.ToString(); | ||||||
|         C_Resize resize = new(_Configuration.ForceResizeLastWriteTimeToCreationTime, _Configuration.OverrideForResizeImages, _Configuration.PropertiesChangedForResize, _Configuration.ValidResolutions, imageCodecInfo, encoderParameters, filenameExtension); |         C_Resize resize = new(_Configuration.ForceResizeLastWriteTimeToCreationTime, _Configuration.OverrideForResizeImages, _Configuration.PropertiesChangedForResize, _Configuration.ValidResolutions, imageCodecInfo, encoderParameters, filenameExtension); | ||||||
|         _ = resize.ToString(); |         _ = resize.ToString(); | ||||||
|         bool? isUniqueFileName = null; |         bool isUniqueFileName = false; | ||||||
|  |         bool? isNotUniqueAndNeedsReview = null; | ||||||
|         bool anyNullOrNoIsUniqueFileName = true; |         bool anyNullOrNoIsUniqueFileName = true; | ||||||
|         FileHolder sourceDirectoryFileHolder = new(".json"); |         FileHolder sourceDirectoryFileHolder = new(".json"); | ||||||
|         FileHolder fileHolder = new(Path.Combine(sourceDirectory, sourceFileName)); |         FileHolder fileHolder = new(Path.Combine(sourceDirectory, sourceFileName)); | ||||||
| @ -240,7 +241,7 @@ public class UnitTestFace | |||||||
|         sourceDirectory = Path.Combine(aPropertySingletonDirectory, sourceDirectoryName); |         sourceDirectory = Path.Combine(aPropertySingletonDirectory, sourceDirectoryName); | ||||||
|         propertyLogic.SetAngleBracketCollection(aResultsFullGroupDirectory, sourceDirectory, anyNullOrNoIsUniqueFileName); |         propertyLogic.SetAngleBracketCollection(aResultsFullGroupDirectory, sourceDirectory, anyNullOrNoIsUniqueFileName); | ||||||
|         resize.SetAngleBracketCollection(_Configuration.PropertyConfiguration, cResultsFullGroupDirectory, sourceDirectory); |         resize.SetAngleBracketCollection(_Configuration.PropertyConfiguration, cResultsFullGroupDirectory, sourceDirectory); | ||||||
|         item = new(sourceDirectoryFileHolder, relativePath, fileHolder, isUniqueFileName, isValidImageFormatExtension, property, false, false, false); |         item = new(sourceDirectoryFileHolder, relativePath, fileHolder, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, property, false, false, false); | ||||||
|         Assert.IsNotNull(item.ImageFileHolder); |         Assert.IsNotNull(item.ImageFileHolder); | ||||||
|         if (item.Property is null) |         if (item.Property is null) | ||||||
|         { |         { | ||||||
|  | |||||||
		Reference in New Issue
	
	Block a user