当前位置: 首页 > news >正文

利用OpenCV做个熊猫表情包 二

之前写了一篇

利用OpenCV做个熊猫表情包吧_Leen的博客-CSDN博客

回想起来觉得有点太弱了,意犹未尽,每次使用需要自己去手动截取人脸,清除黑边什么的才能使用demo去合成表情,无奈之前由于安装的vs,opencv版本都比较低,也懒得再折腾。

恰逢前些天电脑硬盘坏了,数据丢了,一切都要重装,那直接高配走起,VS2022+OpenCV4.8,既然环境都有了,于是有空的时候就改进了一下,让它利用opencv,做简单的人脸识别,自动去图片中识别、提取人脸,同时去做黑边清理工作,自动化程度更高,用起来更省事儿~

原理呢就是在处理原始图片的流程中加入了面部识别,将面部单独切出来,同时对面部图片做黑边清晰处理,然后再进行表情的合成工作,下面介绍一下具体过程:

首先是识别到用户输入的原图

利用opencv进行面部识别

灰度化图片后提取面部,并清理黑边

再将面部跟熊猫脸进行融合

下面介绍关键步骤的代码:

初始化面部识别

int InitFaceDetect()
{if (!faceCascade.load("D:\\Workspace\\opencv\\build\\etc\\haarcascades\\haarcascade_frontalface_default.xml")) {cout << "人脸检测级联分类器没找到!!" << endl;return -1;}if (!eyes_Cascade.load("D:\\Workspace\\opencv\\build\\etc\\haarcascades\\haarcascade_eye_tree_eyeglasses.xml")) {cout << "眼睛检测级联分类器没找到!!" << endl;return -1;}return 0;
}

用到的两个xml特征文件均为openCV提供。

清楚灰度图像中的深色边角区域

/************************************************************************/
/* 消除图片四周的黑色边角区域                                           */
/************************************************************************/Mat RemoveBlackCorner(Mat img)
{int i, j;int h = img.size().height;int w = img.size().width;if (img.channels() == 1)	//灰度图片{for (j = 0; j < h; j++){for (i = 0; i < w; i++){if (img.at<uchar>(j, i) < 110){img.at<uchar>(j, i) = 255;}else{break;}}for (i = w - 1; i >= 0; i--){if (img.at<uchar>(j, i) < 110){img.at<uchar>(j, i) = 255;}else{break;}}}for (i = 0; i < w; i++){for (j = 0; j < h; j++){if (img.at<uchar>(j, i) < 110){img.at<uchar>(j, i) = 255;}else{break;}}for (j = h - 1; j >= 0; j--){if (img.at<uchar>(j, i) < 110){img.at<uchar>(j, i) = 255;}else{break;}}}}return img;
}

人脸识别以及将加工后的人脸存成临时文件

bool parse_cmd(int argc, char* argv[])
{if (argc < 3){return false;}g_str_src = string(argv[1]);g_str_bg = string(argv[2]);return true;
}string GetFolderFromFile(string strFile)
{size_t last_slash = strFile.find_last_of("\\");std::string directory = strFile.substr(0, last_slash);return directory;
}int DetectFace(Mat img, Mat imgGray) {namedWindow("src", WINDOW_AUTOSIZE);vector<Rect> faces, eyes;faceCascade.detectMultiScale(imgGray, faces, 1.2, 5, 0, Size(30, 30));int retVal = -1;//目前只取一个脸if (faces.size() > 0) {for (size_t i = 0; i < faces.size(); i++) {//框出人脸位置rectangle(img, Point(faces[i].x+ faces[i].width / 8, faces[i].y+faces[i].height / 8), Point(faces[i].x + faces[i].width*7/8, faces[i].y + faces[i].height * 7 / 8), Scalar(0, 0, 255), 1, 8);cout << faces[i] << endl;//将人脸从灰度图中抠出来Mat face_ = imgGray(faces[i]);//缩小一点,默认取的矩形比较大Rect rect(Point(faces[i].width / 8, faces[i].height / 8),Point(faces[i].width * 7 / 8,  faces[i].height * 7/ 8));Mat ROI = face_(rect);//RemoveBlackBorder(ROI, ROI);Mat imgOut = RemoveBlackCorner(ROI);//RemoveBlackBorder(ROI, imgOut);imwrite(g_str_face, imgOut);retVal = 0;eyes_Cascade.detectMultiScale(face_, eyes, 1.2, 2, 0, Size(30, 30));for (size_t j = 0; j < eyes.size(); j++) {Point eye_center(faces[i].x + eyes[j].x + eyes[j].width / 2, faces[i].y + eyes[j].y + eyes[j].height / 2);int radius = cvRound((eyes[j].width + eyes[j].height) * 0.25);circle(img, eye_center, radius, Scalar(65, 105, 255), 4, 8, 0);}}}imshow("src", img);return retVal;
}

