Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/323.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 使用Ffmpeg设置视频流元数据_Java_Android_Video_Ffmpeg_Javacv - Fatal编程技术网

Java 使用Ffmpeg设置视频流元数据

Java 使用Ffmpeg设置视频流元数据,java,android,video,ffmpeg,javacv,Java,Android,Video,Ffmpeg,Javacv,我正在使用JavaCV类将Android的相机预览帧编码到视频中 目标是复制以下命令行的结果: ffmpeg -i input.mp4 -metadata:s:v:0 rotate="90" output.mp4 我修改了startUnsafe()方法如下,但未能生成所需的输出: if ((video_st = avformat_new_stream(oc, video_codec)) != null) { video_c = video_st.codec();

我正在使用JavaCV类将Android的相机预览帧编码到视频中

目标是复制以下命令行的结果:

ffmpeg -i input.mp4 -metadata:s:v:0 rotate="90" output.mp4
我修改了
startUnsafe()
方法如下,但未能生成所需的输出:

if ((video_st = avformat_new_stream(oc, video_codec)) != null) {
        video_c = video_st.codec();
        video_c.codec_id(oformat.video_codec());
        video_c.codec_type(AVMEDIA_TYPE_VIDEO);
        ...
        AVDictionary avDictionary = new AVDictionary(null);
        av_dict_set(avDictionary, "rotate", "90", 0);
        video_st.metadata(avDictionaty);
        ...
}
...
avformat_write_header(oc, (PointerPointer) null);
这仍然正确编码视频,但添加的元数据从未出现在ffprobe上。如果有帮助,视频编码是h264

顺便说一下,这里是ffprobe的输出:

ffprobe version 2.3.3 Copyright (c) 2007-2014 the FFmpeg developers
  built on Jan 22 2015 18:22:57 with Apple LLVM version 6.0 (clang-600.0.56) (based on LLVM 3.5svn)
  configuration: --prefix=/usr/local/Cellar/ffmpeg/2.3.3 --enable-shared --enable-pthreads --enable-gpl --enable-version3 --enable-nonfree --enable-hardcoded-tables --enable-avresample --enable-vda --cc=clang --host-cflags= --host-ldflags= --enable-libx264 --enable-libfaac --enable-libmp3lame --enable-libxvid --enable-libfreetype --enable-libvorbis --enable-libvpx --enable-libass --enable-ffplay --enable-libfdk-aac --enable-libopus --enable-libquvi --enable-libx265
  libavutil      52. 92.100 / 52. 92.100
  libavcodec     55. 69.100 / 55. 69.100
  libavformat    55. 48.100 / 55. 48.100
  libavdevice    55. 13.102 / 55. 13.102
  libavfilter     4. 11.100 /  4. 11.100
  libavresample   1.  3.  0 /  1.  3.  0
  libswscale      2.  6.100 /  2.  6.100
  libswresample   0. 19.100 /  0. 19.100
  libpostproc    52.  3.100 / 52.  3.100
Input #0, mov,mp4,m4a,3gp,3g2,mj2, from 'abcd.mp4':
  Metadata:
    major_brand     : isom
    minor_version   : 512
    compatible_brands: isomiso2avc1mp41
    encoder         : Lavf56.15.102
  Duration: 00:00:19.48, start: 0.023220, bitrate: 572 kb/s
    Stream #0:0(und): Video: h264 (Constrained Baseline) (avc1 / 0x31637661), yuv420p, 1280x720, 573 kb/s, 5.71 fps, 30 tbr, 15360 tbn, 60 tbc (default)
    Metadata:
      handler_name    : VideoHandler
    Stream #0:1(und): Audio: aac (mp4a / 0x6134706D), 44100 Hz, mono, fltp, 64 kb/s (default)
    Metadata:
      handler_name    : SoundHandler

有没有关于它为什么失败的建议?谢谢。

您正在使用的
FFmpegFrameRecorder
使用
AVFormatContext
。在第2579行附近,您可以从方法签名中看到,
AVFormatContext
类使用本机代码来实现这两个功能

  • 公共本机AVDictionary元数据()
    方法
  • 公共本机AVFormatContext元数据(AVDictionary元数据)
    方法
您提供的链接的答案是,他们直接使用了
AVFormatContext
metadata
属性,这与我认为的第一种方法类似。但是
FFmpegFrameRecorder
的第649行使用了第二种方法——我怀疑。i、 e:

AVDictionary metadata = new AVDictionary(null);
... code to fill up dictionary ...
...

avformat_write_header(oc.metadata(metadata), options);
不幸的是,我现在无法尝试,但我想知道您是否可以这样做:

AVDictionary metadata = co.metadata();
... code to fill up dictionary ...

//I would assume at this point that oc has the metadata so
avformat_write_header(oc, (PointerPointer) null);
//if not then maybe
// avformat_write_header(oc.metadata(metadata), options);
签名显示它是公共的,所以我不明白为什么不能直接从
AVFormatContext
获取元数据字典。我不确定
avformat\u write\u header
方法是如何工作的,所以我建议上面两件事


注意:我以前没有使用过这个库。我曾经尝试过一些基本的编码,但没有成功。

这个问题似乎引起了很多人的兴趣,所以我添加了更多的信息。下面是JavaCV中的一些更改,以允许更轻松地访问元数据设置

设置元数据可以通过以下代码段实现:

AVDictionary metadata = new AVDictionary(null);
for (Entry<String, String> e : videoMetadata.entrySet()) {
    av_dict_set(metadata, e.getKey(), e.getValue(), 0);
}
video_st.metadata(metadata);
AVDictionary元数据=新的AVDictionary(null);
对于(条目e:videoMetadata.entrySet()){
av_dict_set(元数据,e.getKey(),e.getValue(),0);
}
视频元数据(元数据);
您可以通过执行
mvn安装-Pffmpeg
立即启用它,或者等到下一个JavacV版本(应该是0.12)才启用它

PS:正如你所看到的,这与我在问题中提出的非常相似,所以我不确定为什么它一开始就不起作用。

类似的问题: