WPF 实现人脸检测

WPF开发者QQ群

此群已满340500857 ,请加新群458041663

       由于微信群人数太多入群请添加小编微信号

 yanjinhuawechatW_Feng_aiQ 邀请入群

 需备注WPF开发者 

  PS:有更好的方式欢迎推荐。

  接着上一篇

  利用已经训练好的数据文件,检测人脸 地址如下:

  https://github.com/opencv/opencv/tree/master/data/haarcascades

a91b8fd45bb94bfe43c38f39c467d828.png

使用NuGet如下:

befbcb5321794702a1fef181922b015f.png

01

代码如下

一、创建MainWindow.xaml代码如下。

<ws:Window x:Class="OpenCVSharpExample.MainWindow"xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"xmlns:ws="https://github.com/WPFDevelopersOrg.WPFDevelopers.Minimal"xmlns:d="http://schemas.microsoft.com/expression/blend/2008"xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"xmlns:local="clr-namespace:OpenCVSharpExample"Icon="OpenCV_Logo.png"mc:Ignorable="d" WindowStartupLocation="CenterScreen"Title="OpenCVSharpExample https://github.com/WPFDevelopersOrg" Height="450" Width="800"><Grid Margin="4"><Grid.ColumnDefinitions><ColumnDefinition MinWidth="500" Width="8*"/><ColumnDefinition Width="2*" MinWidth="200"/></Grid.ColumnDefinitions><Image Grid.Row="0" Name="imgViewport"/><GridSplitter Grid.Column="0" HorizontalAlignment="Right" Width="2"/><GroupBox Header="Operation" Grid.Column="1" Margin="0,0,4,0"><Grid><Grid.RowDefinitions><RowDefinition/><RowDefinition/><RowDefinition Height="Auto"/></Grid.RowDefinitions><StackPanel Grid.Row="0" HorizontalAlignment="Left"><CheckBox IsChecked="{Binding IsSave,RelativeSource={RelativeSource AncestorType=local:MainWindow}}"VerticalAlignment="Center" Content="Save" Margin="0,4"/><CheckBox IsChecked="{Binding IsFace,RelativeSource={RelativeSource AncestorType=local:MainWindow}}"VerticalAlignment="Center" Content="Face" Margin="0,4"/><ComboBox Name="ComboBoxCamera" ItemsSource="{Binding CameraArray,RelativeSource={RelativeSource AncestorType=local:MainWindow}}" SelectedIndex="{Binding CameraIndex,RelativeSource={RelativeSource AncestorType=local:MainWindow}}"SelectionChanged="ComboBoxCamera_SelectionChanged"/></StackPanel><StackPanel Orientation="Horizontal" Grid.Row="2" HorizontalAlignment="Center"><Button Name="btPlay" Content="Play" Style="{StaticResource PrimaryButton}" Click="btPlay_Click" IsEnabled="False"/><Button Name="btStop" Click="btStop_Click" Content="Stop" Margin="4,0"/></StackPanel></Grid></GroupBox></Grid>
</ws:Window>

二、MainWindow.xaml.cs代码如下。

using OpenCvSharp;
using OpenCvSharp.Extensions;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Drawing.Imaging;
using System.Globalization;
using System.IO;
using System.Management;
using System.Threading;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media.Imaging;
using System.Windows.Threading;namespace OpenCVSharpExample
{/// <summary>/// MainWindow.xaml 的交互逻辑/// </summary>public partial class MainWindow{private VideoCapture capCamera;private VideoWriter videoWriter;private Mat matImage = new Mat();private Thread cameraThread;private Thread writerThread;private CascadeClassifier haarCascade;private WriteableBitmap writeableBitmap;private Rectangle rectangle;private Mat gray;private Mat result;private OpenCvSharp.Rect[] faces;public List<string> CameraArray{get { return (List<string>)GetValue(CameraArrayProperty); }set { SetValue(CameraArrayProperty, value); }}public static readonly DependencyProperty CameraArrayProperty =DependencyProperty.Register("CameraArray", typeof(List<string>), typeof(MainWindow), new PropertyMetadata(null));public int CameraIndex{get { return (int)GetValue(CameraIndexProperty); }set { SetValue(CameraIndexProperty, value); }}public static readonly DependencyProperty CameraIndexProperty =DependencyProperty.Register("CameraIndex", typeof(int), typeof(MainWindow), new PropertyMetadata(0));public bool IsSave{get { return (bool)GetValue(IsSaveProperty); }set { SetValue(IsSaveProperty, value); }}public static readonly DependencyProperty IsSaveProperty =DependencyProperty.Register("IsSave", typeof(bool), typeof(MainWindow), new UIPropertyMetadata(IsSaveChanged));private static void IsSaveChanged(DependencyObject d, DependencyPropertyChangedEventArgs e){var mainWindow = d as MainWindow;if (e.NewValue != null){var save = (bool) e.NewValue;if (save)mainWindow.StartRecording();elsemainWindow.StopRecording();}}public bool IsFace{get { return (bool)GetValue(IsFaceProperty); }set { SetValue(IsFaceProperty, value); }}public static readonly DependencyProperty IsFaceProperty =DependencyProperty.Register("IsFace", typeof(bool), typeof(MainWindow), new UIPropertyMetadata(IsFaceChanged));private static void IsFaceChanged(DependencyObject d, DependencyPropertyChangedEventArgs e){var mainWindow = d as MainWindow;if (e.NewValue != null){var save = (bool)e.NewValue;if (save)mainWindow.CreateFace();elsemainWindow.CloseFace();}}public MainWindow(){InitializeComponent();Width = SystemParameters.WorkArea.Width / 1.5;Height = SystemParameters.WorkArea.Height / 1.5;this.Loaded += MainWindow_Loaded;}private void MainWindow_Loaded(object sender, RoutedEventArgs e){InitializeCamera();}private void ComboBoxCamera_SelectionChanged(object sender, SelectionChangedEventArgs e){if (CameraArray.Count - 1 < CameraIndex)return;if (capCamera != null && cameraThread != null){cameraThread.Abort();StopDispose();}CreateCamera();writeableBitmap = new WriteableBitmap(capCamera.FrameWidth, capCamera.FrameHeight, 0, 0, System.Windows.Media.PixelFormats.Bgra32, null);imgViewport.Source = writeableBitmap;}private void btStop_Click(object sender, RoutedEventArgs e){StopDispose();btStop.IsEnabled = false;}protected override void OnClosing(CancelEventArgs e){if(WPFDevelopers.Minimal.Controls.MessageBox.Show("是否关闭系统?", "询问", MessageBoxButton.OKCancel, MessageBoxImage.Question) != MessageBoxResult.OK) {e.Cancel = true;return;}}protected override void OnClosed(EventArgs e){StopDispose();}private void btPlay_Click(object sender, RoutedEventArgs e){btPlay.IsEnabled = false;btStop.IsEnabled = true;CreateCamera();}#region 方法void CloseFace(){if (haarCascade != null){haarCascade.Dispose();haarCascade = null;gray.Dispose();gray = null;result.Dispose();result = null;faces = null;}}void CreateFace(){var facePath = System.IO.Path.Combine(System.Environment.CurrentDirectory, "Data/haarcascade_frontalface_default.xml");if (!System.IO.File.Exists(facePath)){WPFDevelopers.Minimal.Controls.MessageBox.Show("缺少人脸检测文件。", "错误", MessageBoxButton.OK, MessageBoxImage.Error);return;}haarCascade = new CascadeClassifier(facePath);}private void InitializeCamera(){CameraArray = GetAllConnectedCameras();}List<string> GetAllConnectedCameras(){var cameraNames = new List<string>();using (var searcher = new ManagementObjectSearcher("SELECT * FROM Win32_PnPEntity WHERE (PNPClass = 'Image' OR PNPClass = 'Camera')")){foreach (var device in searcher.Get()){cameraNames.Add(device["Caption"].ToString());}}return cameraNames;}void CreateCamera(){capCamera = new VideoCapture(CameraIndex);capCamera.Fps = 30;cameraThread = new Thread(PlayCamera);cameraThread.Start();}private void PlayCamera(){while (capCamera != null && !capCamera.IsDisposed){capCamera.Read(matImage);if (matImage.Empty()) break;Dispatcher.Invoke(new Action(() =>{if (IsFace){result = matImage.Clone();gray = new Mat();Cv2.CvtColor(result, gray, ColorConversionCodes.BGR2GRAY);faces = haarCascade.DetectMultiScale(gray, 1.3);if (faces.Length > 0){Cv2.Rectangle(matImage, faces[0], Scalar.Green, 2);}result.Dispose();}}));using (var img = BitmapConverter.ToBitmap(matImage)){var now = DateTime.Now;var g = Graphics.FromImage(img);var brush = new SolidBrush(System.Drawing.Color.Red);System.Globalization.CultureInfo cultureInfo = new CultureInfo("zh-CN");var week = cultureInfo.DateTimeFormat.GetAbbreviatedDayName(now.DayOfWeek);g.DrawString($"{week} { now.ToString("yyyy年MM月dd日 HH:mm:ss ")} ", new System.Drawing.Font(System.Drawing.SystemFonts.DefaultFont.Name, System.Drawing.SystemFonts.DefaultFont.Size), brush, new PointF(0, matImage.Rows - 20));brush.Dispose();g.Dispose();rectangle = new Rectangle(0, 0, img.Width, img.Height);Dispatcher.Invoke(new Action(() =>{WriteableBitmapHelper.BitmapCopyToWriteableBitmap(img, writeableBitmap, rectangle, 0, 0, System.Drawing.Imaging.PixelFormat.Format32bppArgb);}));img.Dispose();};Thread.Sleep(100);}}private void StartRecording(){if (capCamera == null){WPFDevelopers.Minimal.Controls.MessageBox.Show("未开启摄像机", "提示", MessageBoxButton.OKCancel, MessageBoxImage.Error);return;}var videoFile = System.IO.Path.Combine(System.Environment.CurrentDirectory, "Video");if (!System.IO.Directory.Exists(videoFile))System.IO.Directory.CreateDirectory(videoFile);var currentTime = System.IO.Path.Combine(videoFile, $"{DateTime.Now.ToString("yyyyMMddHHmmsshh")}.avi");videoWriter = new VideoWriter(currentTime, FourCCValues.XVID, capCamera.Fps, new OpenCvSharp.Size(capCamera.FrameWidth, capCamera.FrameHeight));writerThread = new Thread(AddCameraFrameToRecording);writerThread.Start();}private void StopRecording(){if (videoWriter != null && !videoWriter.IsDisposed){videoWriter.Release();videoWriter.Dispose();videoWriter = null;}}private void AddCameraFrameToRecording(){var waitTimeBetweenFrames = 1_000 / capCamera.Fps;var lastWrite = DateTime.Now;while (!videoWriter.IsDisposed){if (DateTime.Now.Subtract(lastWrite).TotalMilliseconds < waitTimeBetweenFrames)continue;lastWrite = DateTime.Now;videoWriter.Write(matImage);}}void StopDispose(){if (capCamera != null && capCamera.IsOpened()){capCamera.Dispose();capCamera = null;}if (videoWriter != null && !videoWriter.IsDisposed){videoWriter.Release();videoWriter.Dispose();videoWriter = null;}CloseFace();btPlay.IsEnabled = true;GC.Collect();}void CreateRecord(){cameraThread = new Thread(PlayCamera);cameraThread.Start();}#endregion}
}