主逻辑流程


int main(int argc, char* argv[])
{if (!parse_cmd(argc, argv)){cout << "command error" << endl;return -1;}if (InitFaceDetect() != 0){return -1;}//string strDirBase = GetFolderFromFile(g_str_src);Mat img_src = imread(g_str_src);Mat img_background = imread(g_str_bg);g_str_face = strDirBase + "\\tmp_face.jpg";
#ifdef _DBG_SHOWnamedWindow("img_src");imshow("img_src", img_src);
#endifMat img_gray;cvtColor(img_src, img_gray, COLOR_BGR2GRAY); //图像灰度化int nFace = DetectFace(img_src, img_gray);waitKey(3000);
#ifdef _DBG_SHOWnamedWindow("gray", WINDOW_NORMAL);imshow("gray", img_gray);
#endif// 按照背景图大小等比缩放Size dsize = Size(img_background.cols * 0.55, img_background.rows * 0.55);//判断一下是否自动检测到了人脸Mat img_face;if (nFace == 0) {cout << "opencv find face,get face." << endl;img_face = imread(g_str_face);}else{cout << "can not find face.use image user input." << endl;img_face = img_gray;}resize(img_face, img_face, dsize, 1, 1, INTER_AREA);//输出缩放后效果图并重新加载Mat img_face2;threshold(img_face, img_face2, 105, 255, THRESH_BINARY);imwrite(strDirBase + "\\tmp.jpg", img_face2);//imshow("img_face2", img_face2);Mat img_face3 = imread(strDirBase + "\\tmp.jpg");//居中粘合两图Rect roi_rect = Rect((img_background.cols - img_face3.cols) / 2, (img_background.rows - img_face3.rows) / 2, img_face3.cols, img_face3.rows);img_face3.copyTo(img_background(roi_rect));//显示并输出imshow("mixed", img_background);imwrite(g_str_src + ".emoji.jpg", img_background);waitKey(5000);destroyAllWindows();return 0;
}

相关文章:

利用OpenCV做个熊猫表情包 二

之前写了一篇 利用OpenCV做个熊猫表情包吧_Leen的博客-CSDN博客 回想起来觉得有点太弱了&#xff0c;意犹未尽&#xff0c;每次使用需要自己去手动截取人脸&#xff0c;清除黑边什么的才能使用demo去合成表情&#xff0c;无奈之前由于安装的vs&#xff0c;opencv版本都比较低…...

华纳云服务器怎么清理cdn缓存?

清理 CDN(内容分发网络)缓存通常需要通过 CDN 提供商的管理界面或 API 进行操作。不同的 CDN 提供商可能有不同的方法和步骤&#xff0c;以下是一个通用的清理 CDN 缓存的一般步骤&#xff1a; 1. 登录到 CDN 提供商的管理界面&#xff1a; 打开你所使用的 CDN 提供商的网站。 …...

python functools.wraps保留被装饰函数属性

作用 普通装饰器 &#xff0c;会覆盖函数名称&#xff0c;并且 会替换 函数 文档字符串 介绍 functools.wraps(wrapped[, assigned][, updated]) This is a convenience function for invoking partial(update_wrapper, wrappedwrapped, assignedassigned, updatedupdated) …...

【多线程 - 11、死锁】

死锁 1、介绍 在 Java 中使用多线程&#xff0c;就会有可能导致死锁问题。死锁会让程序一直卡住&#xff0c;程序不再往下执行。只能通过中止并重启的方式来让程序重新执行。要尽可能避免死锁的情况发生 2、造成死锁的原因 互斥条件&#xff1a; 同一资源同时只能由一个线程读…...

flask实现session开发

要在Flask应用中实现会话&#xff08;session&#xff09;开发&#xff0c;你可以使用Flask内置的session模块。以下是一个示例代码&#xff0c;演示在Flask应用中启用和使用会话功能&#xff1a; from flask import Flask, session, redirect, url_for, requestapp Flask(__…...

paddle dataset

paddle实现图像旋转 import numpy as np from PIL import Image from matplotlib import pyplot as plt from paddle.vision.transforms import functional as F import cv2imagecv2.imread(./1.jpg) imagecv2.cvtColor(image,cv2.COLOR_BGR2RGB)# 图像旋转 opencv # imgR90 …...

接口自动化测试实战:JMeter+Ant+Jenkins+钉钉机器人群通知完美结合

前言 一、本地JAVA环境安装配置,安装JAVA8和JAVA17 二、安装和配置Jmeter 三、安装和配置ant 四、jmeter + ant配置 五、jenkins安装和配置持续构建项目 六、jenkins配置流程 前言 搭建jmeter+ant+jenkins环境有些前提条件,那就是要先配置好java环境,本地java环境…...

