使用gstreamer分割/分割视频流

时间:2011-01-26 20:28:00

标签: video gstreamer

有没有办法将视频分割成指定长度的片段?即60分钟的视频到12x5分钟。

5 个答案:

答案 0 :(得分:1)

Afaik,你需要开发自己的“分段器”。这类似于创建HTTP Live流文件所需的内容。可能有一个更简单的解决方案,但这就是我要做的事情:

你可以使用multifilesink next-file = buffer(或下一个文件标记,如果段不能适合内存)制作一个相对较小的程序(在python中)。

您需要对输入流进行编码或解复用,然后将流复用回来。当达到所需的持续时间时,在关键帧上剪切多路复用的流,并推送聚合的缓冲区(或标记假的关键帧,例如,强制接收器创建新文件)。重新初始化多路复用器(或附加多路复用器流头)以获取具有正确标头的文件,而不是单独播放(取决于多路复用器)。

答案 1 :(得分:1)

gnonlingnlfilesource就是为此而制作的。由于gstreamer没有特殊支持在没有转码的情况下拆分某些格式,因此您必须将视频转码为流程的一部分。

有关如何从音频文件制作剪辑的示例,请参阅How do I use gstreamer to make an audio clip from a segment of a longer source?

答案 2 :(得分:1)

在没有重新编码且没有丢失帧的情况下执行此操作的“官方”方式似乎是使用splitmuxsink元素:

例如,对于MKV文件输入:

max-size-time

{{1}}给出段长度,单位为纳秒(sic),因此上述值为5分钟。因为它会切断关键帧,实际的段长度不会精确到5分钟,但会有几秒钟的变化。

答案 3 :(得分:0)

我能够使用Perl与GStreamer和GLib绑定完成类似的事情。我的hack滥用GStreamer Pipeline状态以重置filesink的位置。我使用流式源,因此在set_state('null')之后可以接受重置为零的行为。您需要在源元素中管理搜索位置,以支持正确的分段。

my $g_pipeline = GStreamer::Pipeline->new('pipeline');
....
my $g_filesink  = GStreamer::ElementFactory->make(filesink  =>  "filesink");
$g_filesink->set(location => $file_name);
...
$g_pipeline->add(..., $g_filesink);

my $delay = 5000; # switch output file at this interval
my $timer = Glib::Timeout->add( $delay, 
  sub {
    $g_pipeline->set_state('null');
    ...
    $g_filesink->set(location=> $next_file_name);
    $g_pipeline->set_state('playing');
  }
);

答案 4 :(得分:0)

FFMPEG有一个内置的分段分离器。

检查文档中的-segment选项。

http://ffmpeg.org/ffmpeg.html#segment