实验2.1:对比度调整
设计一个Sigmoid函数,实现对图像的对比度调整(使用opencv窗口系统的slider控件,交互改变Sigmoid函数的参数,实现不同程度的对比度调整;)
(1)线性函数调节对比度亮度:
根据调节公式g(i,j) = af(i,j) + b*,在新建的图像里进行
new_image.at(y, x)[c] = saturate_cast
(0.01a(image.at(y,x)[c])+b)即可。
(2)线性测试截图:
代码
#include<opencv2/core/core.hpp>
#include<opencv2/imgcodecs.hpp>
#include<opencv2/core/saturate.hpp>
#include<opencv2/highgui/highgui.hpp>
#include<iostream>
using namespace std;
using namespace cv;
int main(int, char** argv)
{
double alpha = 1.0; //< Simple contrast control
int beta = 0; //< Simple brightness control
Mat image = imread("D:\\picture\\leaf.jpg");
Mat new_image = Mat::zeros(image.size(), image.type());//创建新的图像
cout << "* Enter the alpha value [1.0-3.0]: "; cin >> alpha;
cout << "* Enter the beta value [0-100]: "; cin >> beta;
for (int y = 0; y < image.rows; y++) {
for (int x = 0; x < image.cols; x++) {
for (int c = 0; c < 3; c++) {
new_image.at<Vec3b>(y, x)[c] = saturate_cast<uchar>(alpha * (image.at<Vec3b>(y, x)[c]) + beta);
}
}
}
namedWindow("Original Image", WINDOW_AUTOSIZE);
namedWindow("New Image", WINDOW_AUTOSIZE);
imshow("Original Image", image);
imshow("New Image", new_image);
waitKey();
return 0;
}
(3)sigmoid函数对比度亮度调节
Sigmoid函数,即f(x)=1/(1+e-x),该函数具有如下的特性:当x趋近于负无穷时,y趋近于0;当当x趋近于正无穷时,y趋近于1;x等于0时,y等于1/2。
对其求导并结合图像给定参数,得到函数
255/(1+e−k(x−127.5))
则核心调节对比度亮度代码为
new_image.at(y, x)[c] = saturate_cast
(image.at(y, x)[c] * ((1.00 / (1.00 + exp(-t))) + 0.3) + b)
;
(4)最后创建滑动条来调节参数
int createTrackbar(const string& trackbarname, const string&winname, int* value, int count ,TrackbarCallback onChange = 0, void* userdata = 0);
参数1:轨迹条名字
参数2:窗口名字
参数3:滑块初始位置
参数4:表示滑块达到最大位置的值
参数5:默认值为0,指向回调函数
参数6:默认值为0,用户传给回调函数的数据值
#include <opencv2/core/core.hpp>
#include<opencv2/highgui/highgui.hpp>
#include"opencv2/imgproc/imgproc.hpp"
#include<math.h>
#include <iostream>
using namespace std;
using namespace cv;
static void ContrastAndBright(int, void*);
int c_p;
int b_value;
Mat s_image, t_imag;
int main()
{
s_image = imread("D:\\picture\\leaf.jpg");
if (!s_image.data)
{
cout << "图片读取失败!" << endl;
return false;
}
t_imag = Mat::zeros(s_image.size(), s_image.type());
c_p = 20;
b_value = 100;
namedWindow("Slider", WINDOW_AUTOSIZE);
createTrackbar("对比度", "Slider", &c_p, 200, ContrastAndBright);
createTrackbar("亮 度", "Slider", &b_value, 200, ContrastAndBright);
ContrastAndBright(c_p, 0);
ContrastAndBright(b_value, 0);
waitKey(0);
return 0;
}
static void ContrastAndBright(int, void*)
{
namedWindow("Image", WINDOW_AUTOSIZE);
for (int y = 0; y < s_image.rows; y++)
{
for (int x = 0; x < s_image.cols; x++)
{
for (int c = 0; c < 3; c++)
{
double t = ((s_image.at<Vec3b>(y, x)[c] - 127) / 225.00) * c_p * 0.1;
t_imag.at<Vec3b>(y, x)[c] = saturate_cast<uchar>(s_image.at<Vec3b>(y, x)[c] * ((1.00 / (1.00 + exp(-t))) + 0.3) + b_value - 100);
}
}
}
imshow("Image", s_image);
imshow("Slider", t_imag);
}
(5)测试截图
通过滑动条对对比度和亮度分别进行调节