输出视频持续时间与C ++中的GStreamer不匹配

问题描述 投票:0回答:1

我正在尝试从USB摄像头录制视频,使用GStreamer进行编码和保存。每隔20秒我想停止视频,更改输出名称并重新开始捕获/编码。

我将发布我的代码的简化版本,因为它很长且无关紧要。

其他细节:timer记录经过的时间(以秒为单位)。 create_pip(j)构建以下gst管道并将j附加到文件名(如test_rgb_0.mp4,test_rgb_1.mp4等)

    "v4l2src ! video/x-raw, width=1280, height=720, framerate=30/1, format=RGB ! videoconvert ! omxh265enc bitrate=2000000 qp-range=35,51:35,51:-1,-1 vbv-size=1 iframeinterval=60 ! matroskamux ! filesink location=test_rgb.mp4 -e" 
    // declarations and stuff
    // this for is just to have 3 different video files
    for(int j=0; j<3; j++){
        // create pipeline
        pipeline = gst_parse_launch(create_pip(j).c_str(),NULL);
        gst_element_set_state(pipeline,GST_STATE_PLAYING);
        timer.reset();        // reset timer to 0
        while(timer.elapsed()<=20){
            // do some other stuff, can be ignored
        }
        // stop stream and release pipeline
        gst_element_set_state(pipeline,GST_STATE_NULL);
        gst_object_unref(pipeline);
    }

一切正常,输出视频长20秒,但vlc(或mediainfo)显示视频长0或1秒。如果我打开视频,它实际上是20秒长,所以剩余时间是负数,(-19或-20秒)。由于我创建的管道在命令行上工作正常,我认为我的程序在关闭流时无法保存一些元数据。对不起,我对Gstreamer很新,我错过了什么?

c++11 gstreamer
1个回答
0
投票

哦,我没有意识到你重新启动整个管道。您需要通过管道发送EOS而不是仅将其状态设置为NULL。

-e特定于gst-launch-1.0应用程序。它不是我认为的常规启动语法的一部分。你必须自己做。

EG

// send EOS to pipeline
gst_element_send_event(pipeline, gst_event_new_eos());

// wait for the EOS to traverse the pipeline and is reported to the bus
GstBus *bus = gst_element_get_bus(pipeline);
gst_bus_timed_pop_filtered(bus, GST_CLOCK_TIME_NONE, GST_MESSAGE_EOS);

gst_element_set_state(pipeline, GST_STATE_NULL);

[..]

虽然我不确定现场消息来源。也许您需要告诉v4l2src自己发送EOS而不是整个管道。或者只是mp4mux?至少我很确定mp4 mux在某些时候需要一个EOS来正确地完成文件。

© www.soinside.com 2019 - 2024. All rights reserved.