1. 程式人生 > >影象花屏效果或者模糊效果新增

影象花屏效果或者模糊效果新增


#include <string>
#include <vector>
#include <dirent.h>
#include <iostream>
#include <fstream>
#include "opencv2/opencv.hpp"
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/core/core.hpp"
#include "opencv2/imgproc/imgproc.hpp"

using namespace std;
using namespace cv;
void flower_screen(const cv::Mat* input, const cv::Rect* rect, cv::Mat* output);
void blurred(const cv::Mat* input, cv::Mat* output);
Mat img_input;
Mat img_mosaic;
Mat img_clone;

//馬賽克的大小
int neightbourhood = 20;

//記錄滑鼠的狀態,0為滑鼠左鍵未按下或彈起,1為滑鼠左鍵按下
int mouseStatus = 0;

void on_mouse(int events, int x, int y, int flag, void* ustg);

//建立馬賽克圖片
void createMosaicImage(Mat inputMat, Mat& outputMat, int size);

//設定馬賽克區域
void set_mosaic(Mat& inputMat, Rect rect);
//
//int main(int argc, char** argv){
//    inputImage = imread("test2.jpg");
//    inputImage_clone = inputImage.clone();
//    createMosaicImage(inputImage, inputImage_mosaic, neightbourhood);
//
//    namedWindow("showImage", 0);
//    setMouseCallback("showImage", onMouse);
//
//    waitKey();
//    return 0;
//}

void createMosaicImage(Mat inputMat, Mat& outputMat, int size){
    RNG rng;
    int height = inputMat.rows;
    int width = inputMat.cols;
    Mat padding;
    Mat tempMat;

    //為了方便後面的計算,將輸入的影象大小擴充到寬高都是size的倍數
    copyMakeBorder(inputMat, padding, 0, size - inputMat.rows % size, 0, size - inputMat.cols % size, BORDER_REPLICATE);
    tempMat = padding.clone();
    
    for (int row = 0; row < padding.rows; row += size){
        for (int col = 0; col < padding.cols; col += size){
            int rand_x = rng.uniform(0, size);
            int rand_y = rng.uniform(0, size);
            Rect rect = Rect(col, row, size, size);
            Mat roi = tempMat(rect);
            Scalar color = Scalar(padding.at<Vec3b>(row + rand_y, col + rand_x)[0], \
                padding.at<Vec3b>(row + rand_y, col + rand_x)[1], \
                padding.at<Vec3b>(row + rand_y, col + rand_x)[2]);
            roi.setTo(color);
        }
    }
    outputMat = tempMat(Rect(0, 0, width, height)).clone();
}

void set_mosaic(Mat& inputMat, Rect rect){
    Mat roi = inputMat(rect);
    Mat tempRoi = img_mosaic(rect);
    tempRoi.copyTo(roi);
}

void on_mouse(int events, int x, int y, int flag, void* ustg){

    //當滑鼠移除圖片區域的時候,不做操作
    if (x < 0 || x > img_input.cols || y < 0 || y > img_input.rows){
        return;
    }

    //馬賽克塊的位置資訊
    int x_left, x_right, y_top, y_bottom;
    x - neightbourhood <= 0 ? x_left = 0 : x_left = x - neightbourhood;
    x + neightbourhood > img_input.cols ? x_right = img_input.cols: x_right = x + neightbourhood;
    y - neightbourhood <= 0 ? y_top = 0 : y_top = y - neightbourhood;
    y + neightbourhood > img_input.rows ? y_bottom = img_input.rows: y_bottom = y + neightbourhood;

    if (events == CV_EVENT_LBUTTONDOWN){
        mouseStatus = 1;
        set_mosaic(img_clone, Rect(x_left, y_top, x_right - x_left, y_bottom - y_top));
    }
    else if (events == CV_EVENT_MOUSEMOVE){
        if (mouseStatus == 1){
            set_mosaic(img_clone, Rect(x_left, y_top, x_right - x_left, y_bottom - y_top));
        }
        else{
            //nothing
        }
    }
    else if (events == CV_EVENT_LBUTTONUP){
        mouseStatus = 0;
    }
    else {
        //cout << "nothing" << endl;
    }
    imshow("showImage", img_clone);
}


int main(int argc, char** argv)
{
//    ofstream in;
//    in.open("svm_pos_20180906.txt",ios::trunc); // turn to creat the name of txt
    DIR *dp;
    struct dirent *dirp;
    string path = argv[1];

    vector<std::string> filename;
    if( (dp=opendir(path.c_str()) )==NULL )
    perror("open dir error");
    while( (dirp=readdir(dp) )!= NULL )
    filename.push_back(path + "/"+ string(dirp->d_name));

       int size = filename.size();
       for (int i = 0; i < size; i++)
       {
            if(filename[i] == path + "/" + "." or
            filename[i] == path + "/" + ".."){
                continue;
            }
            //cout << files[i].c_str() << endl;
            Mat img = imread(filename[i]);
            if (img.empty())
            {
                cout << "Cannot get image " << filename[i].c_str() << endl;
                getchar();
            }
            else
            {
                cout << "get image: " << filename[i].c_str() << endl;
                cv::Mat img_dst;
                cv::imshow("img", img);
                blurred(&img, &img_dst);
                
                cv::Rect rect = cv::Rect(0, 0, 30, 30);
//                cv::Mat img_fs;
//                flower_screen(&img, &rect, &img_fs);
                
                
                
//                inputImage = imread("test2.jpg");
                img_input = img.clone();
                img_clone = img.clone();
                createMosaicImage(img_input, img_mosaic, neightbourhood);

                namedWindow("showImage", 0);
                setMouseCallback("showImage", on_mouse);
                cv::waitKey();
            }
       }
       return 0;
}

//影象花屏處理
void flower_screen(const cv::Mat* input, const cv::Rect* rect, cv::Mat* output){
    
    cv::Scalar color;
    *output = input->clone();
    //將矩形區域的畫素
    for (int row = rect->y; row < rect->height; row++){
        for (int col = rect->x; col < rect->width; col++){
                //設定原影象中某點的BGR顏色值
            int tmp1 = rand();
            int tmp2 = rand();
            int tmp3 = rand();
            output->at<Vec3b>(row, col) = Vec3b(tmp1, tmp2, tmp3);
        }
    }
    
    cv::imshow("input", *output);
    cv::waitKey( 0);    
}


//影象模糊處理
void blurred(const cv::Mat* input, cv::Mat* output){
    
    cv::Mat img_tmp;
    //均值濾波
    cv::blur(*input, img_tmp, cv::Size(5,5));
    cv::imshow("blur", img_tmp);
    
    //中值濾波
    cv::Mat img_mean;
    cv::medianBlur(*input, img_mean, 5);
    cv::imshow("img_mean", img_mean);
    
    //高斯濾波
    cv::Mat img_gs;
    cv::GaussianBlur(*input, img_gs, cv::Size(5,5), 3, 3);
    cv::imshow("img_gs", img_gs);
    
    cv::waitKey( 0);
}