When, where and how to set caps for a source plugin
Tim Müller
tim at centricular.com
Thu Feb 12 13:15:24 PST 2015
On Wed, 2015-02-11 at 13:50 +0100, Peter Maersk-Moller wrote:
Hi Peter,
> I'm writing a couple of plugins for GStreamer for reading and writing
> raw video streams to and from a video mixer. It is largely based on
> the shm plugins.
>
>
> For the source plugin initially the its source pad is defined is
> initially defined as a static pad template as written in the plugin
> documentation:
>
> static GstStaticPadTemplate srctemplate = GST_STATIC_PAD_TEMPLATE
> ("src",
> GST_PAD_SRC,
> GST_PAD_ALWAYS,
> GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE("video/x-raw ") \
> ", format=(string)BGRA"
> ", interlace-mode=(string)progressive"
> ", height = " GST_VIDEO_SIZE_RANGE
> ", width = " GST_VIDEO_SIZE_RANGE
> ", framerate= " GST_VIDEO_FPS_RANGE)
> );
>
>
> Should I use "src" or "mypluginsrc" in GST_STATIC_PAD_TEMPLATE(...)?
"src". It's the name of the pad. If there is only one src pad, it is
customarily called "src". You are free to call it whatever you want of
course, technically.
> Anyway this part works okay. Now the tricky part is that the plugin,
> when used in a pipeline will detect height, width and framerate and
> set its caps on the source pad according to this and forward the
> mandated caps settings downstream. My problem I need some help with is
> to identify when, where and how to set the caps for the source pad.
> Can you help?
>
>
> In my case the caps of the pad must be fixed, when the plugin is
> started whatever startet means. In the documentation I read that I
> should use gst_pad_use_fixed_caps() so in the init sections of the
> plugin, I have the following code:
>
> self->srcpad = gst_pad_new_from_static_template(&srctemplate,
> "src");
> gst_pad_use_fixed_caps(self->srcpad);
>
>
> I also in the init section sets the query function
>
> gst_pad_set_query_function(self->srcpad, gst_myplugin_src_query);
If I may stop you right there: is there a good reason why you are not
deriving from GstBaseSrc or GstPushSrc ?
Regards
-Tim
> However the query functions does not seems to be called when using the
> plugin. Anyway the idea is now to set the fixed caps for the pad when
> the plugin/element changes state. In the documentation is says that
> the element should allocate non-stream specific data. I read this as I
> should not set fixed caps when the element changes state from NULL to
> READY. So I try to set the caps when the element changes state from
> READY to PAUSED:
>
> gst_myplugin_src_change_state (GstElement * element, GstStateChange
> transition)
> {
> ....
> switch (transition) {
> case GST_STATE_CHANGE_NULL_TO_READY:
> break;
> case GST_STATE_CHANGE_READY_TO_PAUSED:
> caps = gst_caps_new_simple ("video/x-raw",
> "format", G_TYPE_STRING, "BGRA",
> "width", G_TYPE_INT, "1024",
> "height", G_TYPE_INT, "576",
> NULL);
> g_message(">>> SNOWMIXSRC Pads setting\n");
> if (!gst_pad_set_caps (self->srcpad, caps)) {
> GST_ELEMENT_ERROR (element, CORE, NEGOTIATION, (NULL),
> ("Failed to set caps on source"));
> }
>
>
> In the final code, the width, height and framerate depends on external
> settings in another program of course. Now when I compile and install
> the plugin and use the following pipeline to test it, it fails to set
> the caps. So obviously I am not setting the caps correctly and quite
> likely not at the right place.
>
>
> Testing plugin:
>
>
> gst-launch-1.0 -v mypluginsrc socket-path=something is-live=true !
> queue ! fakesink
>
>
> Result:
>
> Setting pipeline to PAUSED ...
> ** Message: >>> MYPLUGINSRC CHANGE STATE Null to Ready
>
> ** Message: >>> MYPLUGINSRC CHANGE STATE Ready to Pause
>
> ** Message: >>> MYPLUGINSRC Pads setting
>
> ** Message: >>> MYPLUGINSRC Pads setting error
>
> Pipeline is live and does not need PREROLL ...
> /GstPipeline:pipeline0/GstMypluginSrc:mypluginsrc0.GstPad:src: caps =
> "video/x-raw\,\ format\=\(string\)BGRA\,\ width\=\(int\)1\,\ height\=
> \(int\)1\,\ framerate\=\(fraction\)0/1\,\ interlace-mode\=\(string
> \)progressive"
> ERROR: from
> element /GstPipeline:pipeline0/GstMypluginSrc:mypluginsrc0: GStreamer
> error: negotiation problem.
> Additional debug info:
> gstmypluginsrc.c(596): gst_myplugin_src_change_state
> (): /GstPipeline:pipeline0/GstMypluginSrc:mypluginsrc0:
> Failed to set caps on source
> ERROR: pipeline doesn't want to preroll.
> Setting pipeline to PAUSED ...
> ** Message: >>> MYPLUGINSRC CHANGE STATE Other
>
> /GstPipeline:pipeline0/GstQueue:queue0.GstPad:src: caps = "video/x-raw
> \,\ format\=\(string\)BGRA\,\ width\=\(int\)1\,\ height\=\(int\)1\,\
> framerate\=\(fraction\)0/1\,\ interlace-mode\=\(string\)progressive"
> Setting pipeline to READY ...
>
>
> The extra messages is generated with g_message(..) in the state change
> code.
> sktop.org/mailman/listinfo/gstreamer-devel
--
Tim Müller, Centricular Ltd - http://www.centricular.com
More information about the gstreamer-devel
mailing list