public static MError Register(IntPtr ptrImageEngine, ref MemberWithFeature member) { var retCode = MError.MERR_UNKNOWN.ToInt(); IntPtr feature = IntPtr.Zero; Image image = null; try { image = Image.FromFile(member.FaceImagePath); if (image.Width % 4 != 0) { image = ImageHelper.ScaleImage(image, image.Width - (image.Width % 4), image.Height); } ASF_MultiFaceInfo multiFaceInfo = FaceProcessHelper.DetectFace(ptrImageEngine, image); if (multiFaceInfo.faceNum > 0) { MRECT rect = MemoryHelper.PtrToStructure <MRECT>(multiFaceInfo.faceRects); image = ImageHelper.CutImage(image, rect.left, rect.top, rect.right, rect.bottom); //提取人脸特征 ASF_SingleFaceInfo singleFaceInfo = new ASF_SingleFaceInfo(); feature = FaceProcessHelper.ExtractFeature(ptrImageEngine, Image.FromFile(member.FaceImagePath), out singleFaceInfo); if (singleFaceInfo.faceRect.left == 0 && singleFaceInfo.faceRect.right == 0) { return(MError.MERR_FSDK_FR_INVALID_FACE_INFO); } else { member.AsfFaceFeature = MemoryHelper.PtrToStructure <ASF_FaceFeature>(feature); } } else { return(MError.MERR_FSDK_FR_INVALID_FACE_INFO); } retCode = MError.MOK.ToInt(); } catch (Exception ex) { Afw.Core.Helper.SimplifiedLogHelper.WriteIntoSystemLog(nameof(MemberEnroll), $"Register Exception:{ex.ToString()}"); } finally { MemoryHelper.Free(feature); image.Dispose(); } return(retCode.ToEnum <MError>()); }
public IntPtr ExtractFeature(Image image, ASF_SingleFaceInfo singleFaceInfo) { IntPtr ptrFeature = IntPtr.Zero; var retCode = MError.MOK; if (ptrVideoImageEngine == IntPtr.Zero) { retCode = InitialEngineForVideoImage(); } if (retCode == MError.MOK) { ptrFeature = FaceProcessHelper.ExtractFeature(ptrVideoImageEngine, image, singleFaceInfo); } return(ptrFeature); }
/// <summary> /// 为注册会员检测人脸 /// </summary> /// <param name="transImageInfo"></param> /// <returns></returns> public MError DeteceForMemberEnroll( out string errMsg, out IntPtr ptrImgFeature, out ASF_SingleFaceInfo singleFaceInfo, out int face3DStatus, out int faceNum, out string faceDesc, ref Image srcImage, int imageContainerWidth, int imageContainerHeight) { faceNum = 0; face3DStatus = -1; faceDesc = string.Empty; errMsg = string.Empty; ptrImgFeature = IntPtr.Zero; StringBuilder sbErrMsg = new StringBuilder(); var retCode = MError.MERR_UNKNOWN; int retAge = -1; int retGender = -1; int ret3DAngle = -1; singleFaceInfo = new ASF_SingleFaceInfo(); try { if (ptrImageEngine == IntPtr.Zero) { retCode = InitialEngineForImage(); } else { retCode = MError.MOK; } if (retCode == MError.MOK) { //调整图像宽度,需要宽度为4的倍数 if (srcImage.Width % 4 != 0) { //srcImage = ImageHelper.ScaleImage(srcImage, picImageCompare.Width, picImageCompare.Height); srcImage = ImageHelper.ScaleImage(srcImage, srcImage.Width - (srcImage.Width % 4), srcImage.Height); } //调整图片数据,非常重要 ImageInfo transImageInfo = ImageHelper.ReadBMP(srcImage); //人脸检测 ASF_MultiFaceInfo multiFaceInfo = FaceProcessHelper.DetectFace(ptrImageEngine, transImageInfo); faceNum = multiFaceInfo.faceNum; if (multiFaceInfo.faceNum != 1) { retCode = MError.MERR_ASF_EX_INVALID_FACE_INFO; sbErrMsg.Append(multiFaceInfo.faceNum > 1 ? "检测到多张人脸" : "未检测到人脸"); } else { ASF_AgeInfo ageInfo = FaceProcessHelper.AgeEstimation(ptrImageEngine, transImageInfo, multiFaceInfo, out retAge); ASF_GenderInfo genderInfo = FaceProcessHelper.GenderEstimation(ptrImageEngine, transImageInfo, multiFaceInfo, out retGender); ASF_Face3DAngle face3DAngleInfo = FaceProcessHelper.Face3DAngleDetection(ptrImageEngine, transImageInfo, multiFaceInfo, out ret3DAngle); #region 标记出检测到的人脸 MRECT temp = new MRECT(); int ageTemp = 0; int genderTemp = 0; int rectTemp = 0; //标记出检测到的人脸 for (int i = 0; i < multiFaceInfo.faceNum; i++) { MRECT rect = MemoryHelper.PtrToStructure <MRECT>(multiFaceInfo.faceRects + MemoryHelper.SizeOf <MRECT>() * i); int orient = MemoryHelper.PtrToStructure <int>(multiFaceInfo.faceOrients + MemoryHelper.SizeOf <int>() * i); int age = 0; if (retAge != 0) { sbErrMsg.AppendLine($"年龄检测失败,返回{retAge}!"); } else { age = MemoryHelper.PtrToStructure <int>(ageInfo.ageArray + MemoryHelper.SizeOf <int>() * i); } int gender = -1; if (retGender != 0) { sbErrMsg.AppendLine($"性别检测失败,返回{retGender}!"); } else { gender = MemoryHelper.PtrToStructure <int>(genderInfo.genderArray + MemoryHelper.SizeOf <int>() * i); } //int face3DStatus = -1; float roll = 0f; float pitch = 0f; float yaw = 0f; if (ret3DAngle != 0) { sbErrMsg.AppendLine($"3DAngle检测失败,返回{ret3DAngle}!"); } else { //角度状态 非0表示人脸不可信 face3DStatus = MemoryHelper.PtrToStructure <int>(face3DAngleInfo.status + MemoryHelper.SizeOf <int>() * i); //roll为侧倾角,pitch为俯仰角,yaw为偏航角 roll = MemoryHelper.PtrToStructure <float>(face3DAngleInfo.roll + MemoryHelper.SizeOf <float>() * i); pitch = MemoryHelper.PtrToStructure <float>(face3DAngleInfo.pitch + MemoryHelper.SizeOf <float>() * i); yaw = MemoryHelper.PtrToStructure <float>(face3DAngleInfo.yaw + MemoryHelper.SizeOf <float>() * i); } int rectWidth = rect.right - rect.left; int rectHeight = rect.bottom - rect.top; //查找最大人脸 if (rectWidth * rectHeight > rectTemp) { rectTemp = rectWidth * rectHeight; temp = rect; ageTemp = age; genderTemp = gender; } //srcImage = ImageHelper.MarkRectAndString(srcImage, rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, age, gender); faceDesc = $"{DateTime.Now.ToString("yyyy/MM/dd HH:mm:ss")} - 人脸坐标:[left:{rect.left},top:{rect.top},right:{rect.right},bottom:{rect.bottom},orient:{orient},roll:{roll},pitch:{pitch},yaw:{yaw},status:{face3DStatus}] Age:{age} Gender:{(gender >= 0 ? gender.ToString() : "")}\n"; } //提取人脸特征 ptrImgFeature = FaceProcessHelper.ExtractFeature(ptrImageEngine, srcImage, out singleFaceInfo); float scaleRate = ImageHelper.GetWidthAndHeight(srcImage.Width, srcImage.Height, imageContainerWidth, imageContainerHeight); srcImage = ImageHelper.ScaleImage(srcImage, imageContainerWidth, imageContainerHeight); srcImage = ImageHelper.MarkRectAndString(srcImage, (int)(temp.left * scaleRate), (int)(temp.top * scaleRate), (int)(temp.right * scaleRate) - (int)(temp.left * scaleRate), (int)(temp.bottom * scaleRate) - (int)(temp.top * scaleRate), ageTemp, genderTemp, imageContainerWidth); #endregion } MemoryHelper.Free(transImageInfo.imgData); } errMsg = sbErrMsg.ToString(); } catch (Exception ex) { Afw.Core.Helper.SimplifiedLogHelper.WriteIntoSystemLog(nameof(Afw.WinForm.EngineContext), $"DeteceForMemberEnroll Exception:{ex.ToString()}"); } return(retCode); }