Маскирование капли из двоичного изображения - PullRequest
4 голосов
/ 21 февраля 2012

Я делаю распознавание движения при ходьбе, используя openCV и C ++, и я хотел бы создать маску или скопированное изображение для достижения эффекта, показанного на рисунке. extracted human. Ниже приводится объяснение изображений В результате появляется капля человеческой ходьбы. Затем создается изображение маски или скопированное изображение исходного кадра, двоичный человеческий объект теперь маскируется, а немаскированные пиксели теперь устанавливаются в ноль. В результате извлекается человеческое тело с черным фоном. Диаграмма ниже показывает, как человеческая капля извлекается и затем маскируется. Это должно быть сделано для каждого 5-го кадра видеопоследовательности. Мой код до сих пор состоит из получения каждого 5-го кадра, его масштабирования в оттенках серого, нахождения областей всех больших объектов и применения порогового значения для получения двоичного изображения, где более или менее только человеческая капля является белой, а остальная часть изображения черный. Сейчас я пытаюсь извлечь человеческое тело, но понятия не имею, как поступить. Пожалуйста, помогите мне.

#include "cv.h"
#include "highgui.h"
#include "iostream"

using namespace std;
int main( int argc, char* argv ) {

CvCapture *capture = NULL;
capture = cvCaptureFromAVI("C:\\walking\\lady walking.avi");
if(!capture){
    return -1;
}

IplImage* color_frame = NULL;
IplImage* gray_frame = NULL ;

int thresh_frame = 28;
CvMoments moments;

int frameCount=0;//Counts every 5 frames
cvNamedWindow( "walking", CV_WINDOW_AUTOSIZE );

while(1) {
    color_frame = cvQueryFrame( capture );//Grabs the frame from a file
    if( !color_frame ) break;
    gray_frame = cvCreateImage(cvSize(color_frame->width, color_frame->height), color_frame->depth, 1);
    if( !color_frame ) break;// If the frame does not exist, quit the loop


    frameCount++;
    if(frameCount==5)
    {
        cvCvtColor(color_frame, gray_frame, CV_BGR2GRAY);
        cvThreshold(gray_frame, gray_frame, thresh_frame, 255, CV_THRESH_BINARY);
        cvErode(gray_frame, gray_frame, NULL, 1);
        cvDilate(gray_frame, gray_frame, NULL, 1);

        cvMoments(gray_frame, &moments, 1);
        double m00;
        m00 = cvGetCentralMoment(&moments, 0,0);

        cvShowImage("walking", gray_frame);
        frameCount=0;
    }
    char c = cvWaitKey(33);
    if( c == 27 ) break;
}

double m00 = (double)cvGetCentralMoment(&moments, 0,0);
cout << "Area - : " << m00 << endl;
//area of lady walking = 39696. Therefore, using new threshold area as 30 for this video
//area of walking man = 67929

cvReleaseImage(&color_frame);
cvReleaseImage(&gray_frame);
cvReleaseCapture( &capture );
cvDestroyWindow( "walking" );

return 0;
}

Я также хотел бы загрузить видео, которое я использую в коде, но я не знаю, как загрузить его здесь, так что если кто-то может помочь мне с этим тоже. Я хочу предоставить как можно больше информации w.r.t. мой вопрос.

1 Ответ

1 голос
/ 21 февраля 2012

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

...