opencv学习笔记(二)

    科技2024-09-27  15

    1.像素读写和修改操作

    读一个GRAY像素点的像素值(CV_8UC1)

    Scalar intensity = img.at(y,x);或者Scalar intensity = img.at(Point(x,y));

    读一个多通道像素点的像素值

    Vec3f intensity = img.at(y, x);

    float blue = intensity.val[0];

    float green = intensity.val[1];

    float red = intensity.val[2];

    注意上面的vec3f 代表是三通道 float 类型,除此之外还有 vec3b等类型,按照需要对应使用

    使用 img.convertTo()可以进行float到uchar转换

    案例,读取像素实现反差操作,效果等同bitwise_not():

    #include"pch.h" #include<opencv2/opencv.hpp> #include<iostream> using namespace std; using namespace cv; int main(int argc ,char** argv) { Mat src,gray_src; src = imread("test.png"); if (!src.data) { printf("could not load the image ...\n"); return -1; } namedWindow("input_image", CV_WINDOW_AUTOSIZE); imshow("input_image", src); cvtColor(src, gray_src, CV_BGR2GRAY); namedWindow("output", CV_WINDOW_AUTOSIZE); imshow("output", gray_src); /*单通道 int height = gray_src.rows; int width = gray_src.cols; for (int row = 0; row < height;row++) { for (int col = 0; col < width; col++) { int gray = gray_src.at<uchar>(row, col); gray_src.at<uchar>(row, col) = 255 - gray; } } */ int height = src.rows; int width = src.cols; int nc = src.channels(); //for (int row = 0; row < height; row++) { // for (int col = 0; col < width; col++) { // if (nc == 1) { // int gray = src.at<uchar>(row, col); // src.at<uchar>(row, col) = 255 - gray; // } // else if (nc == 3) { // int blue = src.at<Vec3b>(row, col)[0]; // int green = src.at<Vec3b>(row, col)[1]; // int red = src.at<Vec3b>(row, col)[2]; // src.at<Vec3b>(row, col)[0]= 255 - blue; // src.at<Vec3b>(row, col)[1] = 255 - green; // src.at<Vec3b>(row, col)[2] = 255 - red; // } // } //} Mat dst; dst.create(src.size(), src.type()); bitwise_not(src,dst); namedWindow("fancha", CV_WINDOW_AUTOSIZE); imshow("fancha", dst); waitKey(0); return 0; }
    2.线性混合操作

    addweight,也就是应用这个api的使用。

    3.绘制简单图形(重要)

    绘制图形 往往和检测同时出现,比如检测出人脸之后用红色框圈出

    相关api cv::Point 和cv :: Scalar

    Point 表示2D平面上一个点x,y 例如p=Point(10,10);

    Scalar 表示四个元素的向量 Scalar(a,b,c);//分别代表BGR三个通道

    基本几何形状 基本就是记住英文名字调api

    void MyLines() { Point p1 = Point(20, 30); Point p2; p2.x = 400; p2.y = 400; Scalar color = Scalar(0, 0, 255); line(bgImage, p1, p2, color, 1, LINE_AA); } void MyRectangle() { Rect rect = Rect(200, 100, 300, 300); Scalar color = Scalar(255, 0, 0); rectangle(bgImage, rect, color, 2, LINE_8); } void MyEllipse() { Scalar color = Scalar(0, 255, 0); ellipse(bgImage, Point(bgImage.cols / 2, bgImage.rows / 2), Size(bgImage.cols / 4, bgImage.rows / 8), 90, 0, 360, color, 2, LINE_8); } void MyCircle() { Scalar color = Scalar(0, 255, 255); Point center = Point(bgImage.cols / 2, bgImage.rows / 2); circle(bgImage, center, 150, color, 2, 8); } void MyPolygon() { Point pts[1][5]; pts[0][0] = Point(100, 100); pts[0][1] = Point(100, 200); pts[0][2] = Point(200, 200); pts[0][3] = Point(200, 100); pts[0][4] = Point(100, 100); const Point* ppts[] = { pts[0] }; int npt[] = { 5 }; Scalar color = Scalar(255, 12, 255); fillPoly(bgImage, ppts, npt, 1, color, 8); }

    写文本:

    putText(bgImage, “Hello OpenCV”, Point(300, 300), CV_FONT_HERSHEY_COMPLEX, 1.0, Scalar(12, 23, 200), 3, 8)

    生成随机数:

    cv::RNG ::rng

    使用:

    void RandomLineDemo() { RNG rng(12345);//12345只是为了使每次运行时候相同 Point pt1; Point pt2; Mat bg = Mat::zeros(bgImage.size(), bgImage.type()); namedWindow("random line demo", CV_WINDOW_AUTOSIZE); for (int i = 0; i < 100000; i++) { pt1.x = rng.uniform(0, bgImage.cols);//限定范围 pt2.x = rng.uniform(0, bgImage.cols); pt1.y = rng.uniform(0, bgImage.rows); pt2.y = rng.uniform(0, bgImage.rows); Scalar color = Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)); if (waitKey(50) > 0) { break; } line(bg, pt1, pt2, color, 1, 8); imshow("random line demo", bg); } } r(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)); if (waitKey(50) > 0) { break; } line(bg, pt1, pt2, color, 1, 8); imshow("random line demo", bg); } }
    Processed: 0.009, SQL: 8