Как сохранить выводимое видео в файл в OpenCV

Я хочу сохранить выводимое видео в файл, а не отображать его, и попытался использовать cvcaptureimage, но все еще не смог получить результат

#include <highgui.h>

int main(int argc, char *argv[])
{
    // Create a "Capture" object from 1st command line argument
    CvCapture *video = cvCaptureFromFile(argv[1]);
    // this is the structure that will store the frames
    IplImage *frame = NULL;
    // create a window to display the video
    cvNamedWindow("Video", CV_WINDOW_AUTOSIZE);
    // get the next frame
    while (frame = cvQueryFrame(video) )
    {
        // display it in the window we created
        cvShowImage("Video", frame);
        // wait 1000/fps milliseconds
        cvWaitKey((int)(1000/cvGetCaptureProperty(video, CV_CAP_PROP_FPS)));
        //reading into .avi file
        CvCapture*capture=0  
        capture=cvcreateFileCapture(arg[1]);
      if(!capture)
        {
           // intiate the video read
            IpLImage *bgr_frame=cvQueryFrame(capture);
            double fps=cvGetCaptureProperty(capture,CV_CAP_PROP_FPS);
         } 
    }
}

могу ли я узнать ошибку, которую повторяю в своем коде?

4 ответа

Я знаю, что это довольно старый, но я не могу согласиться с этим утверждением о OSX.

Вы можете легко собрать и скомпилировать FFMPEG на OSX. Нет необходимости использовать QTKIT/Quicktime. На самом деле я пишу видео на OSX без проблем.

Другим предложением будет использование новых структур OpenCV 2.0+ вместо использования устаревших. (Используйте мат вместо IplImage/cvMat, используйте VideoWriter и VideoCapture.)

Mat image;
VideoCapture capture;
VideoWriter out;

capture = VideoCapture(-1);
image << capture;

out.write(image);

Если вам нужен код ссылки, проверьте это и это, чтобы начать.

Во всяком случае, код ниже отображает видео с веб-камеры. Если вы посмотрите поближе, вы увидите, что происходит преобразование цветной рамки в версию в оттенках серого, и в окне отображается шкала серого.

Кадр в градациях серого также записывается в файл на диске с именем out.avi. Вы должны знать, что этот код не будет работать в Mac OS X с OpenCV 2.1 просто потому, что OpenCV необходимо скомпилировать с помощью ffmpeg, чтобы разрешить присоединять видео в файл.

В Windows cvCreateVideoWriter() отобразит диалоговое окно для выбора подходящего кодека, который вы хотите использовать при сохранении видео. Можно изменить этот вызов функции, установив параметр, который будет жестко задавать кодек по вашему усмотрению.

Я написал это в спешке, но я знаю, что это работает.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include <cv.h>
#include <highgui.h>
#include <cxtypes.h>
#include <cvaux.h>

int main()
{
    int camera_index = 0;
    IplImage *color_frame = NULL;
    int exit_key_press = 0;

    CvCapture *capture = NULL;
    capture = cvCaptureFromCAM(camera_index);
    if (!capture)
    {
        printf("!!! ERROR: cvCaptureFromCAM\n");
        return -1;
    }

    double cam_w = cvGetCaptureProperty(capture, CV_CAP_PROP_FRAME_WIDTH);
    double cam_h = cvGetCaptureProperty(capture, CV_CAP_PROP_FRAME_HEIGHT);
    double fps = cvGetCaptureProperty(capture, CV_CAP_PROP_FPS);    
    printf("* Capture properties: %f x %f - %f fps\n", cam_w, cam_h, fps); 

    cvNamedWindow("Grayscale video", CV_WINDOW_AUTOSIZE);

    CvVideoWriter* writer = NULL;
    writer = cvCreateVideoWriter("out.avi", -1, fps, cvSize((int)cam_w,(int)cam_h), 1);
    if (writer == NULL)
    {
        printf("!!! ERROR: cvCreateVideoWriter\n");
        return -1;
    }

    while (exit_key_press != 'q')
    {
        color_frame = cvQueryFrame(capture);
        if (color_frame == NULL)
        {
            printf("!!! ERROR: cvQueryFrame\n");
            break;
        }

        IplImage* gray_frame = cvCreateImage(cvSize(color_frame->width, color_frame->height), color_frame->depth, 1);  
        if (gray_frame == NULL)
        {
            printf("!!! ERROR: cvCreateImage\n");
            continue;
        }

        cvCvtColor(color_frame, gray_frame, CV_BGR2GRAY);
        cvShowImage("Grayscale video", gray_frame);

        cvWriteFrame(writer, gray_frame);

        cvReleaseImage(&gray_frame);

        exit_key_press = cvWaitKey(1);
    }

    cvReleaseVideoWriter(&writer);
    cvDestroyWindow("Grayscale video");
    cvReleaseCapture(&capture);

    return 0;
}

Кажется, вы создаете видеофайл один раз для каждого кадра внутри цикла.

Создайте avi-файл один раз в начале, затем добавьте в него каждый новый кадр с помощью cvWriteFrame()

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

Другие вопросы по тегам