C# OpenCvSharp DNN 部署L2CS-Net人脸朝向估计

2023-10-31 14:30

本文主要是介绍C# OpenCvSharp DNN 部署L2CS-Net人脸朝向估计,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

效果

项目

代码

using OpenCvSharp;
using OpenCvSharp.Dnn;
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Linq;
using System.Text;
using System.Windows.Forms;namespace OpenCvSharp_DNN_Demo
{public partial class frmMain : Form{public frmMain(){InitializeComponent();}string fileFilter = "*.*|*.bmp;*.jpg;*.jpeg;*.tiff;*.tiff;*.png";string image_path = "";string startupPath;DateTime dt1 = DateTime.Now;DateTime dt2 = DateTime.Now;string model_path;Mat image;Mat result_image;Net opencv_net;Mat BN_image;StringBuilder sb = new StringBuilder();int reg_max = 16;int num_class = 1;int inpWidth = 640;int inpHeight = 640;float score_threshold = 0.25f;float nms_threshold = 0.5f;L2CSNet gaze_predictor;private void Form1_Load(object sender, EventArgs e){startupPath = System.Windows.Forms.Application.StartupPath;model_path = startupPath + "\\yolov8n-face.onnx";//初始化网络类,读取本地模型opencv_net = CvDnn.ReadNetFromOnnx(model_path);gaze_predictor = new L2CSNet("l2cs_net_1x3x448x448.onnx");}private void button1_Click(object sender, EventArgs e){OpenFileDialog ofd = new OpenFileDialog();ofd.Filter = fileFilter;if (ofd.ShowDialog() != DialogResult.OK) return;pictureBox1.Image = null;image_path = ofd.FileName;pictureBox1.Image = new Bitmap(image_path);textBox1.Text = "";image = new Mat(image_path);pictureBox2.Image = null;}private void button2_Click(object sender, EventArgs e){if (image_path == ""){return;}int newh = 0, neww = 0, padh = 0, padw = 0;Mat resize_img = Common.ResizeImage(image, inpHeight, inpWidth, ref newh, ref neww, ref padh, ref padw);float ratioh = (float)image.Rows / newh, ratiow = (float)image.Cols / neww;dt1 = DateTime.Now;//数据归一化处理BN_image = CvDnn.BlobFromImage(resize_img, 1 / 255.0, new OpenCvSharp.Size(inpWidth, inpHeight), new Scalar(0, 0, 0), true, false);//配置图片输入数据opencv_net.SetInput(BN_image);//模型推理,读取推理结果Mat[] outs = new Mat[3] { new Mat(), new Mat(), new Mat() };string[] outBlobNames = opencv_net.GetUnconnectedOutLayersNames().ToArray();opencv_net.Forward(outs, outBlobNames);List<Rect> position_boxes = new List<Rect>();List<float> confidences = new List<float>();List<List<OpenCvSharp.Point>> landmarks = new List<List<OpenCvSharp.Point>>();Common.GenerateProposal(inpHeight, inpWidth, reg_max, num_class, score_threshold, 40, 40, outs[0], position_boxes, confidences, landmarks, image.Rows, image.Cols, ratioh, ratiow, padh, padw);Common.GenerateProposal(inpHeight, inpWidth, reg_max, num_class, score_threshold, 20, 20, outs[1], position_boxes, confidences, landmarks, image.Rows, image.Cols, ratioh, ratiow, padh, padw);Common.GenerateProposal(inpHeight, inpWidth, reg_max, num_class, score_threshold, 80, 80, outs[2], position_boxes, confidences, landmarks, image.Rows, image.Cols, ratioh, ratiow, padh, padw);//NMS非极大值抑制int[] indexes = new int[position_boxes.Count];CvDnn.NMSBoxes(position_boxes, confidences, score_threshold, nms_threshold, out indexes);List<Rect> re_result = new List<Rect>();List<List<OpenCvSharp.Point>> re_landmarks = new List<List<OpenCvSharp.Point>>();List<float> re_confidences = new List<float>();for (int i = 0; i < indexes.Length; i++){int index = indexes[i];re_result.Add(position_boxes[index]);re_landmarks.Add(landmarks[index]);re_confidences.Add(confidences[index]);}float[] gaze_yaw_pitch = new float[2];float length = (float)(image.Cols / 1.5);result_image = image.Clone();if (re_result.Count > 0){sb.Clear();for (int i = 0; i < re_result.Count; i++){Mat crop_img = new Mat(result_image, re_result[i]);gaze_predictor.Detect(crop_img, gaze_yaw_pitch);//draw gaze	float pos_x = (float)(re_result[i].X + 0.5 * re_result[i].Width);float pos_y = (float)(re_result[i].Y + 0.5 * re_result[i].Height);float dy = (float)(-length * Math.Sin(gaze_yaw_pitch[0]) * Math.Cos(gaze_yaw_pitch[1]));float dx = (float)(-length * Math.Sin(gaze_yaw_pitch[1]));OpenCvSharp.Point from = new OpenCvSharp.Point((int)pos_x, (int)pos_y);OpenCvSharp.Point to = new OpenCvSharp.Point((int)(pos_x + dx), (int)(pos_y + dy));Cv2.ArrowedLine(result_image, from, to, new Scalar(255, 0, 0), 2, 0, 0, 0.18);Cv2.Rectangle(result_image, re_result[i], new Scalar(0, 0, 255), 2, LineTypes.Link8);//Cv2.Rectangle(result_image, new OpenCvSharp.Point(re_result[i].X, re_result[i].Y), new OpenCvSharp.Point(re_result[i].X + re_result[i].Width, re_result[i].Y+ re_result[i].Height), new Scalar(0, 255, 0), 2);Cv2.PutText(result_image, "face-" + re_confidences[i].ToString("0.00"),new OpenCvSharp.Point(re_result[i].X, re_result[i].Y - 10),HersheyFonts.HersheySimplex, 1, new Scalar(0, 0, 255), 2);foreach (var item in re_landmarks[i]){Cv2.Circle(result_image, item, 2, new Scalar(0, 255, 0), -1);}sb.AppendLine(string.Format("{0}:{1},({2},{3},{4},{5})", "face", re_confidences[i].ToString("0.00"), re_result[i].TopLeft.X, re_result[i].TopLeft.Y, re_result[i].BottomRight.X, re_result[i].BottomRight.Y));}dt2 = DateTime.Now;sb.AppendLine("--------------------------");sb.AppendLine("耗时:" + (dt2 - dt1).TotalMilliseconds + "ms");pictureBox2.Image = new Bitmap(result_image.ToMemoryStream());textBox1.Text = sb.ToString();}else{textBox1.Text = "无信息";}}}
}

参考

GitHub - Ahmednull/L2CS-Net: The official PyTorch implementation of L2CS-Net for gaze estimation and tracking

下载

可执行程序exe包0积分下载

源码下载

这篇关于C# OpenCvSharp DNN 部署L2CS-Net人脸朝向估计的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/315997

相关文章

C#实现千万数据秒级导入的代码

《C#实现千万数据秒级导入的代码》在实际开发中excel导入很常见,现代社会中很容易遇到大数据处理业务,所以本文我就给大家分享一下千万数据秒级导入怎么实现,文中有详细的代码示例供大家参考,需要的朋友可... 目录前言一、数据存储二、处理逻辑优化前代码处理逻辑优化后的代码总结前言在实际开发中excel导入很

通过Docker容器部署Python环境的全流程

《通过Docker容器部署Python环境的全流程》在现代化开发流程中,Docker因其轻量化、环境隔离和跨平台一致性的特性,已成为部署Python应用的标准工具,本文将详细演示如何通过Docker容... 目录引言一、docker与python的协同优势二、核心步骤详解三、进阶配置技巧四、生产环境最佳实践

Nginx部署HTTP/3的实现步骤

《Nginx部署HTTP/3的实现步骤》本文介绍了在Nginx中部署HTTP/3的详细步骤,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学... 目录前提条件第一步:安装必要的依赖库第二步:获取并构建 BoringSSL第三步:获取 Nginx

C#使用Spire.Doc for .NET实现HTML转Word的高效方案

《C#使用Spire.Docfor.NET实现HTML转Word的高效方案》在Web开发中,HTML内容的生成与处理是高频需求,然而,当用户需要将HTML页面或动态生成的HTML字符串转换为Wor... 目录引言一、html转Word的典型场景与挑战二、用 Spire.Doc 实现 HTML 转 Word1

C#实现一键批量合并PDF文档

《C#实现一键批量合并PDF文档》这篇文章主要为大家详细介绍了如何使用C#实现一键批量合并PDF文档功能,文中的示例代码简洁易懂,感兴趣的小伙伴可以跟随小编一起学习一下... 目录前言效果展示功能实现1、添加文件2、文件分组(书签)3、定义页码范围4、自定义显示5、定义页面尺寸6、PDF批量合并7、其他方法

C#下Newtonsoft.Json的具体使用

《C#下Newtonsoft.Json的具体使用》Newtonsoft.Json是一个非常流行的C#JSON序列化和反序列化库,它可以方便地将C#对象转换为JSON格式,或者将JSON数据解析为C#对... 目录安装 Newtonsoft.json基本用法1. 序列化 C# 对象为 JSON2. 反序列化

C#文件复制异常:"未能找到文件"的解决方案与预防措施

《C#文件复制异常:未能找到文件的解决方案与预防措施》在C#开发中,文件操作是基础中的基础,但有时最基础的File.Copy()方法也会抛出令人困惑的异常,当targetFilePath设置为D:2... 目录一个看似简单的文件操作问题问题重现与错误分析错误代码示例错误信息根本原因分析全面解决方案1. 确保

redis-sentinel基础概念及部署流程

《redis-sentinel基础概念及部署流程》RedisSentinel是Redis的高可用解决方案,通过监控主从节点、自动故障转移、通知机制及配置提供,实现集群故障恢复与服务持续可用,核心组件包... 目录一. 引言二. 核心功能三. 核心组件四. 故障转移流程五. 服务部署六. sentinel部署

基于C#实现PDF转图片的详细教程

《基于C#实现PDF转图片的详细教程》在数字化办公场景中,PDF文件的可视化处理需求日益增长,本文将围绕Spire.PDFfor.NET这一工具,详解如何通过C#将PDF转换为JPG、PNG等主流图片... 目录引言一、组件部署二、快速入门:PDF 转图片的核心 C# 代码三、分辨率设置 - 清晰度的决定因

C# LiteDB处理时间序列数据的高性能解决方案

《C#LiteDB处理时间序列数据的高性能解决方案》LiteDB作为.NET生态下的轻量级嵌入式NoSQL数据库,一直是时间序列处理的优选方案,本文将为大家大家简单介绍一下LiteDB处理时间序列数... 目录为什么选择LiteDB处理时间序列数据第一章:LiteDB时间序列数据模型设计1.1 核心设计原则