Найти цвет пикселя из cv::Mat в определенной позиции

хорошо, моя проблема в том, что мне нужно найти субматрицу изображения cv::Mat, которая включает все белые пиксели. Поэтому я хочу перебрать все пиксели, проверить, являются ли они белыми, и создать cv::Rect с этой информацией.
Я понял, как перебрать все пиксели, но не знаю, как получить цвет пикселей. вне этого. Cv::Mat ранее был преобразован в оттенки серого с помощью CV_GRAY2BGR

for(int y = 0; y < outputFrame.rows; y++)
{
    for(int x = 0; x < outputFrame.cols; x++)
    {
        // I don't know which datatype I should use
        if (outputFrame.at<INSERT_DATATYPE_HERE>(x,y) == 255)
           //define area
    }
}

Мой последний вопрос: какой тип данных я должен вставить в код в позицию INSERT_DATATYPE_HERE и является ли 255 правильным значением для сравнения?

Большое спасибо


person Seega    schedule 29.08.2012    source источник
comment
возможный дубликат Переход через пиксели с помощью opencv   -  person Sam    schedule 29.08.2012


Ответы (1)


Это зависит от каналов вашего изображения. Mat имеет метод channels. Возвращает количество каналов — один, если изображение серое, три, если изображение цветное (например, RGB — один канал для каждой цветовой составляющей).

Итак, вы должны сделать что-то вроде этого:

if (outputFrame.channels() == 1) //image is grayscale - so you can use uchar (1 byte) for each pixel
{
    //...
    if (outputFrame.at<uchar>(x,y) == 255)
    {
        //do a check if this pixel is the most left, or the most right, or the most top, or the most bottom (this is needed to construct result rectangle)
    }
}
else
if (outputFrame.channels() == 3) //image is color, so type of each pixel if Vec3b
{
    //...
    // white color is when all values (R, G and B) are 255
    if (outputFrame.at<Vec3b>(x,y)[0] == 255 && outputFrame.at<Vec3b>(x,y)[1] == 255 && outputFrame.at<Vec3b>(x,y)[2] == 255)
    {
        //do a check if this pixel is the most left, or the most right, or the most top, or the most bottom (this is needed to construct result rectangle)
    }
}

Но на самом деле, чтобы получить прямоугольник, содержащий все белые пиксели на изображении, вы можете использовать другой метод:

  1. Преобразование изображения в оттенки серого.
  2. Сделайте threshold со значением 254 (или около 255) в качестве параметра .
  3. Найти все контуры на изображении.
  4. Постройте один контур, содержащий все эти контуры (просто добавив все точки каждого контура в один большой контур).
  5. Используйте функцию ограничивающего прямоугольника, чтобы найти нужный вам прямоугольник.
person ArtemStorozhuk    schedule 29.08.2012
comment
канал == 1, кажется, работает, к сожалению, if (outputFrame.at<uchar>(y,x) == 255) всегда верно, у вас есть идея решить эту проблему? - person Seega; 29.08.2012
comment
У вас есть белое изображение, чем. Разместите это. А также почему (y,x) не (x,y)? - person ArtemStorozhuk; 29.08.2012
comment
работало, я тупой, первый кадр всегда был белым, но поскольку обработка каждого пикселя была очень медленной, я никогда не ждал, пока обработается первый кадр. Большое спасибо! Я также попробую обнаружение контура. Спасибо еще раз - person Seega; 30.08.2012