#include "opencv2/imgcodecs/legacy/constants_c.h"
#include <opencv2/opencv.hpp>
#include <iostream>
#include <random>
using namespace cv;
using namespace std;
void sharpen(const cv::Mat &image, cv::Mat &result)
{
// 判断是否需要分配图像数据。如果需要,就分配
result.create(image.size(), image.type());
int nchannels = image.channels(); // 获得通道数
// 处理所有行(除了第一行和最后一行)
for (int j = 1; j < image.rows - 1; j++)
{
const uchar *previous = image.ptr<const uchar>(j - 1); // 上一行
const uchar *current = image.ptr<const uchar>(j); // 当前行
const uchar *next = image.ptr<const uchar>(j + 1); // 下一行
uchar *output = result.ptr<uchar>(j); // 输出行
for (int i = nchannels; i < (image.cols - 1) * nchannels; i++)
{
// 应用锐化算子
*output++ = cv::saturate_cast<uchar>(
5.3 * current[i] - current[i - nchannels] -
current[i + nchannels] - previous[i] - next[i]);
}
}
// 把未处理的像素设为 0
result.row(0).setTo(cv::Scalar(0));
result.row(result.rows - 1).setTo(cv::Scalar(0));
result.col(0).setTo(cv::Scalar(0));
result.col(result.cols - 1).setTo(cv::Scalar(0));
}
void salt(cv::Mat image, int n)
{
// C++11 的随机数生成器
std::default_random_engine generator;
std::uniform_int_distribution<int>
randomRow(0, image.rows - 1);
std::uniform_int_distribution<int>
randomCol(0, image.cols - 1);
int i, j;
for (int k = 0; k < n; k++)
{
// 随机生成图形位置
i = randomCol(generator);
j = randomRow(generator);
if (image.type() == CV_8UC1)
{ // 灰度图像
// 单通道 8 位图像
image.at<uchar>(j, i) = 255;
}
else if (image.type() == CV_8UC3)
{ // 彩色图像
// 3 通道图像
image.at<cv::Vec3b>(j, i)[0] = 255;
image.at<cv::Vec3b>(j, i)[1] = 255;
image.at<cv::Vec3b>(j, i)[2] = 255;
}
}
}
void wave(const cv::Mat &image, cv::Mat &result)
{
// 映射参数
cv::Mat srcX(image.rows, image.cols, CV_32F);
cv::Mat srcY(image.rows, image.cols, CV_32F);
// 创建映射参数
for (int i = 0; i < image.rows; i++)
{
for (int j = 0; j < image.cols; j++)
{
// (i,j)像素的新位置
srcX.at<float>(i, j) = j; // 保持在同一列
// 原来在第 i 行的像素,现在根据一个正弦曲线移动
srcY.at<float>(i, j) = i + 7 * sin(j / 10.0);
}
}
// 应用映射参数
cv::remap(image, // 源图像
result, // 目标图像
srcX, // x 映射
srcY, // y 映射
cv::INTER_LINEAR); // 填补方法
}
void colorReduce(cv::Mat image, int div = 64)
{
int nl = image.rows; // 行数
// 每行的元素数量
int nc = image.cols * image.channels();
for (int j = 0; j < nl; j++)
{
// 取得行j的地址
uchar *data = image.ptr<uchar>(j);
for (int i = 0; i < nc; i++)
{
// 处理每个像素 ---------------------
data[i] = data[i] / div * div + div / 2;
// 像素处理结束 ----------------
}
}
}
int main()
{
//Mat src = imread("./1.png", IMREAD_GRAYSCALE);
Mat src = imread("./dlrb.png");
Mat src2 = imread("./dlrb.png");
Mat src3 = imread("./dlrb.png");
Mat src4 = imread("./dlrb.png");
Mat src5 = imread("./dlrb.png");
Mat src6;
Mat src7;
Mat src8;
if (src.empty())
{
cout << "Did not find the image" << endl;
return 0;
}
sharpen(src, src2);
wave(src, src3);
salt(src4, 3000);
colorReduce(src5, 64);
src6 = cv::imread("dlrb.png", CV_LOAD_IMAGE_GRAYSCALE);
cvtColor(src, src7, COLOR_BGR2HSV); // 真彩色
cvtColor(src, src8, COLOR_BGR2GRAY); // 灰色
imshow("原图", src);
imshow("锐化之后的图", src2);
imshow("波浪后的图", src3);
imshow("添加噪声以后的图", src4);
imshow("减少颜色以后的图", src5);
imshow("灰度图", src6);
imshow("真彩图", src7);
// imshow("灰度图", src8);
waitKey(0);
return 0;
}
?
|