2

I have searched internet and stackoverflow thoroughly, but I didn't find what exactly I'm looking for!

How can I get RGB (BGR actually) values of a certain image (all pixels of the image) in OpenCV? I'm using C++, the image is stored in cv::Mat variable.

I'm showing some of my efforts so far: I tried this code from another stackoverflow link. But every time I re-run the code the value in Hexadecimal changed! For example once its 00CD5D7C, in next run it is 00C09D7C.

cv::Mat img_rgb = cv::imread("img6.jpg");
Point3_<uchar>* p = img_rgb.ptr<Point3_<uchar> >(10,10);
p->x; //B
p->y; //G
p->z; //R
std::cout<<p;

In another try I used this code from another answer. Here output is always -858993460.

img_rgb.at<cv::Vec3b>(10,10);
img_rgb.at<cv::Vec3b>(10,10)[0] = newval[0];
img_rgb.at<cv::Vec3b>(10,10)[1] = newval[1];
img_rgb.at<cv::Vec3b>(10,10)[2] = newval[2];

cout<<newval[0]; //For cout<<newval[1]; cout<<newval[2]; the result is still same

NOTE: I used (10,10) as a test to get the RGB, my target is get the RGB values if the whole image!

Tousif Zaman
  • 57
  • 4
  • 14
  • It seems that you're not even trying to understand what you're doing. Use `std::cout << img_rgb.at(10,10);` – Miki Jan 12 '17 at 14:00
  • @Miki Didn't realize I'm this much stupid! Thanks for the answer :) It works really fine. – Tousif Zaman Jan 12 '17 at 14:13
  • 2
    Possible duplicate of [Accessing certain pixel RGB value in openCV](http://stackoverflow.com/questions/8932893/accessing-certain-pixel-rgb-value-in-opencv) – TylerH Jan 13 '17 at 16:29
  • @TylerH that solution didn't work out for me, neither the explanations! – Tousif Zaman Jan 21 '17 at 05:05

1 Answers1

1

Since you are loading a color image (of type CV_8UC3), you need to access its elements with .at<Vec3b>(row, col). The elements are in BGR order:

Mat img_bgr = imread("path_to_img");

for(int r = 0; r < img_bgr.rows; ++r) {
    for(int c = 0; c < img_bgr.cols; ++c) {
        std::cout << "Pixel at position (x, y) : (" << c << ", " << r << ") =" <<
             img_bgr.at<Vec3b>(r,c) << std::endl;
    }
}

You can also simplify using Mat3b (aka Mat_<Vec3b>), so you don't need to use the .at function, but using directly the parenthesis:

Mat3b img_bgr = imread("path_to_img");

for(int r = 0; r < img_bgr.rows; ++r) {
    for(int c = 0; c < img_bgr.cols; ++c) {
        std::cout << "Pixel at position (x, y) : (" << c << ", " << r << ") =" <<
             img_bgr(r,c) << std::endl;
    }
}

To get each single channel, you can easily do:

 Vec3b pixel = img_bgr(r,c); // or img_bgr.at<Vec3b>(r,c)
 uchar blue = pixel[0];
 uchar green = pixel[1];
 uchar red = pixel[2];
Miki
  • 40,887
  • 13
  • 123
  • 202
  • Nice explanation Sir, thanks a lot! And I found your email address, I think I'm gonna bother you more in near future as a newbie in Computer Vision. – Tousif Zaman Jan 12 '17 at 14:21
  • 1
    @TousifZaman Please consider posting future questions on StackOverflow rather than in an e-mail so that the community can benefit from the responses as well. – merlinND Jan 12 '17 at 14:33
  • @merlinND Sure, my questions will always come here. I'll knock him about some techniques and tips and suggestions in this field. StackOverflow is not a place for those I think. – Tousif Zaman Jan 12 '17 at 14:35
  • @Miki LOL no problem, and I already posted a new question! Please take a look :) http://stackoverflow.com/questions/41807386/setting-rgb-values-of-pixels-in-a-certain-image-in-opencv – Tousif Zaman Jan 23 '17 at 13:21