原文地址:http://blog.csdn.net/lichengyu/article/details/20840135
图2中左图为原图,中图为gamma = 1/2.2在校正结果,原图中左半侧的灰度值较高,右半侧的灰度值较低,经过gamma = 1/2.2校正后(中图),左侧的对比度降低(见胡须),右侧在对比度提高(明显可以看清面容),同时图像在的整体灰度值提高。
右图为gamma = 2.2在校正结果,校正后,左侧的对比度提高(见胡须),右侧在对比度降低(面容更不清楚了),同时图像在的整体灰度值降低。
值得一提的是,人眼是按照gamma < 1的曲线对输入图像进行处理的。
参考资料:
[1] http://en.wikipedia.org/wiki/Gamma_correction
[2] http://www.cambridgeincolour.com/tutorials/gamma-correction.htm
[3] https://github.com/bytefish/opencv/blob/master/misc/tan_triggs.cpp
代码:
- #include <opencv2/core/core.hpp>
- #include <opencv2/imgproc/imgproc.hpp>
- #include <opencv2/highgui/highgui.hpp>
- #include <iostream>
- using namespace cv;
- using namespace std;
- // Normalizes a given image into a value range between 0 and 255.
- Mat norm_0_255(const Mat& src) {
- // Create and return normalized image:
- Mat dst;
- switch(src.channels()) {
- case 1:
- cv::normalize(src, dst, 0, 255, NORM_MINMAX, CV_8UC1);
- break;
- case 3:
- cv::normalize(src, dst, 0, 255, NORM_MINMAX, CV_8UC3);
- break;
- default:
- src.copyTo(dst);
- break;
- }
- return dst;
- }
- int main(int argc, const char *argv[]) {
- // Get filename to the source image:
- if (argc != 2) {
- cout << "usage: " << argv[0] << " <image.ext>" << endl;
- exit(1);
- }
- // Load image & get skin proportions:
- //Mat image = imread(argv[1], CV_LOAD_IMAGE_GRAYSCALE);
- Mat image = imread(argv[1], CV_LOAD_IMAGE_COLOR);
- // Convert to floating point:
- Mat X;
- image.convertTo(X, CV_32FC1);
- //image.convertTo(X, CV_32F);
- // Start preprocessing:
- Mat I;
- float gamma = 1/2.2;
- pow(X, gamma, I);
- // Draw it on screen:
- imshow("Original Image", image);
- imshow("Gamma correction image", norm_0_255(I));
- //imwrite("origin.jpg", image);
- imwrite("gamma_inv2.2.jpg", norm_0_255(I));