ext/ffmpeg/: Fix encoders. Fix if encoder supports >1 caps.

Original commit message from CVS:
* ext/ffmpeg/gstffmpegcodecmap.c: (gst_ffmpeg_codecid_to_caps),
(gst_ffmpeg_codectype_to_caps), (gst_ffmpeg_caps_with_codecid):
* ext/ffmpeg/gstffmpegenc.c: (gst_ffmpegenc_base_init),
(gst_ffmpegenc_connect), (gst_ffmpegenc_register):
Fix encoders. Fix if encoder supports >1 caps.
This commit is contained in:
Ronald S. Bultje 2004-10-25 11:56:52 +00:00
parent 918b5444c9
commit 8aaf62d816
3 changed files with 55 additions and 15 deletions

View file

@ -1,3 +1,11 @@
2004-10-25 Ronald S. Bultje <rbultje@ronald.bitfreak.net>
* ext/ffmpeg/gstffmpegcodecmap.c: (gst_ffmpeg_codecid_to_caps),
(gst_ffmpeg_codectype_to_caps), (gst_ffmpeg_caps_with_codecid):
* ext/ffmpeg/gstffmpegenc.c: (gst_ffmpegenc_base_init),
(gst_ffmpegenc_connect), (gst_ffmpegenc_register):
Fix encoders. Fix if encoder supports >1 caps.
2004-10-25 Ronald S. Bultje <rbultje@ronald.bitfreak.net>
* ext/ffmpeg/gstffmpegcodecmap.c:

View file

