Подтвердить что ты не робот

Поиск контуров в OpenCV?

Когда вы извлекаете контуры с изображения, вы должны получить 2 контура за капли - один внутренний и один внешний. Рассмотрим круг ниже - так как круг - это линия с шириной пикселя, большей чем одна, вы должны иметь возможность найти два контура на изображении: один из внутренней части круга и один из внешней части.

Используя OpenCV, я хочу получить контуры INNER. Однако, когда я использую findContours(), я только получаю внешние контуры. Как получить внутренние контуры blob с помощью OpenCV?

Я использую С++ API, а не C, поэтому предлагаю только функции, которые используют С++ API. (т.е. findContours(), а не cvFindContours())

Спасибо.

enter image description here

4b9b3361

Ответ 1

Я запустил этот код на вашем изображении, и он вернул внутренний и внешний контур.

#include <iostream>
#include "opencv2/core/core.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/highgui/highgui.hpp"

int main(int argc, const char * argv[]) {

    cv::Mat image= cv::imread("../../so8449378.jpg");
    if (!image.data) {
        std::cout << "Image file not found\n";
        return 1;
    }

    //Prepare the image for findContours
    cv::cvtColor(image, image, CV_BGR2GRAY);
    cv::threshold(image, image, 128, 255, CV_THRESH_BINARY);

    //Find the contours. Use the contourOutput Mat so the original image doesn't get overwritten
    std::vector<std::vector<cv::Point> > contours;
    cv::Mat contourOutput = image.clone();
    cv::findContours( contourOutput, contours, CV_RETR_LIST, CV_CHAIN_APPROX_NONE );

    //Draw the contours
    cv::Mat contourImage(image.size(), CV_8UC3, cv::Scalar(0,0,0));
    cv::Scalar colors[3];
    colors[0] = cv::Scalar(255, 0, 0);
    colors[1] = cv::Scalar(0, 255, 0);
    colors[2] = cv::Scalar(0, 0, 255);
    for (size_t idx = 0; idx < contours.size(); idx++) {
        cv::drawContours(contourImage, contours, idx, colors[idx % 3]);
    }

    cv::imshow("Input Image", image);
    cvMoveWindow("Input Image", 0, 0);
    cv::imshow("Contours", contourImage);
    cvMoveWindow("Contours", 200, 0);
    cv::waitKey(0);

    return 0;
}

Вот контуры, которые он нашел:

findContour result image

Ответ 2

Я думаю, что Фархад просит обрезать контур из исходного изображения.

Для этого вам нужно будет найти контур, как описано выше, затем используйте маску для получения внутренней части оригинала, а затем обведите результат в изображение с тем же размером, что и контур.

Ответ 3

Функция findcontours сохраняет все контуры в разных векторах, в коде, когда все контуры рисуются, вы просто рисуете контур, соответствующий внутренней, idx - это переменная, которая определяет, какой контур рисуется.