02


效果预览

鸣谢素材提供者OpenCVSharp

abf3da456905c92186c05c40637c6414.png

源码地址如下

Github:https://github.com/WPFDevelopersOrg

https://github.com/WPFDevelopersOrg/OpenCVSharpExample

Gitee:https://gitee.com/WPFDevelopersOrg

WPF开发者QQ群: 340500857 

Github:https://github.com/WPFDevelopersOrg

出处:https://www.cnblogs.com/yanjinhua

版权:本作品采用「署名-非商业性使用-相同方式共享 4.0 国际」许可协议进行许可。

转载请著名作者 出处 https://github.com/WPFDevelopersOrg

0e6b152d680f8d75b99d13971d119390.png

扫一扫关注我们,

b201c249a528152861b92dd27d25aff8.gif

更多知识早知道!

fe79d9da347b51d0a9ac4e77cfe27e3f.gif

点击阅读原文可跳转至源代码

8102f1858e1b32ea9becd98e861dfb82.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/290999.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

C++之函数的默认值参数说明

1、思考 今天看到C代码的时候&#xff0c;发现文件里面的函数定义和实现都有3个参数&#xff0c;特码调用的时候只有2个参数了&#xff0c;日了狗&#xff0c;java里面好像没有这种方式&#xff0c;后来才发现是默认参数 2、代码实现 3、展示结果 4、总结 注意默认参数需要写…

