summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--docs/gst/gstreamer-sections.txt28
-rw-r--r--gst/gstelementfactory.c196
-rw-r--r--gst/gstelementfactory.h132
-rw-r--r--gst/gstpluginfeature.c53
-rw-r--r--gst/gstpluginfeature.h9
5 files changed, 418 insertions, 0 deletions
diff --git a/docs/gst/gstreamer-sections.txt b/docs/gst/gstreamer-sections.txt
index 361ed23a0a..fd8198237f 100644
--- a/docs/gst/gstreamer-sections.txt
+++ b/docs/gst/gstreamer-sections.txt
@@ -648,6 +648,32 @@ gst_element_factory_make
gst_element_factory_can_sink_caps
gst_element_factory_can_src_caps
gst_element_factory_get_static_pad_templates
+GstElementFactoryListType
+GST_ELEMENT_FACTORY_TYPE_ANY
+GST_ELEMENT_FACTORY_TYPE_AUDIOVIDEO_SINKS
+GST_ELEMENT_FACTORY_TYPE_AUDIO_ENCODER
+GST_ELEMENT_FACTORY_TYPE_DECODABLE
+GST_ELEMENT_FACTORY_TYPE_DECODER
+GST_ELEMENT_FACTORY_TYPE_DEMUXER
+GST_ELEMENT_FACTORY_TYPE_DEPAYLOADER
+GST_ELEMENT_FACTORY_TYPE_ENCODER
+GST_ELEMENT_FACTORY_TYPE_FORMATTER
+GST_ELEMENT_FACTORY_TYPE_MAX_ELEMENTS
+GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO
+GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE
+GST_ELEMENT_FACTORY_TYPE_MEDIA_METADATA
+GST_ELEMENT_FACTORY_TYPE_MEDIA_SUBTITLE
+GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO
+GST_ELEMENT_FACTORY_TYPE_MEDIA_ANY
+GST_ELEMENT_FACTORY_TYPE_MUXER
+GST_ELEMENT_FACTORY_TYPE_PARSER
+GST_ELEMENT_FACTORY_TYPE_PAYLOADER
+GST_ELEMENT_FACTORY_TYPE_SINK
+GST_ELEMENT_FACTORY_TYPE_SRC
+GST_ELEMENT_FACTORY_TYPE_VIDEO_ENCODER
+gst_element_factory_list_filter
+gst_element_factory_list_get_elements
+gst_element_factory_list_is_type
<SUBSECTION Standard>
GstElementFactoryClass
GST_ELEMENT_FACTORY
@@ -1814,7 +1840,9 @@ gst_plugin_feature_get_name
gst_plugin_feature_load
gst_plugin_feature_list_copy
gst_plugin_feature_list_free
+gst_plugin_feature_list_debug
gst_plugin_feature_check_version
+gst_plugin_feature_rank_compare_func
<SUBSECTION Standard>
GstPluginFeatureClass
GST_PLUGIN_FEATURE
diff --git a/gst/gstelementfactory.c b/gst/gstelementfactory.c
index 713c42b4f6..d19d5841a7 100644
--- a/gst/gstelementfactory.c
+++ b/gst/gstelementfactory.c
@@ -669,3 +669,199 @@ gst_element_factory_has_interface (GstElementFactory * factory,
}
return FALSE;
}
+
+
+typedef struct
+{
+ GstElementFactoryListType type;
+ GstRank minrank;
+} FilterData;
+
+
+/**
+ * gst_element_factory_list_is_type:
+ * @factory: a #GstElementFactory
+ * @type: a #GstElementFactoryListType
+ *
+ * Check if @factory if of the given types.
+ *
+ * Returns: %TRUE if @factory is of @type.
+ *
+ * Since: 0.10.31
+ */
+gboolean
+gst_element_factory_list_is_type (GstElementFactory * factory,
+ GstElementFactoryListType type)
+{
+ gboolean res = FALSE;
+ const gchar *klass;
+
+ klass = gst_element_factory_get_klass (factory);
+
+ /* Filter by element type first, as soon as it matches
+ * one type, we skip all other tests */
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_SINK))
+ res = (strstr (klass, "Sink") != NULL);
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_SRC))
+ res = (strstr (klass, "Source") != NULL);
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_DECODER))
+ res = (strstr (klass, "Decoder") != NULL);
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_ENCODER))
+ res = (strstr (klass, "Encoder") != NULL);
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_MUXER))
+ res = (strstr (klass, "Muxer") != NULL);
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_DEMUXER))
+ res = (strstr (klass, "Demux") != NULL);
+
+ /* FIXME : We're actually parsing two Classes here... */
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_PARSER))
+ res = ((strstr (klass, "Parser") != NULL)
+ && (strstr (klass, "Codec") != NULL));
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_DEPAYLOADER))
+ res = (strstr (klass, "Depayloader") != NULL);
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_PAYLOADER))
+ res = (strstr (klass, "Payloader") != NULL);
+
+ if (!res && (type & GST_ELEMENT_FACTORY_TYPE_FORMATTER))
+ res = (strstr (klass, "Formatter") != NULL);
+
+ /* Filter by media type now, we only test if it
+ * matched any of the types above. */
+ if (res
+ && (type & (GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO |
+ GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
+ GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE)))
+ res = ((type & GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO)
+ && (strstr (klass, "Audio") != NULL))
+ || ((type & GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO)
+ && (strstr (klass, "Video") != NULL))
+ || ((type & GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE)
+ && (strstr (klass, "Image") != NULL));
+
+ return res;
+}
+
+static gboolean
+element_filter (GstPluginFeature * feature, FilterData * data)
+{
+ gboolean res;
+
+ /* we only care about element factories */
+ if (G_UNLIKELY (!GST_IS_ELEMENT_FACTORY (feature)))
+ return FALSE;
+
+ res = (gst_plugin_feature_get_rank (feature) >= data->minrank) &&
+ gst_element_factory_list_is_type (GST_ELEMENT_FACTORY_CAST (feature),
+ data->type);
+
+ return res;
+}
+
+/**
+ * gst_element_factory_list_get_elements:
+ * @type: a #GstElementFactoryListType
+ * @minrank: Minimum rank
+ *
+ * Get a list of factories that match the given @type. Only elements
+ * with a rank greater or equal to @minrank will be returned.
+ * The list of factories is returned by decreasing rank.
+ *
+ * Returns: a #GList of #GstElementFactory elements. Use
+ * gst_plugin_feature_list_free() after usage.
+ *
+ * Since: 0.10.31
+ */
+GList *
+gst_element_factory_list_get_elements (GstElementFactoryListType type,
+ GstRank minrank)
+{
+ GList *result;
+ FilterData data;
+
+ /* prepare type */
+ data.type = type;
+ data.minrank = minrank;
+
+ /* get the feature list using the filter */
+ result = gst_default_registry_feature_filter ((GstPluginFeatureFilter)
+ element_filter, FALSE, &data);
+
+ /* sort on rank and name */
+ result = g_list_sort (result, gst_plugin_feature_rank_compare_func);
+
+ return result;
+}
+
+/**
+ * gst_element_factory_list_filter:
+ * @list: a #GList of #GstElementFactory to filter
+ * @caps: a #GstCaps
+ * @direction: a #GstPadDirection to filter on
+ * @subsetonly: whether to filter on caps subsets or not.
+ *
+ * Filter out all the elementfactories in @list that can handle @caps in
+ * the given direction.
+ *
+ * If @subsetonly is %TRUE, then only the elements whose pads templates
+ * are a complete superset of @caps will be returned. Else any element
+ * whose pad templates caps can intersect with @caps will be returned.
+ *
+ * Returns: a #GList of #GstElementFactory elements that match the
+ * given requisits. Use #gst_plugin_feature_list_free after usage.
+ *
+ * Since: 0.10.31
+ */
+GList *
+gst_element_factory_list_filter (GList * list,
+ const GstCaps * caps, GstPadDirection direction, gboolean subsetonly)
+{
+ GList *result = NULL;
+
+ GST_DEBUG ("finding factories");
+
+ /* loop over all the factories */
+ for (; list; list = list->next) {
+ GstElementFactory *factory;
+ const GList *templates;
+ GList *walk;
+
+ factory = (GstElementFactory *) list->data;
+
+ GST_DEBUG ("Trying %s",
+ gst_plugin_feature_get_name ((GstPluginFeature *) factory));
+
+ /* get the templates from the element factory */
+ templates = gst_element_factory_get_static_pad_templates (factory);
+ for (walk = (GList *) templates; walk; walk = g_list_next (walk)) {
+ GstStaticPadTemplate *templ = walk->data;
+
+ /* we only care about the sink templates */
+ if (templ->direction == direction) {
+ GstCaps *tmpl_caps;
+
+ /* try to intersect the caps with the caps of the template */
+ tmpl_caps = gst_static_caps_get (&templ->static_caps);
+
+ /* FIXME, intersect is not the right method, we ideally want to check
+ * for a subset here */
+
+ /* check if the intersection is empty */
+ if ((subsetonly && gst_caps_is_subset (caps, tmpl_caps)) ||
+ (!subsetonly && gst_caps_can_intersect (caps, tmpl_caps))) {
+ /* non empty intersection, we can use this element */
+ result = g_list_prepend (result, gst_object_ref (factory));
+ break;
+ }
+ gst_caps_unref (tmpl_caps);
+ }
+ }
+ }
+ return g_list_reverse (result);
+}
diff --git a/gst/gstelementfactory.h b/gst/gstelementfactory.h
index 39772b001d..1a71d73046 100644
--- a/gst/gstelementfactory.h
+++ b/gst/gstelementfactory.h
@@ -165,8 +165,140 @@ void __gst_element_factory_add_interface (GstElementFacto
gboolean gst_element_register (GstPlugin *plugin, const gchar *name,
guint rank, GType type);
+/* Factory list functions */
+
+/**
+ * GstFactoryListType:
+ * @GST_ELEMENT_FACTORY_TYPE_DECODER: Decoder elements
+ * @GST_ELEMENT_FACTORY_TYPE_ENCODER: Encoder elements
+ * @GST_ELEMENT_FACTORY_TYPE_SINK: Sink elements
+ * @GST_ELEMENT_FACTORY_TYPE_SRC: Source elements
+ * @GST_ELEMENT_FACTORY_TYPE_MUXER: Muxer elements
+ * @GST_ELEMENT_FACTORY_TYPE_DEMUXER: Demuxer elements
+ * @GST_ELEMENT_FACTORY_TYPE_PARSER: Parser elements
+ * @GST_ELEMENT_FACTORY_TYPE_PAYLOADER: Payloader elements
+ * @GST_ELEMENT_FACTORY_TYPE_DEPAYLOADER: Depayloader elements
+ * @GST_ELEMENT_FACTORY_TYPE_MAX_ELEMENTS: Private, do not use
+ * @GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO: Elements handling video media types
+ * @GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO: Elements handling audio media types
+ * @GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE: Elements handling image media types
+ * @GST_ELEMENT_FACTORY_TYPE_MEDIA_SUBTITLE: Elements handling subtitle media types
+ * @GST_ELEMENT_FACTORY_TYPE_MEDIA_METADATA: Elements handling metadata media types
+ *
+ * The type of #GstElementFactory to filter.
+ *
+ * All @GstFactoryListType up to @GST_ELEMENT_FACTORY_TYPE_MAX_ELEMENTS are exclusive.
+ *
+ * If one or more of the MEDIA types are specified, then only elements
+ * matching the specified media types will be selected.
+ *
+ * Since: 0.10.31
+ */
+
+typedef guint64 GstElementFactoryListType;
+
+#define GST_ELEMENT_FACTORY_TYPE_DECODER (G_GUINT64_CONSTANT (1) << 0)
+#define GST_ELEMENT_FACTORY_TYPE_ENCODER (G_GUINT64_CONSTANT (1) << 1)
+#define GST_ELEMENT_FACTORY_TYPE_SINK (G_GUINT64_CONSTANT (1) << 2)
+#define GST_ELEMENT_FACTORY_TYPE_SRC (G_GUINT64_CONSTANT (1) << 3)
+#define GST_ELEMENT_FACTORY_TYPE_MUXER (G_GUINT64_CONSTANT (1) << 4)
+#define GST_ELEMENT_FACTORY_TYPE_DEMUXER (G_GUINT64_CONSTANT (1) << 5)
+#define GST_ELEMENT_FACTORY_TYPE_PARSER (G_GUINT64_CONSTANT (1) << 6)
+#define GST_ELEMENT_FACTORY_TYPE_PAYLOADER (G_GUINT64_CONSTANT (1) << 7)
+#define GST_ELEMENT_FACTORY_TYPE_DEPAYLOADER (G_GUINT64_CONSTANT (1) << 8)
+#define GST_ELEMENT_FACTORY_TYPE_FORMATTER (G_GUINT64_CONSTANT (1) << 9)
+
+#define GST_ELEMENT_FACTORY_TYPE_MAX_ELEMENTS (G_GUINT64_CONSTANT (1) << 48)
+
+#define GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO (G_GUINT64_CONSTANT (1) << 49)
+#define GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO (G_GUINT64_CONSTANT (1) << 50)
+#define GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE (G_GUINT64_CONSTANT (1) << 51)
+#define GST_ELEMENT_FACTORY_TYPE_MEDIA_SUBTITLE (G_GUINT64_CONSTANT (1) << 52)
+#define GST_ELEMENT_FACTORY_TYPE_MEDIA_METADATA (G_GUINT64_CONSTANT (1) << 53)
+
+/**
+ * GST_ELEMENT_FACTORY_TYPE_ANY:
+ * Elements of any of the defined GST_ELEMENT_FACTORY_LIST types
+ *
+ * Since: 0.10.31
+ */
+#define GST_ELEMENT_FACTORY_TYPE_ANY G_GUINT64_CONSTANT ((1 << 49) - 1)
+
+/**
+ * GST_ELEMENT_FACTORY_TYPE_MEDIA_ANY:
+ * Elements matching any of the defined GST_ELEMENT_FACTORY_TYPE_MEDIA types
+ *
+ * Note: Do not use this if you wish to not filter against any of the defined
+ * media types. If you wish to do this, simply don't specify any
+ * GST_ELEMENT_FACTORY_TYPE_MEDIA flag.
+ *
+ * Since: 0.10.31
+ */
+#define GST_ELEMENT_FACTORY_TYPE_MEDIA_ANY (~G_GUINT64_CONSTANT (0) << 48)
+
+/**
+ * GST_ELEMENT_FACTORY_TYPE_VIDEO_ENCODER:
+ * All encoders handling video or image media types
+ *
+ * Since: 0.10.31
+ */
+#define GST_ELEMENT_FACTORY_TYPE_VIDEO_ENCODER (GST_ELEMENT_FACTORY_TYPE_ENCODER | GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO | GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE)
+
+/**
+ * GST_ELEMENT_FACTORY_TYPE_AUDIO_ENCODER:
+ * All encoders handling audio media types
+ *
+ * Since: 0.10.31
+ */
+#define GST_ELEMENT_FACTORY_TYPE_AUDIO_ENCODER (GST_ELEMENT_FACTORY_TYPE_ENCODER | GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO)
+
+/**
+ * GST_ELEMENT_FACTORY_TYPE_AUDIOVIDEO_SINKS:
+ *
+ * All sinks handling audio, video or image media types
+ *
+ * Since: 0.10.31
+ */
+#define GST_ELEMENT_FACTORY_TYPE_AUDIOVIDEO_SINKS (GST_ELEMENT_FACTORY_TYPE_SINK | GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO | GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO | GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE)
+
+/**
+ * GST_ELEMENT_FACTORY_TYPE_DECODABLE:
+ *
+ * All elements used to 'decode' streams (decoders, demuxers, parsers, depayloaders)
+ *
+ * Since: 0.10.31
+ */
+#define GST_ELEMENT_FACTORY_TYPE_DECODABLE \
+ (GST_ELEMENT_FACTORY_TYPE_DECODER | GST_ELEMENT_FACTORY_TYPE_DEMUXER | GST_ELEMENT_FACTORY_TYPE_DEPAYLOADER | GST_ELEMENT_FACTORY_TYPE_PARSER)
+
+/* Element klass defines */
+#define GST_ELEMENT_FACTORY_KLASS_DECODER "Decoder"
+#define GST_ELEMENT_FACTORY_KLASS_ENCODER "Encoder"
+#define GST_ELEMENT_FACTORY_KLASS_SINK "Sink"
+#define GST_ELEMENT_FACTORY_KLASS_SRC "Source"
+#define GST_ELEMENT_FACTORY_KLASS_MUXER "Muxer"
+#define GST_ELEMENT_FACTORY_KLASS_DEMUXER "Demuxer"
+#define GST_ELEMENT_FACTORY_KLASS_PARSER "Parser"
+#define GST_ELEMENT_FACTORY_KLASS_PAYLOADER "Payloader"
+#define GST_ELEMENT_FACTORY_KLASS_DEPAYLOADER "Depayloader"
+#define GST_ELEMENT_FACTORY_KLASS_FORMATTER "Formatter"
+
+#define GST_ELEMENT_FACTORY_KLASS_MEDIA_VIDEO "Video"
+#define GST_ELEMENT_FACTORY_KLASS_MEDIA_AUDIO "Audio"
+#define GST_ELEMENT_FACTORY_KLASS_MEDIA_IMAGE "Image"
+#define GST_ELEMENT_FACTORY_KLASS_MEDIA_SUBTITLE "Subtitle"
+#define GST_ELEMENT_FACTORY_KLASS_MEDIA_METADATA "Metadata"
+
+gboolean gst_element_factory_list_is_type (GstElementFactory *factory,
+ GstElementFactoryListType type);
+
+GList * gst_element_factory_list_get_elements (GstElementFactoryListType type,
+ GstRank minrank);
+GList * gst_element_factory_list_filter (GList *list, const GstCaps *caps,
+ GstPadDirection direction,
+ gboolean subsetonly);
G_END_DECLS
#endif /* __GST_ELEMENT_FACTORY_H__ */
diff --git a/gst/gstpluginfeature.c b/gst/gstpluginfeature.c
index 0ca7ab5a34..51961e5d32 100644
--- a/gst/gstpluginfeature.c
+++ b/gst/gstpluginfeature.c
@@ -296,6 +296,26 @@ gst_plugin_feature_list_copy (GList * list)
}
/**
+ * gst_plugin_feature_list_debug:
+ * @list: a #GList of plugin features
+ *
+ * Debug the plugin feature names in @list.
+ *
+ * Since: 0.10.31
+ */
+void
+gst_plugin_feature_list_debug (GList * list)
+{
+#ifndef GST_DISABLE_GST_DEBUG
+ while (list) {
+ GST_DEBUG ("%s",
+ gst_plugin_feature_get_name ((GstPluginFeature *) list->data));
+ list = list->next;
+ }
+#endif
+}
+
+/**
* gst_plugin_feature_check_version:
* @feature: a feature
* @min_major: minimum required major version
@@ -368,3 +388,36 @@ gst_plugin_feature_check_version (GstPluginFeature * feature,
return ret;
}
+
+/**
+ * gst_plugin_feature_rank_compare_func:
+ * @p1: a #GstPluginFeature
+ * @p2: a #GstPluginFeature
+ *
+ * Compares the two given #GstPluginFeature instances. This function can be
+ * used as a #GCompareFunc when sorting by rank and then by name.
+ *
+ * Returns: negative value if the rank of p1 > the rank of p2 or the ranks are
+ * equal but the name of p1 comes before the name of p2; zero if the rank
+ * and names are equal; positive value if the rank of p1 < the rank of p2 or the
+ * ranks are equal but the name of p2 comes after the name of p1
+ *
+ * Since: 0.10.31
+ */
+gint
+gst_plugin_feature_rank_compare_func (gconstpointer p1, gconstpointer p2)
+{
+ GstPluginFeature *f1, *f2;
+ gint diff;
+
+ f1 = (GstPluginFeature *) p1;
+ f2 = (GstPluginFeature *) p2;
+
+ diff = f2->rank - f1->rank;
+ if (diff != 0)
+ return diff;
+
+ diff = strcmp (f2->name, f1->name);
+
+ return diff;
+}
diff --git a/gst/gstpluginfeature.h b/gst/gstpluginfeature.h
index ee1a6cef49..ee615d9537 100644
--- a/gst/gstpluginfeature.h
+++ b/gst/gstpluginfeature.h
@@ -138,11 +138,20 @@ G_CONST_RETURN gchar *gst_plugin_feature_get_name (GstPluginFeature *featu
void gst_plugin_feature_list_free (GList *list);
GList *gst_plugin_feature_list_copy (GList *list);
+void gst_plugin_feature_list_debug (GList *list);
+
+#ifndef GST_DISABLE_GST_DEBUG
+#define GST_PLUGIN_FEATURE_LIST_DEBUG(list) gst_plugin_feature_list_debug(list)
+#else
+#define GST_PLUGIN_FEATURE_LIST_DEBUG(list)
+#endif
gboolean gst_plugin_feature_check_version (GstPluginFeature *feature,
guint min_major,
guint min_minor,
guint min_micro);
+gint gst_plugin_feature_rank_compare_func (gconstpointer p1,
+ gconstpointer p2);
G_END_DECLS