C++OpenCV利用Trackbar实现对图片的滑动阈值调节

代码如下所:

#include <opencv2/opencv.hpp>
#include <iostream>
#include"myApi.h"

using namespace std;
using namespace cv;

Mat g_srcImg; //原图片
Mat g_beautyFgImg;  //美颜后的前景图
Mat g_vagueBeImg;  //模糊后背景图
Mat g_roiImg;  //前景和后景组合后图片
Mat g_rectImg;  //绘制矩形边框
Mat g_brightImg;  //调整亮度


// 调整模糊程度
int g_iVagueValue = 3;
int g_iVagueMaxValue = 10;

// 调整美颜程度
int g_iBeautyValue = 9;
int g_iBeautyMaxValue = 20;

// 绘制矩形,设置相框
int g_iRectValue = 5;
int g_iRectMaxValue = 30;

//调整亮度范围
int g_iBrightValue = 6;
int g_iBrightMaxValue = 20;

//调整模糊程度
void TrackbarVague(int, void*);

//调整美颜程度
void TrackbarBeauty(int, void*);

//绘制矩形调整相框
void TrackbarRect(int, void*);

//调整亮度程度
void TrackbarBright(int, void*);

//将美颜前景图调到模糊背景图层上
void SetRoi(void);

int main()
{
	g_srcImg = imread("F:\\testImage\\test2.png");
	if (!g_srcImg.data)
		return -1;
	namedWindow("img", WINDOW_FREERATIO);
	imshow("img", g_srcImg);

	/*
	功能:创建滚动条并将其附加到指定的窗口
	参数:trackbarname:创建的滚动条名称
		  winname:滚动条父窗口的名称
		  value:滚动条所在位置的值
		  count:滚动条的最大值,最小值总是0
		  onChange:指向滚动条改变位置时要调用的函数的指针(回调函数),函数的原型应该是void Foo(int, void*);
					其中第一个参数是滚动条所在的位置,第二个参数是用户数据(见下一个参数);如果回调函数传空,则不调用
					回调,但只更新滚动条值
		  userdata:按原样传递给回调的用户数据,它可以用来处理滚动条不使用全局变量事件
	返回:成功返回0
	*/

	createTrackbar("背景模糊", "img", &g_iVagueValue, g_iVagueMaxValue, TrackbarVague);
	createTrackbar("前景美颜", "img", &g_iBeautyValue, g_iBeautyMaxValue, TrackbarBeauty);
	TrackbarBeauty(0, 0);

	createTrackbar("相框宽度", "img", &g_iRectValue, g_iRectMaxValue, TrackbarRect);
	TrackbarRect(0, 0);

	createTrackbar("图片亮度", "img", &g_iBrightValue, g_iBrightMaxValue, TrackbarBright);
	TrackbarBright(0, 0);
	TrackbarVague(0, 0);
	waitKey(0);
	return 0;
}

void TrackbarVague(int, void*)
{
	//SignaX和SigmaY必须是奇数
	int iSigma = 2 * g_iVagueValue + 1;
	//利用高斯模糊做底图
	GaussianBlur(g_srcImg, g_vagueBeImg, Size(iSigma, iSigma), iSigma, iSigma);
	//全部初始化完才显示
	if (g_beautyFgImg.data && g_vagueBeImg.data)
	{
		SetRoi();
	}
}

void TrackbarBeauty(int, void*)
{
	// 利用双边模糊,实现磨皮的效果
	int iSigmaSpace = 50 + 10 * g_iBeautyValue;
	Mat tmpImg;
	bilateralFilter(g_srcImg, tmpImg, 15, iSigmaSpace, 0);

	// 再利用掩膜计算,增加图像对比度,最终实现美颜相机的效果
	Mat kernal = (Mat_<int>(3, 3) << 0, -1, 0, -1, 5, -1, 0, -1, 0);
	filter2D(tmpImg, g_beautyFgImg, -1, kernal, Point(-1, -1), 0);

	// 功能:调整图像大小
	// 参数:src 源图像
	//		 dst 目标图像
	//		 dsize 输出图像大小,如果为(0, 0),则大小为(img.cols * fx, img.rows * fy)
	//		 fx x方向的缩小比例
	//		 fy y方向的缩小比例
	resize(g_beautyFgImg, g_beautyFgImg, Size(0, 0), 0.8, 0.8);

	// 全部初始化完才显示
	if (g_beautyFgImg.data && g_vagueBeImg.data)
	{
		SetRoi();
	}
}

void TrackbarRect(int, void*)
{
	if (!g_roiImg.data)
	{
		return;
	}

	// 绘制一个矩形,当做相框
	int iPosX = (g_vagueBeImg.cols - g_beautyFgImg.cols) / 2 - g_iRectValue / 2;
	int iPosY = (g_vagueBeImg.rows - g_beautyFgImg.rows) / 2 - g_iRectValue / 2;
	int iWidth = g_beautyFgImg.cols + g_iRectValue;
	int iHeight = g_beautyFgImg.rows + g_iRectValue;
	Rect rect(iPosX, iPosY, iWidth, iHeight);
	Scalar color(255, 255, 255);
	g_rectImg = g_roiImg.clone();
	rectangle(g_rectImg, rect, color, g_iRectValue);

	// 调整颜色
	TrackbarBright(g_iBrightValue, 0);
}

void TrackbarBright(int, void*)
{
	if (!g_rectImg.data)
	{
		cout << "g_rectImg is empty" << endl;
		return;
	}
	int iRows = g_rectImg.rows;
	int iCols = g_rectImg.cols;
	Mat tmpImg = Mat::zeros(g_rectImg.size(), g_rectImg.type());
	float fAlpha = 0.1 + (float)g_iBrightValue / 10.0;
	float fBeta = 30; // 增益变量

	for (int i = 0; i < iRows; i++)
	{
		for (int j = 0; j < iCols; j++)
		{
			if (g_rectImg.channels() == 1)
			{
				float f = g_rectImg.at<uchar>(i, j);
				tmpImg.at<uchar>(i, j) = saturate_cast<uchar>(f * fAlpha + fBeta);
			}
			else if (g_rectImg.channels() == 3)
			{
				float fGreen = g_rectImg.at<Vec3b>(i, j)[0];
				float fBlue = g_rectImg.at<Vec3b>(i, j)[1];
				float fRed = g_rectImg.at<Vec3b>(i, j)[2];

				tmpImg.at<Vec3b>(i, j)[0] = saturate_cast<uchar>(fGreen * fAlpha + fBeta);
				tmpImg.at<Vec3b>(i, j)[1] = saturate_cast<uchar>(fBlue * fAlpha + fBeta);
				tmpImg.at<Vec3b>(i, j)[2] = saturate_cast<uchar>(fRed * fAlpha + fBeta);
			}
		}
	}

	// 保存调整亮度后的背景图
	g_brightImg = tmpImg.clone();

	imshow("img", g_brightImg);
}


void SetRoi(void)
{
	// 设定ROI区域
	int iPosX = (g_vagueBeImg.cols - g_beautyFgImg.cols) / 2;
	int iPosY = (g_vagueBeImg.rows - g_beautyFgImg.rows) / 2;
	g_roiImg = g_vagueBeImg.clone();
	Mat imageROI = g_roiImg(Rect(iPosX, iPosY, g_beautyFgImg.cols, g_beautyFgImg.rows));
	//加载掩摸
	Mat mask;
	cvtColor(g_beautyFgImg, mask, COLOR_BGR2GRAY);
	g_beautyFgImg.copyTo(imageROI, mask);
	TrackbarRect(g_iRectValue, 0);
}

实验结果如下所示:

 

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
实现人脸识别的常用方法是利用人脸检测和人脸识别技术。在此基础上,可以使用C++OpenCV库来实现人脸识别。下面是一个简单的步骤: 1. 加载人脸检测器模型文件。OpenCV提供了Haar分类器和人脸识别模型文件,可以直接下载并使用。 2. 加载待检测的图片。 3. 对图片进行预处理,如灰度化、直方图均衡化等。 4. 使用人脸检测器模型文件检测人脸位置。 5. 利用人脸识别算法比对人脸特征,进行人脸识别。 以下是一个简单的C++代码示例: ```C++ #include <opencv2/opencv.hpp> #include <opencv2/face.hpp> using namespace cv; using namespace cv::face; int main() { // 加载人脸检测器模型文件 CascadeClassifier faceDetector("haarcascade_frontalface_default.xml"); // 加载人脸识别器模型文件 Ptr<LBPHFaceRecognizer> faceRecognizer = LBPHFaceRecognizer::create(); faceRecognizer->read("face_recognizer.xml"); // 加载待检测的图片 Mat img = imread("test.jpg"); // 对图片进行预处理 Mat grayImg; cvtColor(img, grayImg, COLOR_BGR2GRAY); equalizeHist(grayImg, grayImg); // 检测人脸位置 std::vector<Rect> faces; faceDetector.detectMultiScale(grayImg, faces, 1.1, 2, 0, Size(30, 30)); // 对每个检测到的人脸进行识别 for (int i = 0; i < faces.size(); i++) { Mat faceImg = grayImg(faces[i]); // 比对人脸特征,进行人脸识别 int label = -1; double confidence = 0; faceRecognizer->predict(faceImg, label, confidence); // 在图片中标出人脸位置和识别结果 rectangle(img, faces[i], Scalar(255, 0, 0), 2); putText(img, format("Label: %d, Confidence: %.2f", label, confidence), Point(faces[i].x, faces[i].y - 10), FONT_HERSHEY_PLAIN, 1.0, Scalar(255, 0, 0), 2); } // 显示结果 imshow("Face Recognition", img); waitKey(0); return 0; } ``` 需要注意的是,人脸识别的准确率和速度受到多种因素的影响,如人脸图像的质量、人脸识别算法的选择和参数等。在实际应用中,需要根据具体需求进行优化和调整。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

AI炮灰

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值