From 411bd814849dace75ec755c46f668604eb6f4821 Mon Sep 17 00:00:00 2001 From: VaL Doroshchuk Date: Thu, 11 Jul 2019 17:54:10 +0200 Subject: GStreamer: Implement fetching audio/video codecs by container Moved stream types to QGstCodecsInfo and added possibility to fetch audio or video codecs by a container. Or fetch containers by audio or video codec. It would allow to debug supported codecs and containers: QGstCodecsInfo containers(QGstCodecsInfo::Muxer); QGstCodecsInfo audioCodecs(QGstCodecsInfo::AudioEncoder); for (auto &container: containers.supportedCodecs()) qDebug() << audioCodecs.supportedCodecs(containers.supportedStreamTypes(container)); Change-Id: I26bf5579db6974a166d408c4865a9ffe314e3e15 Reviewed-by: Andy Shaw --- src/gsttools/qgstcodecsinfo.cpp | 44 ++++++++++++++++++++++ src/multimedia/gsttools_headers/qgstcodecsinfo_p.h | 4 ++ .../mediacapture/qgstreameraudioencode.cpp | 12 +----- .../gstreamer/mediacapture/qgstreameraudioencode.h | 2 - .../qgstreamermediacontainercontrol.cpp | 38 +------------------ .../mediacapture/qgstreamermediacontainercontrol.h | 3 -- .../mediacapture/qgstreamervideoencode.cpp | 11 +----- .../gstreamer/mediacapture/qgstreamervideoencode.h | 1 - 8 files changed, 51 insertions(+), 64 deletions(-) diff --git a/src/gsttools/qgstcodecsinfo.cpp b/src/gsttools/qgstcodecsinfo.cpp index ca43d489b..512bb828d 100644 --- a/src/gsttools/qgstcodecsinfo.cpp +++ b/src/gsttools/qgstcodecsinfo.cpp @@ -43,9 +43,36 @@ #include +static QSet streamTypes(GstElementFactory *factory, GstPadDirection direction) +{ + QSet types; + const GList *pads = gst_element_factory_get_static_pad_templates(factory); + for (const GList *pad = pads; pad; pad = g_list_next(pad)) { + GstStaticPadTemplate *templ = reinterpret_cast(pad->data); + if (templ->direction == direction) { + GstCaps *caps = gst_static_caps_get(&templ->static_caps); + for (uint i = 0; i < gst_caps_get_size(caps); ++i) { + GstStructure *structure = gst_caps_get_structure(caps, i); + types.insert(QString::fromUtf8(gst_structure_get_name(structure))); + } + gst_caps_unref(caps); + } + } + + return types; +} + QGstCodecsInfo::QGstCodecsInfo(QGstCodecsInfo::ElementType elementType) { updateCodecs(elementType); + for (auto &codec : supportedCodecs()) { + GstElementFactory *factory = gst_element_factory_find(codecElement(codec).constData()); + if (factory) { + GstPadDirection direction = elementType == Muxer ? GST_PAD_SINK : GST_PAD_SRC; + m_streamTypes.insert(codec, streamTypes(factory, direction)); + gst_object_unref(GST_OBJECT(factory)); + } + } } QStringList QGstCodecsInfo::supportedCodecs() const @@ -245,3 +272,20 @@ GList *QGstCodecsInfo::elementFactories(ElementType elementType) const return result; #endif } + +QSet QGstCodecsInfo::supportedStreamTypes(const QString &codec) const +{ + return m_streamTypes.value(codec); +} + +QStringList QGstCodecsInfo::supportedCodecs(const QSet &types) const +{ + QStringList result; + for (auto &candidate : supportedCodecs()) { + auto candidateTypes = supportedStreamTypes(candidate); + if (candidateTypes.intersects(types)) + result << candidate; + } + + return result; +} diff --git a/src/multimedia/gsttools_headers/qgstcodecsinfo_p.h b/src/multimedia/gsttools_headers/qgstcodecsinfo_p.h index 33ab3de4b..d7aadef21 100644 --- a/src/multimedia/gsttools_headers/qgstcodecsinfo_p.h +++ b/src/multimedia/gsttools_headers/qgstcodecsinfo_p.h @@ -54,6 +54,7 @@ #include #include #include +#include #include @@ -76,6 +77,8 @@ public: QString codecDescription(const QString &codec) const; QByteArray codecElement(const QString &codec) const; QStringList codecOptions(const QString &codec) const; + QSet supportedStreamTypes(const QString &codec) const; + QStringList supportedCodecs(const QSet &types) const; private: void updateCodecs(ElementType elementType); @@ -83,6 +86,7 @@ private: QStringList m_codecs; QMap m_codecInfo; + QMap> m_streamTypes; }; Q_DECLARE_TYPEINFO(QGstCodecsInfo::CodecInfo, Q_MOVABLE_TYPE); diff --git a/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.cpp b/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.cpp index 40294214a..6a0816343 100644 --- a/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.cpp +++ b/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.cpp @@ -50,16 +50,6 @@ QGstreamerAudioEncode::QGstreamerAudioEncode(QObject *parent) :QAudioEncoderSettingsControl(parent) , m_codecs(QGstCodecsInfo::AudioEncoder) { - for (const QString& codecName : m_codecs.supportedCodecs()) { - GstElementFactory *factory = gst_element_factory_find(m_codecs.codecElement(codecName).constData()); - - if (factory) { - m_streamTypes.insert(codecName, - QGstreamerMediaContainerControl::supportedStreamTypes(factory, GST_PAD_SRC)); - - gst_object_unref(GST_OBJECT(factory)); - } - } } QGstreamerAudioEncode::~QGstreamerAudioEncode() @@ -247,5 +237,5 @@ GstElement *QGstreamerAudioEncode::createEncoder() QSet QGstreamerAudioEncode::supportedStreamTypes(const QString &codecName) const { - return m_streamTypes.value(codecName); + return m_codecs.supportedStreamTypes(codecName); } diff --git a/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.h b/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.h index 04de602ad..0cfbb4e91 100644 --- a/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.h +++ b/src/plugins/gstreamer/mediacapture/qgstreameraudioencode.h @@ -86,8 +86,6 @@ private: QMap > m_options; - QMap > m_streamTypes; - QAudioEncoderSettings m_audioSettings; }; diff --git a/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.cpp b/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.cpp index 05f1c8af5..33351476d 100644 --- a/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.cpp +++ b/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.cpp @@ -47,47 +47,11 @@ QGstreamerMediaContainerControl::QGstreamerMediaContainerControl(QObject *parent :QMediaContainerControl(parent) , m_containers(QGstCodecsInfo::Muxer) { - QSet allTypes; - - for (const QString& formatName : supportedContainers()) { - GstElementFactory *factory = gst_element_factory_find(m_containers.codecElement(formatName).constData()); - if (factory) { - if (formatName == QByteArray("raw")) { - m_streamTypes.insert(formatName, allTypes); - } else { - QSet types = supportedStreamTypes(factory, GST_PAD_SINK); - m_streamTypes.insert(formatName, types); - allTypes.unite(types); - } - - gst_object_unref(GST_OBJECT(factory)); - } - } } -QSet QGstreamerMediaContainerControl::supportedStreamTypes(GstElementFactory *factory, GstPadDirection direction) -{ - QSet types; - const GList *pads = gst_element_factory_get_static_pad_templates(factory); - for (const GList *pad = pads; pad; pad = g_list_next(pad)) { - GstStaticPadTemplate *templ = (GstStaticPadTemplate*)pad->data; - if (templ->direction == direction) { - GstCaps *caps = gst_static_caps_get(&templ->static_caps); - for (uint i=0; i QGstreamerMediaContainerControl::supportedStreamTypes(const QString &container) const { - return m_streamTypes.value(container); + return m_containers.supportedStreamTypes(container); } QString QGstreamerMediaContainerControl::containerExtension() const diff --git a/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.h b/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.h index 5c730b21d..02c7346b1 100644 --- a/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.h +++ b/src/plugins/gstreamer/mediacapture/qgstreamermediacontainercontrol.h @@ -68,14 +68,11 @@ public: QSet supportedStreamTypes(const QString &container) const; - static QSet supportedStreamTypes(GstElementFactory *factory, GstPadDirection direction); - QString containerExtension() const; private: QString m_format; QGstCodecsInfo m_containers; - QMap > m_streamTypes; }; QT_END_NAMESPACE diff --git a/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.cpp b/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.cpp index 6b4dbe4b7..62d9bbd8c 100644 --- a/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.cpp +++ b/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.cpp @@ -49,15 +49,6 @@ QGstreamerVideoEncode::QGstreamerVideoEncode(QGstreamerCaptureSession *session) :QVideoEncoderSettingsControl(session), m_session(session) , m_codecs(QGstCodecsInfo::VideoEncoder) { - for (const QString& codecName : supportedVideoCodecs()) { - GstElementFactory *factory = gst_element_factory_find(m_codecs.codecElement(codecName).constData()); - if (factory) { - m_streamTypes.insert(codecName, - QGstreamerMediaContainerControl::supportedStreamTypes(factory, GST_PAD_SRC)); - - gst_object_unref(GST_OBJECT(factory)); - } - } } QGstreamerVideoEncode::~QGstreamerVideoEncode() @@ -303,5 +294,5 @@ QPair QGstreamerVideoEncode::rateAsRational() const QSet QGstreamerVideoEncode::supportedStreamTypes(const QString &codecName) const { - return m_streamTypes.value(codecName); + return m_codecs.supportedStreamTypes(codecName); } diff --git a/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.h b/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.h index bc6636012..a35e2b456 100644 --- a/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.h +++ b/src/plugins/gstreamer/mediacapture/qgstreamervideoencode.h @@ -90,7 +90,6 @@ private: QVideoEncoderSettings m_videoSettings; QMap > m_options; - QMap > m_streamTypes; }; QT_END_NAMESPACE -- cgit v1.2.3