如何用c语言验证一个定理,验证动量定理方法一

【目的和要求】验证物体做直线运动时&#xff0c;其动量的增量等于合外力的冲量&#xff0c;以加深学生对动量定理的理解。【仪器和器材】电磁打点计时器(J0203型)&#xff0c;学生电源(J1202型)&#xff0c;斜面(带定滑轮)&#xff0c;小车&#xff0c;纸带&#xff0c;天平(托…

Merge Two Sorted Lists leetcode java

题目&#xff1a; Merge two sorted linked lists and return it as a new list. The new list should be made by splicing together the nodes of the first two lists. 题解&#xff1a;这道题是链表操作题&#xff0c;题解方法很直观。首先&#xff0c;进行边界条件判断&am…

插头DP

AC HDU1693 不能再简单了的插头DP 1 #include <cstdio>2 #include <fstream>3 #include <iostream>4 5 #include <cstdlib>6 #include <cstring>7 #include <algorithm>8 #include <cmath>9 10 #include <queue>11 #include…

自定义控件详解(四):Paint 画笔路径效果

Paint 画笔 &#xff0c;即用来绘制图形的"笔" 前面我们知道了Paint的一些基本用法&#xff1a; paint.setAntiAlias(true);//抗锯齿功能 paint.setColor(Color.RED); //设置画笔颜色 paint.setStyle(Style.FILL);//设置填充样式 paint.setStrokeWidth(10);//设…

C++之undefined reference to “ssl::first::first()“

1、错误 只写了一个简单的C继承类&#xff0c;就出现了这个错误 undefined reference to "ssl::first::first()" 2、原因 我在second类里面继承了first类&#xff0c;但是在first类里面&#xff0c;我把构造函数写成了 first();然后这个函数有没有实现&#xff0c;…

qt中c语言怎么显示图片和文字,Qt中在图片上叠加显示文字