HAL库STM32串口开启DMA接收数据

STM32CubeMx的配置 此博客仅仅作为记录&#xff0c;这个像是有bug一样&#xff0c;有时候好使&#xff0c;有时候不好&#xff0c;所以趁现在好使赶紧记录一下&#xff0c;很多地方用到串口接收数据&#xff0c;DMA又是一种非常好的接收方式&#xff0c;可以节约CPU的时间&…...

Web安全研究(五)

Automated WebAssembly Function Purpose Identification With Semantics-Aware Analysis WWW23 文章结构 introbackgroundsystem design abstraction genapplying abstractionsclassifier data collection and handling data acquisitionstatistics of collected datamodule-…...

2023.11.17-hive调优的常见方式

目录 0.设置hive参数 1.数据压缩 2.hive数据存储格式 3.fetch抓取策略 4.本地模式 5.join优化操作 6.SQL优化(列裁剪,分区裁剪,map端聚合,count(distinct),笛卡尔积) 6.1 列裁剪: 6.2 分区裁剪: 6.3 map端聚合(group by): 6.4 count(distinct): 6.5 笛卡尔积: 7…...

ts 联合react 实现ajax的封装,refreshtoken的功能

react ts混合双打&#xff0c;实现ajax的封装&#xff0c;以及401的特殊处理 import axios from axios import {AMDIN_EXPIRES_KEY,AMDIN_KEY,AMDIN_REFRESH_EXPIRES_KEY,AMDIN_REFRESH_KEY,COMMID_KEY,getToken,removeToken } from ../utils/user-token import { showMessage…...

CISP模拟试题(一)

免责声明 文章仅做经验分享用途,利用本文章所提供的信息而造成的任何直接或者间接的后果及损失,均由使用者本人负责,作者不为此承担任何责任,一旦造成后果请自行承担!!! 1.下面关于信息安全保障的说法错误的是:C A.信息安全保障的概念是与信息安全的概念同时产生的 …...

轻量封装WebGPU渲染系统示例<35>- HDR环境数据应用到PBR渲染材质

当前示例源码github地址: https://github.com/vilyLei/voxwebgpu/blob/feature/rendering/src/voxgpu/sample/BasePbrMaterialTest.ts 当前示例运行效果: 微调参数之后的效果: 此示例基于此渲染系统实现&#xff0c;当前示例TypeScript源码如下: export class BasePbrMateri…...

春秋云境靶场CVE-2022-28512漏洞复现(sql手工注入)

文章目录 前言一、CVE-2022-28512靶场简述二、找注入点三、CVE-2022-28512漏洞复现1、判断注入点2、爆显位个数3、爆显位位置4 、爆数据库名5、爆数据库表名6、爆数据库列名7、爆数据库数据 总结 前言 此文章只用于学习和反思巩固sql注入知识&#xff0c;禁止用于做非法攻击。…...

数字化文化的守护之星:十八数藏的非遗创新之道

在数字时代的浪潮中&#xff0c;十八数藏犹如一颗璀璨的守护之星&#xff0c;为传统文化注入了新的生命力。这个非遗创新项目以数字化为工具&#xff0c;以守护为使命&#xff0c;开辟了文化传承的新航道。 十八数藏是文化数字守护的引领者&#xff0c;通过数字技术&#xff0…...

[机缘参悟-119] :反者道之动与阴阳太极

目录 一、阴阳对立、二元对立的规律 1.1 二元对立 1.2 矛盾的对立与统一 二、阴阳互转、阴阳变化、变化无常 》无序变化和有序趋势的规律 三、阴阳合一、佛魔一体、善恶同源 四、看到积极的一面 五、反者道之动 5.1 概述 5.2 "否极泰来" 5.3 “乐极生悲”…...

Docker搭建Redis集群

Docker搭建Redis集群 创建一个专属redis的网络 docker network create redis --subnet 172.38.0.0/16通过shell脚本创建并启动6个redis服务 #通过脚本一次创建6个redis配置 for port in $(seq 1 6); \ do \ mkdir -p /mydata/redis/node-${port}/conf touch /mydata/redis/n…...

学习Opencv(蝴蝶书/C++)代码——2.OpenCV初探

文章目录 0. 图像读取与显示1. 视频文件读取与操作1.1 示例代码1.1 OpenCV支持的视频格式2. 加入滑动条2.1 示例代码2.2 报错/Warning2.3 关于toolbar3. 简易视频播放器3.1 OpenCV检测方向键被按下3.1.1 Windows下3.1.2 linux下3.1 方向键控制视频变化4. 简单的变换5. 写视频5.…...

基于AVR单片机的便携式心电监测设备设计与实现

