Поиск самого большого объекта области из двоичной маски с использованием cv :: findContours не удался, потому что контур не замкнут. Как это предотвратить?

Я пытаюсь выполнить обнаружение темного (почти черного) объекта в видеоисточнике на основе его характеристик формы (например, площадь, длина контура и т. Д.), Но у меня есть проблема с обнаружением контуров в двоичной маске.

Иногда, даже если объект не меняет форму, а контур получается из простой маски, содержащей только один компактный большой двоичный объект, контуры не закрываются (я могу сказать это, потому что я отображаю его с опцией CV_FILLED, а для многих кадров контур заполнено), и из-за этого вычисляемая область фактически не заслуживает доверия (значение уменьшается до нескольких пикселей).

Я также заметил, что когда контур объекта не замкнут, длина примерно в 2 раза больше, чем предполагалось (что имеет смысл).

Почему контуры простых пятен иногда открываются, а иногда закрываются, и как я могу заставить их всегда быть замкнутыми? Я уже пробовал выпуклый корпус, а также копировал первую точку контура до конца, но это не сработало.

Шаги моего подхода следующие:

  1. Конвертировать изображение в оттенки серого
  2. Выполнить пороговое, эрозионное и растяжение, чтобы удалить шум и улучшить «форму»
  3. Используйте детектор краев Canny, чтобы получить только края
  4. Используйте findContours для получения контуров и их областей:
  5. Используйте arcLength для расчета длины контуров и других функций.

0

Решение

  1. Используйте детектор краев Canny, чтобы получить только края

Это классическая ошибка. После и во время шага 2 я предполагаю, что у вас есть двоичное изображение, т.е. черное изображение с кучей заполненный белые пятна, которые обозначают области, которые вы хотите найти. Это именно то, что cv::findContours работает на.

Когда вы делаете обнаружение краев, вы фактически превращаете эти хорошо заполненные области в кучу очень тонких длинных и возможно, но не обязательно замкнутые линии, ограничивающие ваши прежние области, что все портит. таким образом cv::findContours вернет именно это, куча очень тонких контуров. Эти контуры являются на самом деле тоже замкнутый, потому что они представляют собой замкнутый многоугольник с последней точкой, соединяющейся обратно с первой, просто этот многоугольник обвивает эти тонкие линии, полученные в результате обнаружения краев, что объясняет, почему их площадь очень мала, а периметр примерно вдвое больше, чем вы ожидаете. Он в основном обрабатывает те линии, которые возникают в результате обнаружения краев не как фактические контуры, а не очень тонкие районы Вы хотите найти границы контуров, что, скорее всего, не то, что вы намерены.

Если эти границы закрыты а также вы получаете только внешние контуры (например, с помощью CV_RETR_EXTERNAL), вы может быть получить примерно те же правильные контуры области, которые вы ожидаете, но это просто не гарантировано и легко испортить.

Таким образом, простое решение состоит в том, чтобы просто отбросьте шаг Canny Edge Detection и работайте над правильным двоичным изображением напрямую, как cv::findContours является обычно Предназначен для.

0

Другие решения


По вопросам рекламы [email protected]