Juster
Juster

Reputation: 752

How to get width/height of a video stream via gstreamer?

How to get width/height of a video stream via gstreamer? I have a pipeline coded in C++ with the following structure:

rtspsrc -> rtpjitterbuffer -> rtph264depay -> mpegtsmux -> filesink

My task is: When I get a first image data (either h264 encoded or mjpeg) I need to query width and height from it. Is it possible? I tried to get current caps from 'src' pad of rtph264depay and get width/height from its structure, but failed to do the last.

Thanks!

Upvotes: 2

Views: 6432

Answers (3)

Resq
Resq

Reputation: 301

I had the same task for a RTP H264 stream. Coding in C++.

I'll give a short code snippet for future developers.

My pipe looks like this.

    auto source = gst_element_factory_make("udpsrc", nullptr);
    auto rtpJitterBuffer = gst_element_factory_make("rtpjitterbuffer", nullptr);
    auto depay = gst_element_factory_make("rtph264depay", nullptr);
    auto h264parse = gst_element_factory_make("h264parse", nullptr);
    auto decode = gst_element_factory_make("openh264dec", nullptr);
    auto sinkV = gst_element_factory_make("glimagesink", nullptr);

I used a probe pad for my decoder. Therefore you need a GstPadProbeCallback:

    GstPadProbeReturn (*GstPadProbeCallback) (GstPad *pad, GstPadProbeInfo *info,    gpointer user_data);

like

    static GstPadProbeReturn pad_cb(GstPad *pad, GstPadProbeInfo *info, gpointer user_data) {

        GstEvent *event = GST_PAD_PROBE_INFO_EVENT(info);
        if (GST_EVENT_CAPS == GST_EVENT_TYPE(event)) {
          GstCaps * caps = gst_caps_new_any();
          int width, height;
          gst_event_parse_caps(event, &caps);

          GstStructure *s = gst_caps_get_structure(caps, 0);

          gboolean res;
          res = gst_structure_get_int (s, "width", &width);
          res |= gst_structure_get_int (s, "height", &height);
          if (!res) {
              qWarning() << "no dimenions";
          }
          qDebug() << "GST_EVENT_CAPS" << width << height;
       }
       return GST_PAD_PROBE_OK;
    }

You can than add the probe to your pad like so

    auto *pad = gst_element_get_static_pad(decode, "src");

    gst_pad_add_probe(pad, GST_PAD_PROBE_TYPE_EVENT_BOTH, pad_cb, &customData_, nullptr);
    gst_object_unref(pad);

This callback will be called everytime the format changes. You don't need to check for both directions, but I did it anyways.

Upvotes: 5

thiagoss
thiagoss

Reputation: 2094

Are you using 0.10? It is old and obsolete and unmantained for years. Please move to 1.0.

That said, in 0.10 you can register a callback for the notify:caps signal in an element's pad. So you can do that in the h264depay and check if it has the width/height fields. If it does not, you can add an h264parse and that should likely find out width and height for you and you can use the notify:caps in its source pad.

In 1.0 it should work the same, but use an event probe on the pad and look for the CAPS event.

Upvotes: 0

Prabhakar Lad
Prabhakar Lad

Reputation: 1438

you can use the typefind element which is used to find the media type of a stream and get the caps from it.

Hope that helps!

Upvotes: 0

Related Questions