@ -241,15 +241,10 @@ gst_ffmpeg_codecid_to_caps (enum CodecID codec_id,
break;
case CODEC_ID_MPEG4:
if (encode) {
if (encode && context != NULL) {
/* I'm not exactly sure what ffmpeg outputs... ffmpeg itself uses
* the AVI fourcc 'DIVX', but 'mp4v' for Quicktime... */
guint32 fourcc = 0;
if (context)
fourcc = context->codec_tag;
switch (fourcc) {
switch (context->codec_tag) {
case GST_MAKE_FOURCC ('D', 'I', 'V', 'X'):
caps = GST_FF_VID_CAPS_NEW ("video/x-divx",
"divxversion", G_TYPE_INT, 5, NULL);
@ -267,10 +262,15 @@ gst_ffmpeg_codecid_to_caps (enum CodecID codec_id,
caps = GST_FF_VID_CAPS_NEW ("video/mpeg",
"mpegversion", G_TYPE_INT, 4,
"systemstream", G_TYPE_BOOLEAN, FALSE, NULL);
gst_caps_append (caps, GST_FF_VID_CAPS_NEW ("video/x-divx",
"divxversion", GST_TYPE_INT_RANGE, 4, 5, NULL));
gst_caps_append (caps, GST_FF_VID_CAPS_NEW ("video/x-xvid", NULL));
gst_caps_append (caps, GST_FF_VID_CAPS_NEW ("video/x-3ivx", NULL));
if (encode) {
gst_caps_append (caps, GST_FF_VID_CAPS_NEW ("video/x-divx",
"divxversion", G_TYPE_INT, 5, NULL));
} else {
gst_caps_append (caps, GST_FF_VID_CAPS_NEW ("video/x-divx",
"divxversion", GST_TYPE_INT_RANGE, 4, 5, NULL));
gst_caps_append (caps, GST_FF_VID_CAPS_NEW ("video/x-xvid", NULL));
gst_caps_append (caps, GST_FF_VID_CAPS_NEW ("video/x-3ivx", NULL));
}
}
break;
@ -901,7 +901,8 @@ gst_ffmpeg_codectype_to_caps (enum CodecType codec_type,
switch (codec_type) {
case CODEC_TYPE_VIDEO:
if (context) {
caps = gst_ffmpeg_pixfmt_to_caps (context->pix_fmt, context);
caps = gst_ffmpeg_pixfmt_to_caps (context->pix_fmt,
context->width == -1 ? NULL : context);
} else {
GstCaps *temp;
enum PixelFormat i;
@ -1201,6 +1202,9 @@ gst_ffmpeg_caps_with_codecid (enum CodecID codec_id,
break;
}
if (!gst_caps_is_fixed (caps))
return;
/* common properties (width, height, fps) */
switch (codec_type) {
case CODEC_TYPE_VIDEO:

View file

@ -154,6 +154,7 @@ gst_ffmpegenc_base_init (GstFFMpegEncClass * klass)
GstFFMpegEncClassParams *params;
GstElementDetails details;
GstPadTemplate *srctempl, *sinktempl;
AVCodecContext *ctx;
params = g_hash_table_lookup (enc_global_plugins,
GINT_TO_POINTER (G_OBJECT_CLASS_TYPE (gobject_class)));
@ -177,6 +178,28 @@ gst_ffmpegenc_base_init (GstFFMpegEncClass * klass)
g_free (details.klass);
g_free (details.description);
/* get pix_fmt for this encoder */
if (params->in_plugin->type == CODEC_TYPE_VIDEO &&
(ctx = avcodec_alloc_context ()) != NULL) {
ctx->width = 384;
ctx->height = 288;
ctx->frame_rate_base = DEFAULT_FRAME_RATE_BASE;
ctx->frame_rate = 25 * DEFAULT_FRAME_RATE_BASE;
ctx->bit_rate = 350 * 1000;
/* makes it silent */
ctx->strict_std_compliance = -1;
if (avcodec_open (ctx, params->in_plugin) >= 0) {
gst_caps_free (params->sinkcaps);
ctx->width = -1;
params->sinkcaps =
gst_ffmpeg_codectype_to_caps (params->in_plugin->type, ctx);
}
/* FIXME: ffmpeg likes to crash on this */
//avcodec_close (ctx);
av_free (ctx);
}
/* pad templates */
sinktempl = gst_pad_template_new ("sink", GST_PAD_SINK,
GST_PAD_ALWAYS, params->sinkcaps);
@ -337,20 +360,24 @@ gst_ffmpegenc_connect (GstPad * pad, const GstCaps * caps)
return GST_PAD_LINK_REFUSED;
}
/* some codecs support more than one format, first auto-choose one */
allowed_caps = gst_pad_get_allowed_caps (ffmpegenc->srcpad);
gst_ffmpeg_caps_with_codecid (oclass->in_plugin->id,
oclass->in_plugin->type, allowed_caps, ffmpegenc->context);
/* try to set this caps on the other side */
other_caps = gst_ffmpeg_codecid_to_caps (oclass->in_plugin->id,
ffmpegenc->context, TRUE);
if (!other_caps) {
avcodec_close (ffmpegenc->context);
GST_DEBUG ("Unsupported codec - no caps found");
return GST_PAD_LINK_REFUSED;
}
allowed_caps = gst_pad_get_allowed_caps (ffmpegenc->srcpad);
icaps = gst_caps_intersect (allowed_caps, other_caps);
gst_caps_free (allowed_caps);
gst_caps_free (other_caps);
if (gst_caps_is_empty (icaps)) {
gst_caps_free (icaps);
return GST_PAD_LINK_REFUSED;
@ -361,7 +388,7 @@ gst_ffmpegenc_connect (GstPad * pad, const GstCaps * caps)
newcaps =
gst_caps_new_full (gst_structure_copy (gst_caps_get_structure (icaps,
0)), NULL);
0)), NULL);
gst_caps_free (icaps);
icaps = newcaps;
}
@ -619,6 +646,7 @@ gst_ffmpegenc_register (GstPlugin * plugin)
/* no quasi codecs, please */
if (in_plugin->id == CODEC_ID_RAWVIDEO ||
in_plugin->id == CODEC_ID_ZLIB ||
(in_plugin->id >= CODEC_ID_PCM_S16LE &&
in_plugin->id <= CODEC_ID_PCM_ALAW)) {
goto next;