如何在win7上安装ant-design1.首先要安装务必确认 Node.js 已经升级到 v4.x 或以上. 2.打开cmd,输入"npm install antd-init -g",安装antd(可以自己先指定安装目 ...&lbrack;TopCoder&rsqb; SRM&lowbar;594&lowbar;DIV2&period;250好长一段时间没…

2021 .NET Conf China 主题分享之-轻松玩转.NET大规模版本升级

去年.NET Conf China 技术大会上&#xff0c;我给大家分享了主题《轻松玩转.NET大规模版本升级》&#xff0c;今天把具体分享的内容整理成一篇博客&#xff0c;供大家研究参考学习。一、先说一下技术挑战和业务背景我们公司&#xff1a;特来电新能源股份有限公司&#xff1a;中…

HDU4462-稻草人

思想不难&#xff0c;代码不易&#xff0c;且敲且珍惜。 枚举的方式&#xff0c;假设有十个位置可以放稻草人&#xff0c;用二进制的形式转换一下&#xff0c;对每种情况判断是否全被覆盖&#xff0c;记录成功时稻草人的个数&#xff0c;每次比较选出最小的。 注意一个陷阱&…

OC-归档和解归档

1 //归档:将对象数据存储到文件的过程 NSArchiver2 //反归档:从文件中读取数据到对象中的过程3 4 int main(int argc, const char * argv[]) {5 autoreleasepool {6 7 #if 08 //使用系统的方法进行归档 NSArchiver9 NSDictionary *mutDic [NSMu…

推荐电影 奥黛丽赫本的十大经典电影 1953-1989

奥黛丽赫本的十部经典电影 1.《罗马假日》 &#xff08;Roman Holiday&#xff0c;1953&#xff09; 导演&#xff1a;威廉惠勒 风情指数★★★★★ 看点&#xff1a;奥黛丽赫本和格里高利派克的完美组合 如果没有奥黛丽赫本&#xff0c;或许《罗马假日》只会作为一部平庸…

C和C++之用extern “C“实现它们之间的互调

1、extern "C"的解释 一个C++程序包含其它语言编写的部分代码。C++编写的代码片段可能被使用在其它语言编写的代码中,不同语言编写的代码互相调用是困难的,甚至是同一种编写的代码但不同的编译器编译的代码。例如,不同语言和同种语言的不同实现可能会在注册变…

ASP.NET Core基于滑动窗口算法实现限流控制

前言在实际项目中&#xff0c;为了保障服务器的稳定运行&#xff0c;需要对接口的可访问频次进行限流控制&#xff0c;避免因客户端频繁请求导致服务器压力过大。而AspNetCoreRateLimit[1]是目前ASP.NET Core下最常用的限流解决方案。查看它的实现代码&#xff0c;我发现它使用…

android 资源文件获取啥退,重拾Android之路之获得各种资源文件的方法

引言通常我们会在项目中频繁获取color、raw、drawable、mipmap、string等资源文件。因此&#xff0c;今天整理下获取资源文件的工具类方法。最新通用方法ContextCompat.getColor(this,R.color.activity_bg);ContextCompat.getDrawable(this,R.drawable.leak_canary_icon);最近在…

linux操作系统cp命令

转载于:https://www.cnblogs.com/skl374199080/p/3863918.html

WPF将数据库和GridView绑定并更改GridView模板

首先来看一下如何使用GridView,在前台的话代码如下&#xff1a;这里仅仅举出一个例子&#xff0c;GridView是作为子项嵌套在ListView中的&#xff0c;这里的数据源是通过绑定的方式来绑定到GridView中的。 <ListView Margin"15,115,15,48" Name"lstProducts&…

sql必读的九本书

2019独角兽企业重金招聘Python工程师标准>>> 原文地址 直接上书(书籍以后会陆续加上去)书籍下载地址 《MySQL必知必会》《SQL学习指南&#xff08;第2版 修订版&#xff09;》《MySQL技术内幕——InnoDB存储引擎》《Redis设计与实现》《ZooKeeper&#xff1a;分布式…

C语言之加入头文件<stdbool.h>可以使用true和false

1、头文件<stdbool.h>介绍 &#xff08;1&#xff09;使用了<stdbool.h>后&#xff0c;可使用true和false来表示真假。 &#xff08;2&#xff09;在循环语句中进行变量声明是C99中才有的&#xff0c;因此编译时显式指明 gcc -stdc99 prime.c 2、最简单的例子 3、…

Nginx负载均衡+转发策略

负载均衡负载均衡(详解)https://cloud.tencent.com/developer/article/1526664--示例1upstream www_server_pool { server 10.0.0.5; server 10.0.0.6&#xff1a;80 weight1 max_fails1 fails_timeout10s; server 10.0.0.7&#xff1a;80 weight1 max_fails2 fails_timeo…

ftp 断点续传 Android,Android使用FTP实现断点续传

Android使用FTP实现断点续传断点续传指的是在下载或上传时&#xff0c;将下载或上传任务(一个文件或一个压缩包)人为的划分为几个部分&#xff0c;每一个部分采用一个线程进行上传或下载&#xff0c;如果碰到网络故障&#xff0c;可以从已经上传或下载的部分开始继续上传下载未…