基于AVR单片机的便携式心电监测设备是一种常用的医疗设备&#xff0c;用于随时监测和记录人体的心电信号。本文将介绍便携式心电监测设备的设计原理和实现步骤&#xff0c;并提供相应的代码示例。 1. 设计概述 便携式心电监测设备是一种小巧、方便携带的设备&#xff0c;能够…...

微机原理_14

一、单项选择题(本大题共15小题,每小题3分,共45分。在每小题给出的四个备选项中,选出一个正确的答案。&#xff09; 1,下面寻址方式的操作数不在存储器中的是(&#xff09; A. 堆栈寻址 B. 寄存器间址 C.寄存器寻址 D. 直接寻址 2,条件转移指令JNE的条件是(&#xff09; A. CF…...

Go 语言接口详解

Go 语言接口详解 核心概念 接口定义 在 Go 语言中&#xff0c;接口是一种抽象类型&#xff0c;它定义了一组方法的集合&#xff1a; // 定义接口 type Shape interface {Area() float64Perimeter() float64 } 接口实现 Go 接口的实现是隐式的&#xff1a; // 矩形结构体…...

Java-41 深入浅出 Spring - 声明式事务的支持 事务配置 XML模式 XML+注解模式

点一下关注吧&#xff01;&#xff01;&#xff01;非常感谢&#xff01;&#xff01;持续更新&#xff01;&#xff01;&#xff01; &#x1f680; AI篇持续更新中&#xff01;&#xff08;长期更新&#xff09; 目前2025年06月05日更新到&#xff1a; AI炼丹日志-28 - Aud…...

【RockeMQ】第2节|RocketMQ快速实战以及核⼼概念详解(二)

升级Dledger高可用集群 一、主从架构的不足与Dledger的定位 主从架构缺陷 数据备份依赖Slave节点&#xff0c;但无自动故障转移能力&#xff0c;Master宕机后需人工切换&#xff0c;期间消息可能无法读取。Slave仅存储数据&#xff0c;无法主动升级为Master响应请求&#xff…...

NLP学习路线图(二十三):长短期记忆网络(LSTM)

在自然语言处理(NLP)领域,我们时刻面临着处理序列数据的核心挑战。无论是理解句子的结构、分析文本的情感,还是实现语言的翻译,都需要模型能够捕捉词语之间依时序产生的复杂依赖关系。传统的神经网络结构在处理这种序列依赖时显得力不从心,而循环神经网络(RNN) 曾被视为…...

uniapp中使用aixos 报错

问题&#xff1a; 在uniapp中使用aixos&#xff0c;运行后报如下错误&#xff1a; AxiosError: There is no suitable adapter to dispatch the request since : - adapter xhr is not supported by the environment - adapter http is not available in the build 解决方案&…...

在WSL2的Ubuntu镜像中安装Docker

Docker官网链接: https://docs.docker.com/engine/install/ubuntu/ 1、运行以下命令卸载所有冲突的软件包&#xff1a; for pkg in docker.io docker-doc docker-compose docker-compose-v2 podman-docker containerd runc; do sudo apt-get remove $pkg; done2、设置Docker…...

Unsafe Fileupload篇补充-木马的详细教程与木马分享(中国蚁剑方式)

在之前的皮卡丘靶场第九期Unsafe Fileupload篇中我们学习了木马的原理并且学了一个简单的木马文件 本期内容是为了更好的为大家解释木马&#xff08;服务器方面的&#xff09;的原理&#xff0c;连接&#xff0c;以及各种木马及连接工具的分享 文件木马&#xff1a;https://w…...

html css js网页制作成品——HTML+CSS榴莲商城网页设计(4页)附源码

目录 一、&#x1f468;‍&#x1f393;网站题目 二、✍️网站描述 三、&#x1f4da;网站介绍 四、&#x1f310;网站效果 五、&#x1fa93; 代码实现 &#x1f9f1;HTML 六、&#x1f947; 如何让学习不再盲目 七、&#x1f381;更多干货 一、&#x1f468;‍&#x1f…...

Kafka入门-生产者

生产者 生产者发送流程&#xff1a; 延迟时间为0ms时&#xff0c;也就意味着每当有数据就会直接发送 异步发送API 异步发送和同步发送的不同在于&#xff1a;异步发送不需要等待结果&#xff0c;同步发送必须等待结果才能进行下一步发送。 普通异步发送 首先导入所需的k…...

RabbitMQ入门4.1.0版本(基于java、SpringBoot操作)

RabbitMQ 一、RabbitMQ概述 RabbitMQ RabbitMQ最初由LShift和CohesiveFT于2007年开发&#xff0c;后来由Pivotal Software Inc.&#xff08;现为VMware子公司&#xff09;接管。RabbitMQ 是一个开源的消息代理和队列服务器&#xff0c;用 Erlang 语言编写。广泛应用于各种分布…...