using System.Text.Json; namespace View_by_Distance.Shared.Models.Stateless.Methods; internal abstract class Face { internal static string GetJson(string jsonFileFullName) { string result; FileInfo fileInfo; string fileSegment = "FileSegment"; result = File.ReadAllText(jsonFileFullName); if (result.Contains(fileSegment)) { fileInfo = new FileInfo(jsonFileFullName); result = result.Replace(fileSegment, nameof(Properties.IIndex.RelativePaths)).Replace("\\\\", "/"); File.WriteAllText(fileInfo.FullName, result); File.SetLastWriteTime(fileInfo.FullName, fileInfo.LastWriteTime); } if (result.Contains("/u0")) { fileInfo = new FileInfo(jsonFileFullName); result = result.Replace("/u0", "\\u0"); File.WriteAllText(fileInfo.FullName, result); File.SetLastWriteTime(fileInfo.FullName, fileInfo.LastWriteTime); } return result; } private static JsonElement[] GetJsonElements(string jsonFileFullName) { string json = GetJson(jsonFileFullName); JsonElement[]? jsonElements = JsonSerializer.Deserialize(json) ?? throw new Exception(); return jsonElements; } private static List GetFaces(string jsonFileFullName, int? maximum) { List results = []; Tuple? tuple; JsonElement[] jsonElements = GetJsonElements(jsonFileFullName); foreach (JsonElement jsonElement in jsonElements) { tuple = JsonSerializer.Deserialize>(jsonElement.ToString()); if (tuple is null || tuple.Item1 is null || string.IsNullOrEmpty("tuple.Item1.RelativePath")) continue; results.Add(tuple.Item1); if (maximum.HasValue && results.Count >= maximum) break; } return results; } internal static Models.Face GetFace(string jsonFileFullName) { Models.Face? result; List results = GetFaces(jsonFileFullName, maximum: 1); if (results.Count == 0) throw new Exception(); result = results[0]; return result; } internal static Models.Face[] GetFaces(string jsonFileFullName) { List results = GetFaces(jsonFileFullName, maximum: null); return results.ToArray(); } internal static double Getα(int x1, int x2, int y1, int y2) { double result; if (y1 == y2) result = 0; else { int b; if (x1 > x2) b = x1 - x2; else b = x2 - x1; int a; if (y1 > y2) a = y1 - y2; else a = y2 - y1; double c = Math.Sqrt(Math.Pow(a, 2) + Math.Pow(b, 2)); if (y1 < y2) result = 180 / Math.PI * Math.Asin(a / c); else result = 180 / Math.PI * Math.Asin(a / c) * -1; } return result; } internal static (bool?, double?) GetEyeα(Dictionary faceParts) { bool? review; double? result; int? lipY = null; int? leftEyeX = null; int? leftEyeY = null; int? rightEyeX = null; int? rightEyeY = null; foreach ((FacePart facePart, Models.FacePoint[] facePoints) in faceParts) { if (facePart is not FacePart.LeftEye and not FacePart.RightEye) continue; if (facePart is FacePart.LeftEye) { leftEyeX = (int)(from l in facePoints select l.X).Average(); leftEyeY = (int)(from l in facePoints select l.Y).Average(); } if (facePart is FacePart.RightEye) { rightEyeX = (int)(from l in facePoints select l.X).Average(); rightEyeY = (int)(from l in facePoints select l.Y).Average(); } if (facePart is FacePart.BottomLip or FacePart.TopLip) lipY ??= (int)(from l in facePoints select l.X).Average(); } if (rightEyeX is null || leftEyeX is null || rightEyeY is null || leftEyeY is null) (result, review) = (null, null); else { review = lipY < rightEyeY || lipY < leftEyeY; result = Getα(rightEyeX.Value, leftEyeX.Value, rightEyeY.Value, leftEyeY.Value); } return (review, result); } internal static (bool, int[]) GetEyeCollection(int threshold, List faces) { bool result = false; List results = []; foreach (Models.Face face in faces) { if (face.Mapping?.MappingFromLocation?.Eyeα is null || face.Mapping.MappingFromLocation.EyeReview is null) continue; results.Add(face.Mapping.MappingFromLocation.Eyeα.Value); if (!result && face.Mapping.MappingFromLocation.EyeReview.Value || face.Mapping.MappingFromLocation.Eyeα.Value > threshold) result = true; } return (result, results.ToArray()); } }