2

フラッドフィル関数のドキュメントに記載されている浮動範囲と固定範囲の意味は何ですか??

以下に示すグレースケール画像にフラッドフィル機能を使用しました。イメージには、強度が異なる 3 つの領域があります。

入力画像

  1. 外側の長方形 = 170
  2. 内側の楕円 = 175
  3. 内側の長方形 = 180

170 と 175 の領域を単一の接続されたコンポーネントとして一緒に塗りつぶし、180 の領域を別のコンポーネントとして塗りつぶしたいと考えています。

ここからコードを変更し、 次のように機能します。

  #include <iostream>
#include <vector>

#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>

void FindBlobs(const cv::Mat &binary, std::vector < std::vector<cv::Point2i> > &blobs);

int main(int argc, char **argv)
{
    cv::Mat img = cv::imread("blob.png", 0); // force greyscale

    if(!img.data) {
        std::cout << "File not found" << std::endl;
        return -1;
    }

    cv::namedWindow("binary");
    cv::namedWindow("labelled");

    cv::Mat output = cv::Mat::zeros(img.size(), CV_8UC3);

    cv::Mat binary=img.clone();
    std::vector < std::vector<cv::Point2i > > blobs;
        
    FindBlobs(binary, blobs);

    // Randomy color the blobs
    for(size_t i=0; i < blobs.size(); i++) {
        unsigned char r = 255 * (rand()/(1.0 + RAND_MAX));
        unsigned char g = 255 * (rand()/(1.0 + RAND_MAX));
        unsigned char b = 255 * (rand()/(1.0 + RAND_MAX));

        for(size_t j=0; j < blobs[i].size(); j++) {
            int x = blobs[i][j].x;
            int y = blobs[i][j].y;

            output.at<cv::Vec3b>(y,x)[0] = b;
            output.at<cv::Vec3b>(y,x)[1] = g;
            output.at<cv::Vec3b>(y,x)[2] = r;
        }
    }

    cv::imshow("binary", img);
    cv::imshow("labelled", output);
    cv::waitKey(0);

    return 0;
}

void FindBlobs(const cv::Mat &binary, std::vector < std::vector<cv::Point2i> > &blobs)
{
    blobs.clear();

    cv::Mat label_image;
    binary.convertTo(label_image, CV_32FC1); 

    int label_count = 2; 

    for(int y=0; y < binary.rows; y++) {
    {
     for(int x=0; x < binary.cols; x++) {
         {   if((int)label_image.at<float>(y,x) < 150) {  //start labelling only when pixel > 150
             {
         continue;
             }

            cv::Rect rect;
            cv::floodFill(label_image, cv::Point(x,y), cv::Scalar(label_count), &rect, cv::Scalar(0), cv::Scalar(6), 4+CV_FLOODFILL_FIXED_RANGE);

            std::vector <cv::Point2i> blob;

            for(int i=rect.y; i < (rect.y+rect.height); i++) {
            {   for(int j=rect.x; j < (rect.x+rect.width); j++) {
                {   if((int)label_image.at<float>(i,j) != label_count) {
                    {    continue;
                    }

                    blob.push_back(cv::Point2i(j,i));
                }
            }

            blobs.push_back(blob);

            label_count++;
        }
    }
}

フラグ CV_FLOODFILL_FIXED_RANGE を使用して固定範囲を使用しました(使用した方法は正しいですか?? )

loDiff=0 と upDiff=6を指定します。

シードが 170 になると、範囲 170-0 から 170+6、つまり170 から 176 (外側の長方形と内側の楕円) のすべてのポイントが同じラベルで塗りつぶされ、内側の長方形が 180 であるため、異なるラベルを持つと予想しました

ただし、次のような出力が得られます:-

ここに画像の説明を入力

外側の長方形と内側の楕円には同じラベルがありません。何が間違いでしょうか?

予想される o/p : 内側の楕円もオレンジ色になります (外側の長方形と同じ)

4

0 に答える 0