mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-23 18:21:04 +00:00
gstcaps: new API : gst_caps_intersect_full
Just like gst_caps_intersect, but adds a new parameter 'mode' that allows selecting the intersection algorithm to use. Currently we have GST_CAPS_INTERSECT_MODE_ZIG_ZAG (default) and GST_CAPS_INTERSECT_MODE_FIRST. API: gst_caps_intersect_full API: GstCapsIntersectMode API: GST_CAPS_INTERSECT_MODE_ZIG_ZAG API: GST_CAPS_INTERSECT_MODE_FIRST https://bugzilla.gnome.org/show_bug.cgi?id=617045
This commit is contained in:
parent
f9558b163f
commit
09d83e589a
4 changed files with 143 additions and 15 deletions
|
@ -747,6 +747,7 @@ init_post (GOptionContext * context, GOptionGroup * group, gpointer data,
|
|||
g_type_class_ref (gst_parse_flags_get_type ());
|
||||
g_type_class_ref (gst_search_mode_get_type ());
|
||||
g_type_class_ref (gst_progress_type_get_type ());
|
||||
g_type_class_ref (gst_caps_intersect_mode_get_type ());
|
||||
|
||||
gst_structure_get_type ();
|
||||
_gst_value_initialize ();
|
||||
|
@ -1112,6 +1113,7 @@ gst_deinit (void)
|
|||
g_type_class_unref (g_type_class_peek (gst_parse_error_get_type ()));
|
||||
g_type_class_unref (g_type_class_peek (gst_param_spec_fraction_get_type ()));
|
||||
g_type_class_unref (g_type_class_peek (gst_progress_type_get_type ()));
|
||||
g_type_class_unref (g_type_class_peek (gst_caps_intersect_mode_get_type ()));
|
||||
|
||||
gst_deinitialized = TRUE;
|
||||
GST_INFO ("deinitialized GStreamer");
|
||||
|
|
120
gst/gstcaps.c
120
gst/gstcaps.c
|
@ -1416,18 +1416,8 @@ gst_caps_can_intersect (const GstCaps * caps1, const GstCaps * caps2)
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_caps_intersect:
|
||||
* @caps1: a #GstCaps to intersect
|
||||
* @caps2: a #GstCaps to intersect
|
||||
*
|
||||
* Creates a new #GstCaps that contains all the formats that are common
|
||||
* to both @caps1 and @caps2.
|
||||
*
|
||||
* Returns: the new #GstCaps
|
||||
*/
|
||||
GstCaps *
|
||||
gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2)
|
||||
static GstCaps *
|
||||
gst_caps_intersect_zig_zag (const GstCaps * caps1, const GstCaps * caps2)
|
||||
{
|
||||
guint64 i; /* index can be up to 2 * G_MAX_UINT */
|
||||
guint j, k, len1, len2;
|
||||
|
@ -1437,9 +1427,6 @@ gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2)
|
|||
GstCaps *dest;
|
||||
GstStructure *istruct;
|
||||
|
||||
g_return_val_if_fail (GST_IS_CAPS (caps1), NULL);
|
||||
g_return_val_if_fail (GST_IS_CAPS (caps2), NULL);
|
||||
|
||||
/* caps are exactly the same pointers, just copy one caps */
|
||||
if (G_UNLIKELY (caps1 == caps2))
|
||||
return gst_caps_copy (caps1);
|
||||
|
@ -1500,6 +1487,109 @@ gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2)
|
|||
return dest;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_caps_intersect_first:
|
||||
* @caps1: a #GstCaps to intersect
|
||||
* @caps2: a #GstCaps to intersect
|
||||
*
|
||||
* Creates a new #GstCaps that contains all the formats that are common
|
||||
* to both @caps1 and @caps2.
|
||||
*
|
||||
* Unlike @gst_caps_intersect, the returned caps will be ordered in a similar
|
||||
* fashion as @caps1.
|
||||
*
|
||||
* Returns: the new #GstCaps
|
||||
*/
|
||||
static GstCaps *
|
||||
gst_caps_intersect_first (const GstCaps * caps1, const GstCaps * caps2)
|
||||
{
|
||||
guint64 i; /* index can be up to 2 * G_MAX_UINT */
|
||||
guint j, len1, len2;
|
||||
|
||||
GstStructure *struct1;
|
||||
GstStructure *struct2;
|
||||
GstCaps *dest;
|
||||
GstStructure *istruct;
|
||||
|
||||
/* caps are exactly the same pointers, just copy one caps */
|
||||
if (G_UNLIKELY (caps1 == caps2))
|
||||
return gst_caps_copy (caps1);
|
||||
|
||||
/* empty caps on either side, return empty */
|
||||
if (G_UNLIKELY (CAPS_IS_EMPTY (caps1) || CAPS_IS_EMPTY (caps2)))
|
||||
return gst_caps_new_empty ();
|
||||
|
||||
/* one of the caps is any, just copy the other caps */
|
||||
if (G_UNLIKELY (CAPS_IS_ANY (caps1)))
|
||||
return gst_caps_copy (caps2);
|
||||
if (G_UNLIKELY (CAPS_IS_ANY (caps2)))
|
||||
return gst_caps_copy (caps1);
|
||||
|
||||
dest = gst_caps_new_empty ();
|
||||
|
||||
len1 = caps1->structs->len;
|
||||
len2 = caps2->structs->len;
|
||||
for (i = 0; i < len1; i++) {
|
||||
struct1 = gst_caps_get_structure_unchecked (caps1, i);
|
||||
for (j = 0; j < len2; j++) {
|
||||
struct2 = gst_caps_get_structure_unchecked (caps2, j);
|
||||
istruct = gst_caps_structure_intersect (struct1, struct2);
|
||||
if (istruct)
|
||||
gst_caps_append_structure (dest, istruct);
|
||||
}
|
||||
}
|
||||
|
||||
return dest;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_caps_intersect_full:
|
||||
* @caps1: a #GstCaps to intersect
|
||||
* @caps2: a #GstCaps to intersect
|
||||
* @mode: The intersection algorithm/mode to use
|
||||
*
|
||||
* Creates a new #GstCaps that contains all the formats that are common
|
||||
* to both @caps1 and @caps2, the order is defined by the #GstCapsIntersectMode
|
||||
* used.
|
||||
*
|
||||
* Returns: the new #GstCaps
|
||||
* Since: 0.10.33
|
||||
*/
|
||||
GstCaps *
|
||||
gst_caps_intersect_full (const GstCaps * caps1, const GstCaps * caps2,
|
||||
GstCapsIntersectMode mode)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_CAPS (caps1), NULL);
|
||||
g_return_val_if_fail (GST_IS_CAPS (caps2), NULL);
|
||||
|
||||
switch (mode) {
|
||||
case GST_CAPS_INTERSECT_FIRST:
|
||||
return gst_caps_intersect_first (caps1, caps2);
|
||||
default:
|
||||
g_warning ("Unknown caps intersect mode: %d", mode);
|
||||
/* fallthrough */
|
||||
case GST_CAPS_INTERSECT_ZIG_ZAG:
|
||||
return gst_caps_intersect_zig_zag (caps1, caps2);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_caps_intersect:
|
||||
* @caps1: a #GstCaps to intersect
|
||||
* @caps2: a #GstCaps to intersect
|
||||
*
|
||||
* Creates a new #GstCaps that contains all the formats that are common
|
||||
* to both @caps1 and @caps2. Defaults to %GST_CAPS_INTERSECT_ZIG_ZAG mode.
|
||||
*
|
||||
* Returns: the new #GstCaps
|
||||
*/
|
||||
GstCaps *
|
||||
gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2)
|
||||
{
|
||||
return gst_caps_intersect_full (caps1, caps2, GST_CAPS_INTERSECT_ZIG_ZAG);
|
||||
}
|
||||
|
||||
|
||||
/* subtract operation */
|
||||
|
||||
typedef struct
|
||||
|
|
|
@ -43,6 +43,37 @@ typedef enum {
|
|||
GST_CAPS_FLAGS_ANY = (1 << 0)
|
||||
} GstCapsFlags;
|
||||
|
||||
/**
|
||||
* GstCapsIntersectMode:
|
||||
* @GST_CAPS_INTERSECT_ZIG_ZAG : Zig-zags over both caps.
|
||||
* @GST_CAPS_INTERSECT_FIRST : Keeps the first caps order.
|
||||
*
|
||||
* Modes of caps intersection
|
||||
*
|
||||
* #GST_CAPS_INTERSECT_ZIG_ZAG tries to preserve overall order of both caps
|
||||
* by iterating on the caps' structures as the following matrix shows:
|
||||
* caps1
|
||||
* +-------------
|
||||
* | 1 2 4 7
|
||||
* caps2 | 3 5 8 10
|
||||
* | 6 9 11 12
|
||||
*
|
||||
* Used when there is no explicit precedence of one caps over the other. e.g.
|
||||
* tee's sink pad getcaps function, it will probe its src pad peers' for their
|
||||
* caps and intersect them with this mode.
|
||||
*
|
||||
* #GST_CAPS_INTERSECT_FIRST is useful when an element wants to preserve
|
||||
* another element's caps priority order when intersecting with its own caps.
|
||||
* Example: If caps1 is [A, B, C] and caps2 is [E, B, D, A], the result
|
||||
* would be [A, B], maintaining the first caps priority on the intersection.
|
||||
*
|
||||
* Since: 0.10.33
|
||||
*/
|
||||
typedef enum {
|
||||
GST_CAPS_INTERSECT_ZIG_ZAG = 0,
|
||||
GST_CAPS_INTERSECT_FIRST = 1
|
||||
} GstCapsIntersectMode;
|
||||
|
||||
/**
|
||||
* GST_CAPS_ANY:
|
||||
*
|
||||
|
@ -237,6 +268,9 @@ gboolean gst_caps_can_intersect (const GstCaps * caps1,
|
|||
/* operations */
|
||||
GstCaps * gst_caps_intersect (const GstCaps *caps1,
|
||||
const GstCaps *caps2);
|
||||
GstCaps * gst_caps_intersect_full (const GstCaps *caps1,
|
||||
const GstCaps *caps2,
|
||||
GstCapsIntersectMode mode);
|
||||
GstCaps * gst_caps_subtract (const GstCaps *minuend,
|
||||
const GstCaps *subtrahend);
|
||||
GstCaps * gst_caps_union (const GstCaps *caps1,
|
||||
|
|
|
@ -162,6 +162,8 @@ EXPORTS
|
|||
gst_caps_get_structure
|
||||
gst_caps_get_type
|
||||
gst_caps_intersect
|
||||
gst_caps_intersect_full
|
||||
gst_caps_intersect_mode_get_type
|
||||
gst_caps_is_always_compatible
|
||||
gst_caps_is_any
|
||||
gst_caps_is_empty
|
||||
|
|
Loading…
Reference in a new issue