mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-12-24 17:20:36 +00:00
toc: Make structures opaque and clean up function names and fields a bit
This commit is contained in:
parent
070f7c4e1c
commit
dfd9b60221
10 changed files with 469 additions and 432 deletions
|
@ -48,15 +48,12 @@ select event with UID to seek on. Field 'subentries' of type GList contains
|
|||
children items of type GstTocEntry. Thus you can achieve arbitrary hierarchy
|
||||
level. Field 'type' can be either GST_TOC_ENTRY_TYPE_CHAPTER or
|
||||
GST_TOC_ENTRY_TYPE_EDITION which corresponds to chapter or edition type of
|
||||
item respectively. Field 'pads' of type GList contains list of GStreamer
|
||||
pads related to the item. It can be used for example to link a TOC with
|
||||
specific pad. Field 'tags' is a list of tags related to the item. And field
|
||||
item respectively. Field 'tags' is a list of tags related to the item. And field
|
||||
'info' is similar to GstToc.info described above.
|
||||
|
||||
So, a little more about managing GstToc. Use gst_toc_new() and gst_toc_unref()
|
||||
to create/free it. GstTocEntry can be created using gst_toc_entry_new() and
|
||||
gst_toc_entry_new_with_pad(). The latter method used to create GstTocEntry
|
||||
linked to particular pad. While building GstToc you can set start and stop
|
||||
to create/free it. GstTocEntry can be created using gst_toc_entry_new().
|
||||
While building GstToc you can set start and stop
|
||||
timestamps for each item using gst_toc_entry_set_start_stop().
|
||||
The best way to process already created GstToc is to recursively go through
|
||||
the 'entries' and 'subentries' fields.
|
||||
|
|
|
@ -2720,14 +2720,25 @@ gst_toc_new
|
|||
gst_toc_ref
|
||||
gst_toc_unref
|
||||
gst_toc_copy
|
||||
gst_toc_get_entries
|
||||
gst_toc_append_entry
|
||||
gst_toc_get_tags
|
||||
gst_toc_merge_tags
|
||||
gst_toc_set_tags
|
||||
gst_toc_entry_new
|
||||
gst_toc_entry_new_with_pad
|
||||
gst_toc_entry_ref
|
||||
gst_toc_entry_unref
|
||||
gst_toc_entry_copy
|
||||
gst_toc_find_entry
|
||||
gst_toc_entry_get_start_stop
|
||||
gst_toc_entry_set_start_stop
|
||||
gst_toc_entry_get_uid
|
||||
gst_toc_entry_get_sub_entries
|
||||
gst_toc_entry_append_sub_entry
|
||||
gst_toc_entry_get_start_stop_times
|
||||
gst_toc_entry_set_start_stop_times
|
||||
gst_toc_entry_get_tags
|
||||
gst_toc_entry_merge_tags
|
||||
gst_toc_entry_set_tags
|
||||
gst_toc_entry_type_get_nick
|
||||
gst_toc_entry_get_entry_type
|
||||
gst_toc_entry_is_alternative
|
||||
|
|
395
gst/gsttoc.c
395
gst/gsttoc.c
|
@ -22,7 +22,7 @@
|
|||
/**
|
||||
* SECTION:gsttoc
|
||||
* @short_description: Generic table of contents support
|
||||
* @see_also: #GstStructure, #GstEvent, #GstMessage, #GstQuery, #GstPad
|
||||
* @see_also: #GstStructure, #GstEvent, #GstMessage, #GstQuery
|
||||
*
|
||||
* #GstToc functions are used to create/free #GstToc and #GstTocEntry structures.
|
||||
* Also they are used to convert #GstToc into #GstStructure and vice versa.
|
||||
|
@ -72,6 +72,31 @@
|
|||
#include "gstpad.h"
|
||||
#include "gstquark.h"
|
||||
|
||||
struct _GstTocEntry
|
||||
{
|
||||
GstMiniObject mini_object;
|
||||
|
||||
gchar *uid;
|
||||
GstTocEntryType type;
|
||||
GstClockTime start, stop;
|
||||
GList *subentries;
|
||||
GstTagList *tags;
|
||||
|
||||
/*< private > */
|
||||
gpointer _gst_reserved[GST_PADDING];
|
||||
};
|
||||
|
||||
struct _GstToc
|
||||
{
|
||||
GstMiniObject mini_object;
|
||||
|
||||
GList *entries;
|
||||
GstTagList *tags;
|
||||
|
||||
/*< private > */
|
||||
gpointer _gst_reserved[GST_PADDING];
|
||||
};
|
||||
|
||||
#undef gst_toc_copy
|
||||
static GstToc *gst_toc_copy (const GstToc * toc);
|
||||
static void gst_toc_free (GstToc * toc);
|
||||
|
@ -104,14 +129,111 @@ gst_toc_new (void)
|
|||
(GstMiniObjectFreeFunction) gst_toc_free);
|
||||
|
||||
toc->tags = gst_tag_list_new_empty ();
|
||||
toc->info = gst_structure_new_id_empty (GST_QUARK (INFO_STRUCTURE));
|
||||
|
||||
return toc;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_set_tags:
|
||||
* @toc: A #GstToc instance
|
||||
* @tags: (allow-none) (transfer full): A #GstTagList or %NULL
|
||||
*
|
||||
* Set a #GstTagList with tags for the complete @toc.
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
void
|
||||
gst_toc_set_tags (GstToc * toc, GstTagList * tags)
|
||||
{
|
||||
g_return_if_fail (toc != NULL);
|
||||
g_return_if_fail (gst_mini_object_is_writable (GST_MINI_OBJECT_CAST (toc)));
|
||||
|
||||
if (toc->tags)
|
||||
gst_tag_list_unref (toc->tags);
|
||||
toc->tags = tags;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_merge_tags:
|
||||
* @toc: A #GstToc instance
|
||||
* @tags: (allow-none): A #GstTagList or %NULL
|
||||
* @mode: A #GstTagMergeMode
|
||||
*
|
||||
* Merge @tags into the existing tags of @toc using @mode.
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
void
|
||||
gst_toc_merge_tags (GstToc * toc, GstTagList * tags, GstTagMergeMode mode)
|
||||
{
|
||||
g_return_if_fail (toc != NULL);
|
||||
g_return_if_fail (gst_mini_object_is_writable (GST_MINI_OBJECT_CAST (toc)));
|
||||
|
||||
if (!toc->tags) {
|
||||
toc->tags = gst_tag_list_ref (tags);
|
||||
} else {
|
||||
GstTagList *tmp = gst_tag_list_merge (toc->tags, tags, mode);
|
||||
gst_tag_list_unref (toc->tags);
|
||||
toc->tags = tmp;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_get_tags:
|
||||
* @toc: A #GstToc instance
|
||||
*
|
||||
* Gets the tags for @toc.
|
||||
*
|
||||
* Returns: (transfer none): A #GstTagList for @entry
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
GstTagList *
|
||||
gst_toc_get_tags (const GstToc * toc)
|
||||
{
|
||||
g_return_val_if_fail (toc != NULL, NULL);
|
||||
|
||||
return toc->tags;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_append_entry:
|
||||
* @toc: A #GstToc instance
|
||||
* @entry: (transfer full): A #GstTocEntry
|
||||
*
|
||||
* Appends the #GstTocEntry @entry to @toc.
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
void
|
||||
gst_toc_append_entry (GstToc * toc, GstTocEntry * entry)
|
||||
{
|
||||
g_return_if_fail (toc != NULL);
|
||||
g_return_if_fail (gst_mini_object_is_writable (GST_MINI_OBJECT_CAST (toc)));
|
||||
|
||||
toc->entries = g_list_append (toc->entries, entry);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_get_entries:
|
||||
* @toc: A #GstToc instance
|
||||
*
|
||||
* Gets the list of #GstTocEntry of @toc.
|
||||
*
|
||||
* Returns: (transfer none) (element-type Gst.TocEntry): A #GList of #GstTocEntry for @entry
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
GList *
|
||||
gst_toc_get_entries (const GstToc * toc)
|
||||
{
|
||||
g_return_val_if_fail (toc != NULL, NULL);
|
||||
|
||||
return toc->entries;
|
||||
}
|
||||
|
||||
static GstTocEntry *
|
||||
gst_toc_entry_new_internal (GstTocEntryType type, const gchar * uid,
|
||||
GstPad * pad)
|
||||
gst_toc_entry_new_internal (GstTocEntryType type, const gchar * uid)
|
||||
{
|
||||
GstTocEntry *entry;
|
||||
|
||||
|
@ -123,11 +245,8 @@ gst_toc_entry_new_internal (GstTocEntryType type, const gchar * uid,
|
|||
|
||||
entry->uid = g_strdup (uid);
|
||||
entry->type = type;
|
||||
entry->tags = gst_tag_list_new_empty ();
|
||||
entry->info = gst_structure_new_id_empty (GST_QUARK (INFO_STRUCTURE));
|
||||
|
||||
if (pad != NULL && GST_IS_PAD (pad))
|
||||
entry->pads = g_list_append (entry->pads, gst_object_ref (pad));
|
||||
entry->tags = NULL;
|
||||
entry->start = entry->stop = GST_CLOCK_TIME_NONE;
|
||||
|
||||
return entry;
|
||||
}
|
||||
|
@ -148,29 +267,7 @@ gst_toc_entry_new (GstTocEntryType type, const gchar * uid)
|
|||
{
|
||||
g_return_val_if_fail (uid != NULL, NULL);
|
||||
|
||||
return gst_toc_entry_new_internal (type, uid, NULL);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_new_with_pad:
|
||||
* @type: entry type.
|
||||
* @uid: unique ID (UID) in the whole TOC.
|
||||
* @pad: #GstPad related to this entry.
|
||||
*
|
||||
* Create new #GstTocEntry structure with #GstPad related.
|
||||
*
|
||||
* Returns: newly allocated #GstTocEntry structure, free it with gst_toc_entry_unref()
|
||||
* when done.
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
GstTocEntry *
|
||||
gst_toc_entry_new_with_pad (GstTocEntryType type, const gchar * uid,
|
||||
GstPad * pad)
|
||||
{
|
||||
g_return_val_if_fail (uid != NULL, NULL);
|
||||
|
||||
return gst_toc_entry_new_internal (type, uid, pad);
|
||||
return gst_toc_entry_new_internal (type, uid);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -182,17 +279,12 @@ gst_toc_free (GstToc * toc)
|
|||
if (toc->tags != NULL)
|
||||
gst_tag_list_unref (toc->tags);
|
||||
|
||||
if (toc->info != NULL)
|
||||
gst_structure_free (toc->info);
|
||||
|
||||
g_slice_free (GstToc, toc);
|
||||
}
|
||||
|
||||
static void
|
||||
gst_toc_entry_free (GstTocEntry * entry)
|
||||
{
|
||||
GList *cur;
|
||||
|
||||
g_return_if_fail (entry != NULL);
|
||||
|
||||
g_list_foreach (entry->subentries, (GFunc) gst_mini_object_unref, NULL);
|
||||
|
@ -203,18 +295,6 @@ gst_toc_entry_free (GstTocEntry * entry)
|
|||
if (entry->tags != NULL)
|
||||
gst_tag_list_unref (entry->tags);
|
||||
|
||||
if (entry->info != NULL)
|
||||
gst_structure_free (entry->info);
|
||||
|
||||
cur = entry->pads;
|
||||
while (cur != NULL) {
|
||||
if (GST_IS_PAD (cur->data))
|
||||
gst_object_unref (cur->data);
|
||||
cur = cur->next;
|
||||
}
|
||||
|
||||
g_list_free (entry->pads);
|
||||
|
||||
g_slice_free (GstTocEntry, entry);
|
||||
}
|
||||
|
||||
|
@ -283,34 +363,23 @@ static GstTocEntry *
|
|||
gst_toc_entry_copy (const GstTocEntry * entry)
|
||||
{
|
||||
GstTocEntry *ret, *sub;
|
||||
GList *cur;
|
||||
GstTagList *list;
|
||||
GstStructure *st;
|
||||
GList *cur;
|
||||
|
||||
g_return_val_if_fail (entry != NULL, NULL);
|
||||
|
||||
ret = gst_toc_entry_new (entry->type, entry->uid);
|
||||
|
||||
if (GST_IS_STRUCTURE (entry->info)) {
|
||||
st = gst_structure_copy (entry->info);
|
||||
gst_structure_free (ret->info);
|
||||
ret->info = st;
|
||||
}
|
||||
ret->start = entry->start;
|
||||
ret->stop = entry->stop;
|
||||
|
||||
if (GST_IS_TAG_LIST (entry->tags)) {
|
||||
list = gst_tag_list_copy (entry->tags);
|
||||
gst_tag_list_unref (ret->tags);
|
||||
if (ret->tags)
|
||||
gst_tag_list_unref (ret->tags);
|
||||
ret->tags = list;
|
||||
}
|
||||
|
||||
cur = entry->pads;
|
||||
while (cur != NULL) {
|
||||
if (GST_IS_PAD (cur->data))
|
||||
ret->pads = g_list_prepend (ret->pads, gst_object_ref (cur->data));
|
||||
cur = cur->next;
|
||||
}
|
||||
ret->pads = g_list_reverse (ret->pads);
|
||||
|
||||
cur = entry->subentries;
|
||||
while (cur != NULL) {
|
||||
sub = gst_toc_entry_copy (cur->data);
|
||||
|
@ -343,18 +412,11 @@ gst_toc_copy (const GstToc * toc)
|
|||
GstTocEntry *entry;
|
||||
GList *cur;
|
||||
GstTagList *list;
|
||||
GstStructure *st;
|
||||
|
||||
g_return_val_if_fail (toc != NULL, NULL);
|
||||
|
||||
ret = gst_toc_new ();
|
||||
|
||||
if (GST_IS_STRUCTURE (toc->info)) {
|
||||
st = gst_structure_copy (toc->info);
|
||||
gst_structure_free (ret->info);
|
||||
ret->info = st;
|
||||
}
|
||||
|
||||
if (GST_IS_TAG_LIST (toc->tags)) {
|
||||
list = gst_tag_list_copy (toc->tags);
|
||||
gst_tag_list_unref (ret->tags);
|
||||
|
@ -376,7 +438,7 @@ gst_toc_copy (const GstToc * toc)
|
|||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_set_start_stop:
|
||||
* gst_toc_entry_set_start_stop_times:
|
||||
* @entry: #GstTocEntry to set values.
|
||||
* @start: start value to set.
|
||||
* @stop: stop value to set.
|
||||
|
@ -386,34 +448,17 @@ gst_toc_copy (const GstToc * toc)
|
|||
* Since: 0.10.37
|
||||
*/
|
||||
void
|
||||
gst_toc_entry_set_start_stop (GstTocEntry * entry, gint64 start, gint64 stop)
|
||||
gst_toc_entry_set_start_stop_times (GstTocEntry * entry, gint64 start,
|
||||
gint64 stop)
|
||||
{
|
||||
const GValue *val;
|
||||
GstStructure *structure = NULL;
|
||||
|
||||
g_return_if_fail (entry != NULL);
|
||||
g_return_if_fail (GST_IS_STRUCTURE (entry->info));
|
||||
|
||||
if (gst_structure_id_has_field_typed (entry->info, GST_QUARK (TIME),
|
||||
GST_TYPE_STRUCTURE)) {
|
||||
val = gst_structure_id_get_value (entry->info, GST_QUARK (TIME));
|
||||
structure = gst_structure_copy (gst_value_get_structure (val));
|
||||
}
|
||||
|
||||
if (structure == NULL)
|
||||
structure = gst_structure_new_id_empty (GST_QUARK (TIME_STRUCTURE));
|
||||
|
||||
gst_structure_id_set (structure, GST_QUARK (START),
|
||||
G_TYPE_INT64, start, GST_QUARK (STOP), G_TYPE_INT64, stop, NULL);
|
||||
|
||||
gst_structure_id_set (entry->info, GST_QUARK (TIME),
|
||||
GST_TYPE_STRUCTURE, structure, NULL);
|
||||
|
||||
gst_structure_free (structure);
|
||||
entry->start = start;
|
||||
entry->stop = stop;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_get_start_stop:
|
||||
* gst_toc_entry_get_start_stop_times:
|
||||
* @entry: #GstTocEntry to get values from.
|
||||
* @start: (out): the storage for the start value, leave #NULL if not need.
|
||||
* @stop: (out): the storage for the stop value, leave #NULL if not need.
|
||||
|
@ -426,42 +471,17 @@ gst_toc_entry_set_start_stop (GstTocEntry * entry, gint64 start, gint64 stop)
|
|||
* Since: 0.10.37
|
||||
*/
|
||||
gboolean
|
||||
gst_toc_entry_get_start_stop (const GstTocEntry * entry, gint64 * start,
|
||||
gst_toc_entry_get_start_stop_times (const GstTocEntry * entry, gint64 * start,
|
||||
gint64 * stop)
|
||||
{
|
||||
gboolean ret = TRUE;
|
||||
const GValue *val;
|
||||
const GstStructure *structure;
|
||||
|
||||
g_return_val_if_fail (entry != NULL, FALSE);
|
||||
g_return_val_if_fail (GST_IS_STRUCTURE (entry->info), FALSE);
|
||||
|
||||
if (!gst_structure_id_has_field_typed (entry->info,
|
||||
GST_QUARK (TIME), GST_TYPE_STRUCTURE))
|
||||
return FALSE;
|
||||
|
||||
val = gst_structure_id_get_value (entry->info, GST_QUARK (TIME));
|
||||
structure = gst_value_get_structure (val);
|
||||
|
||||
if (start != NULL) {
|
||||
if (gst_structure_id_has_field_typed (structure,
|
||||
GST_QUARK (START), G_TYPE_INT64))
|
||||
*start =
|
||||
g_value_get_int64 (gst_structure_id_get_value (structure,
|
||||
GST_QUARK (START)));
|
||||
else
|
||||
ret = FALSE;
|
||||
}
|
||||
|
||||
if (stop != NULL) {
|
||||
if (gst_structure_id_has_field_typed (structure,
|
||||
GST_QUARK (STOP), G_TYPE_INT64))
|
||||
*stop =
|
||||
g_value_get_int64 (gst_structure_id_get_value (structure,
|
||||
GST_QUARK (STOP)));
|
||||
else
|
||||
ret = FALSE;
|
||||
}
|
||||
if (start != NULL)
|
||||
*start = entry->start;
|
||||
if (stop != NULL)
|
||||
*stop = entry->stop;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
@ -505,7 +525,7 @@ gst_toc_entry_type_get_nick (GstTocEntryType type)
|
|||
* Returns: @entry's entry type
|
||||
*/
|
||||
GstTocEntryType
|
||||
gst_toc_entry_get_entry_type (GstTocEntry * entry)
|
||||
gst_toc_entry_get_entry_type (const GstTocEntry * entry)
|
||||
{
|
||||
g_return_val_if_fail (entry != NULL, GST_TOC_ENTRY_TYPE_INVALID);
|
||||
|
||||
|
@ -519,7 +539,7 @@ gst_toc_entry_get_entry_type (GstTocEntry * entry)
|
|||
* Returns: %TRUE if @entry's type is an alternative type, otherwise %FALSE
|
||||
*/
|
||||
gboolean
|
||||
gst_toc_entry_is_alternative (GstTocEntry * entry)
|
||||
gst_toc_entry_is_alternative (const GstTocEntry * entry)
|
||||
{
|
||||
g_return_val_if_fail (entry != NULL, FALSE);
|
||||
|
||||
|
@ -533,9 +553,128 @@ gst_toc_entry_is_alternative (GstTocEntry * entry)
|
|||
* Returns: %TRUE if @entry's type is a sequence type, otherwise %FALSE
|
||||
*/
|
||||
gboolean
|
||||
gst_toc_entry_is_sequence (GstTocEntry * entry)
|
||||
gst_toc_entry_is_sequence (const GstTocEntry * entry)
|
||||
{
|
||||
g_return_val_if_fail (entry != NULL, FALSE);
|
||||
|
||||
return GST_TOC_ENTRY_TYPE_IS_SEQUENCE (entry->type);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_get_uid:
|
||||
* @entry: A #GstTocEntry instance
|
||||
*
|
||||
* Gets the UID of @entry.
|
||||
*
|
||||
* Returns: (transfer none): The UID of @entry
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
const gchar *
|
||||
gst_toc_entry_get_uid (const GstTocEntry * entry)
|
||||
{
|
||||
g_return_val_if_fail (entry != NULL, NULL);
|
||||
|
||||
return entry->uid;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_append_sub_entry:
|
||||
* @entry: A #GstTocEntry instance
|
||||
* @subentry: (transfer full): A #GstTocEntry
|
||||
*
|
||||
* Appends the #GstTocEntry @subentry to @entry.
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
void
|
||||
gst_toc_entry_append_sub_entry (GstTocEntry * entry, GstTocEntry * subentry)
|
||||
{
|
||||
g_return_if_fail (entry != NULL);
|
||||
g_return_if_fail (subentry != NULL);
|
||||
g_return_if_fail (gst_mini_object_is_writable (GST_MINI_OBJECT_CAST (entry)));
|
||||
|
||||
entry->subentries = g_list_append (entry->subentries, subentry);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_get_uid:
|
||||
* @entry: A #GstTocEntry instance
|
||||
*
|
||||
* Gets the sub-entries of @entry.
|
||||
*
|
||||
* Returns: (transfer none) (element-type Gst.TocEntry): A #GList of #GstTocEntry of @entry
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
GList *
|
||||
gst_toc_entry_get_sub_entries (const GstTocEntry * entry)
|
||||
{
|
||||
g_return_val_if_fail (entry != NULL, NULL);
|
||||
|
||||
return entry->subentries;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_set_tags:
|
||||
* @entry: A #GstTocEntry instance
|
||||
* @tags: (allow-none) (transfer full): A #GstTagList or %NULL
|
||||
*
|
||||
* Set a #GstTagList with tags for the complete @entry.
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
void
|
||||
gst_toc_entry_set_tags (GstTocEntry * entry, GstTagList * tags)
|
||||
{
|
||||
g_return_if_fail (entry != NULL);
|
||||
g_return_if_fail (gst_mini_object_is_writable (GST_MINI_OBJECT_CAST (entry)));
|
||||
|
||||
if (entry->tags)
|
||||
gst_tag_list_unref (entry->tags);
|
||||
entry->tags = tags;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_merge_tags:
|
||||
* @entry: A #GstTocEntry instance
|
||||
* @tags: (allow-none): A #GstTagList or %NULL
|
||||
* @mode: A #GstTagMergeMode
|
||||
*
|
||||
* Merge @tags into the existing tags of @entry using @mode.
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
void
|
||||
gst_toc_entry_merge_tags (GstTocEntry * entry, GstTagList * tags,
|
||||
GstTagMergeMode mode)
|
||||
{
|
||||
g_return_if_fail (entry != NULL);
|
||||
g_return_if_fail (gst_mini_object_is_writable (GST_MINI_OBJECT_CAST (entry)));
|
||||
|
||||
if (!entry->tags) {
|
||||
entry->tags = gst_tag_list_ref (tags);
|
||||
} else {
|
||||
GstTagList *tmp = gst_tag_list_merge (entry->tags, tags, mode);
|
||||
gst_tag_list_unref (entry->tags);
|
||||
entry->tags = tmp;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_toc_entry_get_tags:
|
||||
* @entry: A #GstTocEntry instance
|
||||
*
|
||||
* Gets the tags for @entry.
|
||||
*
|
||||
* Returns: (transfer none): A #GstTagList for @entry
|
||||
*
|
||||
* Since: 0.10.37
|
||||
*/
|
||||
GstTagList *
|
||||
gst_toc_entry_get_tags (const GstTocEntry * entry)
|
||||
{
|
||||
g_return_val_if_fail (entry != NULL, NULL);
|
||||
|
||||
return entry->tags;
|
||||
}
|
||||
|
|
87
gst/gsttoc.h
87
gst/gsttoc.h
|
@ -63,65 +63,19 @@ typedef enum {
|
|||
#define GST_TOC_ENTRY_TYPE_IS_ALTERNATIVE(entry_type) (entry_type < 0)
|
||||
#define GST_TOC_ENTRY_TYPE_IS_SEQUENCE(entry_type) (entry_type > 0)
|
||||
|
||||
/**
|
||||
* GstTocEntry:
|
||||
* @uid: unique (for a whole TOC) id of the entry. This value should be persistent and
|
||||
* should not be changed while updating TOC. @uid should be handled as "opaque" value
|
||||
* without meaning (e.g. applications should not assume the /editionX/chapterY/chapter/Z structure,
|
||||
* other demuxers could do something else), it should help to track updates of certain entries.
|
||||
* @type: #GstTocEntryType of this entry.
|
||||
* @subentries: (element-type GstTocEntry): list of #GstTocEntry
|
||||
* children.
|
||||
* @pads: (element-type GstPad): list of #GstPad objects, related to
|
||||
* this #GstTocEntry.
|
||||
* @tags: tags related to this entry.
|
||||
* @info: extra information related to this entry.
|
||||
*
|
||||
* Definition of TOC entry structure.
|
||||
*/
|
||||
struct _GstTocEntry {
|
||||
GstMiniObject mini_object;
|
||||
|
||||
gchar *uid;
|
||||
GstTocEntryType type;
|
||||
GList *subentries;
|
||||
GList *pads;
|
||||
GstTagList *tags;
|
||||
GstStructure *info;
|
||||
|
||||
/*< private >*/
|
||||
gpointer _gst_reserved[GST_PADDING];
|
||||
};
|
||||
|
||||
/* FIXME: pad member should be GstPad type, but that's
|
||||
* impossible due to recursive includes */
|
||||
|
||||
/**
|
||||
* GstToc:
|
||||
* @entries: (element-type GstTocEntry): list of #GstTocEntry entries
|
||||
* of the TOC.
|
||||
* @tags: tags related to the whole TOC.
|
||||
* @info: extra information related to the TOC.
|
||||
*
|
||||
* Definition of TOC structure.
|
||||
*/
|
||||
struct _GstToc {
|
||||
GstMiniObject mini_object;
|
||||
|
||||
GList *entries;
|
||||
GstTagList *tags;
|
||||
GstStructure *info;
|
||||
|
||||
/*< private >*/
|
||||
gpointer _gst_reserved[GST_PADDING];
|
||||
};
|
||||
|
||||
/* functions to return type structures */
|
||||
GType gst_toc_get_type (void);
|
||||
GType gst_toc_entry_get_type (void);
|
||||
|
||||
/* functions to create, ref and unref/free TOCs */
|
||||
GstToc * gst_toc_new (void);
|
||||
GstToc * gst_toc_new (void);
|
||||
|
||||
void gst_toc_set_tags (GstToc *toc, GstTagList * tags);
|
||||
void gst_toc_merge_tags (GstToc *toc, GstTagList *tags, GstTagMergeMode mode);
|
||||
GstTagList * gst_toc_get_tags (const GstToc *toc);
|
||||
|
||||
void gst_toc_append_entry (GstToc *toc, GstTocEntry *entry);
|
||||
GList * gst_toc_get_entries (const GstToc *toc);
|
||||
|
||||
#define gst_toc_ref(toc) (GstToc*)gst_mini_object_ref(GST_MINI_OBJECT_CAST(toc))
|
||||
#define gst_toc_unref(toc) gst_mini_object_unref(GST_MINI_OBJECT_CAST(toc))
|
||||
|
@ -130,23 +84,32 @@ GstToc * gst_toc_new (void);
|
|||
|
||||
/* functions to create, ref and unref/free TOC entries */
|
||||
GstTocEntry * gst_toc_entry_new (GstTocEntryType type, const gchar *uid);
|
||||
GstTocEntry * gst_toc_entry_new_with_pad (GstTocEntryType type, const gchar *uid, GstPad * pad);
|
||||
|
||||
#define gst_toc_entry_ref(entry) (GstTocEntry*)gst_mini_object_ref(GST_MINI_OBJECT_CAST(entry))
|
||||
#define gst_toc_entry_unref(entry) gst_mini_object_unref(GST_MINI_OBJECT_CAST(entry))
|
||||
#define gst_toc_entry_copy(entry) (GstTocEntry*)gst_mini_object_copy(GST_MINI_OBJECT_CAST(entry))
|
||||
#define gst_toc_entry_make_writable(entry) (GstTocEntry*)gst_mini_object_make_writable(GST_MINI_OBJECT_CAST(entry))
|
||||
|
||||
GstTocEntry * gst_toc_find_entry (const GstToc *toc, const gchar *uid);
|
||||
GstTocEntry * gst_toc_find_entry (const GstToc *toc, const gchar *uid);
|
||||
|
||||
GstTocEntryType gst_toc_entry_get_entry_type (GstTocEntry * entry);
|
||||
GstTocEntryType gst_toc_entry_get_entry_type (const GstTocEntry *entry);
|
||||
const gchar * gst_toc_entry_get_uid (const GstTocEntry *entry);
|
||||
|
||||
gboolean gst_toc_entry_is_alternative (GstTocEntry * entry);
|
||||
gboolean gst_toc_entry_is_sequence (GstTocEntry * entry);
|
||||
void gst_toc_entry_append_sub_entry (GstTocEntry *entry, GstTocEntry *subentry);
|
||||
GList * gst_toc_entry_get_sub_entries (const GstTocEntry *entry);
|
||||
|
||||
void gst_toc_entry_set_start_stop (GstTocEntry *entry, gint64 start, gint64 stop);
|
||||
gboolean gst_toc_entry_get_start_stop (const GstTocEntry *entry, gint64 *start, gint64 *stop);
|
||||
const gchar * gst_toc_entry_type_get_nick (GstTocEntryType type);
|
||||
void gst_toc_entry_set_tags (GstTocEntry *entry, GstTagList *tags);
|
||||
void gst_toc_entry_merge_tags (GstTocEntry *entry, GstTagList *tags, GstTagMergeMode mode);
|
||||
GstTagList * gst_toc_entry_get_tags (const GstTocEntry *entry);
|
||||
|
||||
gboolean gst_toc_entry_is_alternative (const GstTocEntry *entry);
|
||||
gboolean gst_toc_entry_is_sequence (const GstTocEntry *entry);
|
||||
|
||||
void gst_toc_entry_set_start_stop_times (GstTocEntry *entry, gint64 start, gint64 stop);
|
||||
gboolean gst_toc_entry_get_start_stop_times (const GstTocEntry *entry, gint64 *start, gint64 *stop);
|
||||
|
||||
|
||||
const gchar * gst_toc_entry_type_get_nick (GstTocEntryType type);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
|
|
@ -46,90 +46,75 @@
|
|||
#define TOC_TAG "TocTag"
|
||||
|
||||
#define TEST_UID "129537542"
|
||||
#define INFO_NAME "gst-toc-check"
|
||||
#define INFO_FIELD "info-test"
|
||||
#define INFO_TEXT_EN "info-text-entry"
|
||||
#define INFO_TEXT_TOC "info-text-toc"
|
||||
|
||||
#define CHECK_TOC_ENTRY(entry_c,type_c,uid_c) \
|
||||
{ \
|
||||
GstTagList *tags; \
|
||||
gchar *tag_c; \
|
||||
const GValue *val; \
|
||||
GstStructure *struct_c; \
|
||||
\
|
||||
fail_unless_equals_string (entry_c->uid, uid_c); \
|
||||
fail_unless (entry_c->type == type_c); \
|
||||
fail_unless (entry_c->tags != NULL); \
|
||||
fail_unless (entry_c->pads == NULL); \
|
||||
fail_unless_equals_string (gst_toc_entry_get_uid (entry_c), uid_c); \
|
||||
fail_unless (gst_toc_entry_get_entry_type (entry_c) == type_c); \
|
||||
\
|
||||
fail_unless (entry_c->info != NULL); \
|
||||
gst_structure_get (entry_c->info, INFO_NAME, GST_TYPE_STRUCTURE, \
|
||||
&struct_c, NULL); \
|
||||
fail_unless (struct_c != NULL); \
|
||||
val = gst_structure_get_value (struct_c, INFO_FIELD); \
|
||||
fail_unless (val != NULL); \
|
||||
fail_unless_equals_string (g_value_get_string (val), INFO_TEXT_EN); \
|
||||
\
|
||||
fail_unless (gst_tag_list_get_string (entry_c->tags, \
|
||||
GST_TAG_TITLE, &tag_c)); \
|
||||
tags = gst_toc_entry_get_tags (entry_c); \
|
||||
fail_unless (tags != NULL); \
|
||||
fail_unless (gst_tag_list_get_string (tags, \
|
||||
GST_TAG_TITLE, &tag_c)); \
|
||||
fail_unless_equals_string (tag_c, ENTRY_TAG); \
|
||||
g_free (tag_c); \
|
||||
gst_structure_free (struct_c); \
|
||||
}
|
||||
|
||||
#define CHECK_TOC(toc_t) \
|
||||
{ \
|
||||
GstTocEntry *entry_t, *subentry_t; \
|
||||
GstTagList *tags; \
|
||||
GList *entries, *subentries, *subsubentries; \
|
||||
gchar *tag_t; \
|
||||
const GValue *val; \
|
||||
GstStructure *struct_toc; \
|
||||
\
|
||||
/* check TOC */ \
|
||||
fail_unless (g_list_length (toc_t->entries) == 2); \
|
||||
fail_unless (toc_t->tags != NULL); \
|
||||
fail_unless (gst_tag_list_get_string (toc_t->tags, \
|
||||
GST_TAG_TITLE, &tag_t)); \
|
||||
tags = gst_toc_get_tags (toc_t); \
|
||||
fail_unless (tags != NULL); \
|
||||
fail_unless (gst_tag_list_get_string (tags, \
|
||||
GST_TAG_TITLE, &tag_t)); \
|
||||
fail_unless_equals_string (tag_t, TOC_TAG); \
|
||||
g_free (tag_t); \
|
||||
\
|
||||
fail_unless (toc_t->info != NULL); \
|
||||
gst_structure_get (toc_t->info, INFO_NAME, GST_TYPE_STRUCTURE, \
|
||||
&struct_toc, NULL); \
|
||||
fail_unless (struct_toc != NULL); \
|
||||
val = gst_structure_get_value (struct_toc, INFO_FIELD); \
|
||||
fail_unless (val != NULL); \
|
||||
fail_unless_equals_string (g_value_get_string (val), INFO_TEXT_TOC); \
|
||||
gst_structure_free (struct_toc); \
|
||||
\
|
||||
entries = gst_toc_get_entries (toc_t); \
|
||||
fail_unless_equals_int (g_list_length (entries), 2); \
|
||||
/* check edition1 */ \
|
||||
entry_t = g_list_nth_data (toc_t->entries, 0); \
|
||||
entry_t = g_list_nth_data (entries, 0); \
|
||||
fail_if (entry_t == NULL); \
|
||||
fail_unless (g_list_length (entry_t->subentries) == 2); \
|
||||
subentries = gst_toc_entry_get_sub_entries (entry_t); \
|
||||
fail_unless_equals_int (g_list_length (subentries), 2); \
|
||||
CHECK_TOC_ENTRY (entry_t, GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED1); \
|
||||
/* check chapter1 */ \
|
||||
subentry_t = g_list_nth_data (entry_t->subentries, 0); \
|
||||
subentry_t = g_list_nth_data (subentries, 0); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 0); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 0); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH1); \
|
||||
/* check chapter2 */ \
|
||||
subentry_t = g_list_nth_data (entry_t->subentries, 1); \
|
||||
subentry_t = g_list_nth_data (subentries, 1); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 0); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 0); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH2); \
|
||||
/* check edition2 */ \
|
||||
entry_t = g_list_nth_data (toc_t->entries, 1); \
|
||||
entry_t = g_list_nth_data (entries, 1); \
|
||||
fail_if (entry_t == NULL); \
|
||||
fail_unless (g_list_length (entry_t->subentries) == 1); \
|
||||
subentries = gst_toc_entry_get_sub_entries (entry_t); \
|
||||
fail_unless_equals_int (g_list_length (subentries), 1); \
|
||||
CHECK_TOC_ENTRY (entry_t, GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED2); \
|
||||
/* check chapter3 */ \
|
||||
subentry_t = g_list_nth_data (entry_t->subentries, 0); \
|
||||
subentry_t = g_list_nth_data (subentries, 0); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 1); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 1); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH3); \
|
||||
/* check subchapter1 */ \
|
||||
subentry_t = g_list_nth_data (subentry_t->subentries, 0); \
|
||||
subentry_t = g_list_nth_data (subentries, 0); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 0); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 0); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_SUB1); \
|
||||
}
|
||||
|
||||
|
@ -137,9 +122,9 @@
|
|||
* the original TOC into the message/query/event */
|
||||
GST_START_TEST (test_serializing)
|
||||
{
|
||||
GstStructure *structure;
|
||||
GstToc *toc, *test_toc = NULL;
|
||||
GstTocEntry *ed, *ch, *subch;
|
||||
GstTagList *tags;
|
||||
GstEvent *event;
|
||||
GstMessage *message;
|
||||
GstQuery *query;
|
||||
|
@ -149,62 +134,48 @@ GST_START_TEST (test_serializing)
|
|||
|
||||
toc = gst_toc_new ();
|
||||
fail_if (toc == NULL);
|
||||
gst_tag_list_add (toc->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
TOC_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_TOC,
|
||||
NULL);
|
||||
gst_structure_set (toc->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, TOC_TAG, NULL);
|
||||
gst_toc_set_tags (toc, tags);
|
||||
|
||||
/* create edition1 */
|
||||
ed = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED1);
|
||||
fail_if (ed == NULL);
|
||||
gst_tag_list_add (ed->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ed->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ed, tags);
|
||||
|
||||
CHECK_TOC_ENTRY (ed, GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED1);
|
||||
|
||||
/* append chapter1 to edition1 */
|
||||
ch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH1);
|
||||
fail_if (ch == NULL);
|
||||
gst_tag_list_add (ch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ch, tags);
|
||||
|
||||
CHECK_TOC_ENTRY (ch, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH1);
|
||||
|
||||
ed->subentries = g_list_append (ed->subentries, ch);
|
||||
fail_unless (g_list_length (ed->subentries) == 1);
|
||||
gst_toc_entry_append_sub_entry (ed, ch);
|
||||
fail_unless_equals_int (g_list_length (gst_toc_entry_get_sub_entries (ed)),
|
||||
1);
|
||||
|
||||
/* append chapter2 to edition1 */
|
||||
ch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH2);
|
||||
fail_if (ch == NULL);
|
||||
gst_tag_list_add (ch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ch, tags);
|
||||
|
||||
CHECK_TOC_ENTRY (ch, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH2);
|
||||
|
||||
ed->subentries = g_list_append (ed->subentries, ch);
|
||||
fail_unless (g_list_length (ed->subentries) == 2);
|
||||
gst_toc_entry_append_sub_entry (ed, ch);
|
||||
fail_unless_equals_int (g_list_length (gst_toc_entry_get_sub_entries (ed)),
|
||||
2);
|
||||
|
||||
/* append edition1 to the TOC */
|
||||
toc->entries = g_list_append (toc->entries, ed);
|
||||
fail_unless (g_list_length (toc->entries) == 1);
|
||||
gst_toc_append_entry (toc, ed);
|
||||
fail_unless_equals_int (g_list_length (gst_toc_get_entries (toc)), 1);
|
||||
|
||||
/* test gst_toc_entry_find() */
|
||||
ed = NULL;
|
||||
|
@ -215,62 +186,51 @@ GST_START_TEST (test_serializing)
|
|||
CHECK_TOC_ENTRY (ed, GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED1);
|
||||
|
||||
/* test info GstStructure */
|
||||
gst_toc_entry_set_start_stop (ch, 100, 1000);
|
||||
fail_if (!gst_toc_entry_get_start_stop (ch, &start, &stop));
|
||||
gst_toc_entry_set_start_stop_times (ch, 100, 1000);
|
||||
fail_if (!gst_toc_entry_get_start_stop_times (ch, &start, &stop));
|
||||
fail_unless (start == 100);
|
||||
fail_unless (stop == 1000);
|
||||
|
||||
/* create edition2 */
|
||||
ed = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED2);
|
||||
fail_if (ed == NULL);
|
||||
gst_tag_list_add (ed->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ed->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ed, tags);
|
||||
|
||||
CHECK_TOC_ENTRY (ed, GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED2);
|
||||
|
||||
/* create chapter3 */
|
||||
ch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH3);
|
||||
fail_if (ch == NULL);
|
||||
gst_tag_list_add (ch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ch, tags);
|
||||
|
||||
CHECK_TOC_ENTRY (ch, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH3);
|
||||
|
||||
/* create subchapter1 */
|
||||
subch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_SUB1);
|
||||
fail_if (subch == NULL);
|
||||
gst_tag_list_add (subch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (subch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure,
|
||||
NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (subch, tags);
|
||||
|
||||
CHECK_TOC_ENTRY (subch, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_SUB1);
|
||||
|
||||
/* append subchapter1 to chapter3 */
|
||||
ch->subentries = g_list_append (ch->subentries, subch);
|
||||
fail_unless (g_list_length (ch->subentries) == 1);
|
||||
gst_toc_entry_append_sub_entry (ch, subch);
|
||||
fail_unless_equals_int (g_list_length (gst_toc_entry_get_sub_entries (ch)),
|
||||
1);
|
||||
|
||||
/* append chapter3 to edition2 */
|
||||
ed->subentries = g_list_append (ed->subentries, ch);
|
||||
fail_unless (g_list_length (ed->subentries) == 1);
|
||||
gst_toc_entry_append_sub_entry (ed, ch);
|
||||
fail_unless_equals_int (g_list_length (gst_toc_entry_get_sub_entries (ed)),
|
||||
1);
|
||||
|
||||
/* finally append edition2 to the TOC */
|
||||
toc->entries = g_list_append (toc->entries, ed);
|
||||
fail_unless (g_list_length (toc->entries) == 2);
|
||||
gst_toc_append_entry (toc, ed);
|
||||
fail_unless_equals_int (g_list_length (gst_toc_get_entries (toc)), 2);
|
||||
|
||||
/* test gst_toc_copy() */
|
||||
test_toc = gst_toc_copy (toc);
|
||||
|
|
|
@ -34,90 +34,75 @@
|
|||
|
||||
#define ENTRY_TAG "EntryTag"
|
||||
#define TOC_TAG "TocTag"
|
||||
#define INFO_NAME "gst-toc-setter-check"
|
||||
#define INFO_FIELD "info-test"
|
||||
#define INFO_TEXT_EN "info-text-entry"
|
||||
#define INFO_TEXT_TOC "info-text-toc"
|
||||
|
||||
#define CHECK_TOC_ENTRY(entry_c,type_c,uid_c) \
|
||||
{ \
|
||||
GstTagList *tags; \
|
||||
gchar *tag_c; \
|
||||
const GValue *val; \
|
||||
GstStructure *struct_c; \
|
||||
\
|
||||
fail_unless_equals_string (entry_c->uid, uid_c); \
|
||||
fail_unless (entry_c->type == type_c); \
|
||||
fail_unless (entry_c->tags != NULL); \
|
||||
fail_unless (entry_c->pads == NULL); \
|
||||
fail_unless_equals_string (gst_toc_entry_get_uid (entry_c), uid_c); \
|
||||
fail_unless (gst_toc_entry_get_entry_type (entry_c) == type_c); \
|
||||
\
|
||||
fail_unless (entry_c->info != NULL); \
|
||||
gst_structure_get (entry_c->info, INFO_NAME, GST_TYPE_STRUCTURE, \
|
||||
&struct_c, NULL); \
|
||||
fail_unless (struct_c != NULL); \
|
||||
val = gst_structure_get_value (struct_c, INFO_FIELD); \
|
||||
fail_unless (val != NULL); \
|
||||
fail_unless_equals_string (g_value_get_string (val), INFO_TEXT_EN); \
|
||||
\
|
||||
fail_unless (gst_tag_list_get_string (entry_c->tags, \
|
||||
tags = gst_toc_entry_get_tags (entry_c); \
|
||||
fail_unless (tags != NULL); \
|
||||
fail_unless (gst_tag_list_get_string (tags, \
|
||||
GST_TAG_TITLE, &tag_c)); \
|
||||
fail_unless_equals_string (tag_c, ENTRY_TAG); \
|
||||
g_free (tag_c); \
|
||||
gst_structure_free (struct_c); \
|
||||
}
|
||||
|
||||
#define CHECK_TOC(toc_t) \
|
||||
{ \
|
||||
GstTocEntry *entry_t, *subentry_t; \
|
||||
GstTagList *tags; \
|
||||
GList *entries, *subentries, *subsubentries; \
|
||||
gchar *tag_t; \
|
||||
const GValue *val; \
|
||||
GstStructure *struct_toc; \
|
||||
\
|
||||
/* check TOC */ \
|
||||
fail_unless (g_list_length (toc_t->entries) == 2); \
|
||||
fail_unless (toc_t->tags != NULL); \
|
||||
fail_unless (gst_tag_list_get_string (toc_t->tags, \
|
||||
tags = gst_toc_get_tags (toc_t); \
|
||||
fail_unless (tags != NULL); \
|
||||
fail_unless (gst_tag_list_get_string (tags, \
|
||||
GST_TAG_TITLE, &tag_t)); \
|
||||
fail_unless_equals_string (tag_t, TOC_TAG); \
|
||||
g_free (tag_t); \
|
||||
\
|
||||
fail_unless (toc_t->info != NULL); \
|
||||
gst_structure_get (toc_t->info, INFO_NAME, GST_TYPE_STRUCTURE, \
|
||||
&struct_toc, NULL); \
|
||||
fail_unless (struct_toc != NULL); \
|
||||
val = gst_structure_get_value (struct_toc, INFO_FIELD); \
|
||||
fail_unless (val != NULL); \
|
||||
fail_unless_equals_string (g_value_get_string (val), INFO_TEXT_TOC); \
|
||||
gst_structure_free (struct_toc); \
|
||||
\
|
||||
entries = gst_toc_get_entries (toc_t); \
|
||||
fail_unless_equals_int (g_list_length (entries), 2); \
|
||||
/* check edition1 */ \
|
||||
entry_t = g_list_nth_data (toc_t->entries, 0); \
|
||||
entry_t = g_list_nth_data (entries, 0); \
|
||||
fail_if (entry_t == NULL); \
|
||||
fail_unless (g_list_length (entry_t->subentries) == 2); \
|
||||
subentries = gst_toc_entry_get_sub_entries (entry_t); \
|
||||
fail_unless_equals_int (g_list_length (subentries), 2); \
|
||||
CHECK_TOC_ENTRY (entry_t, GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED1); \
|
||||
/* check chapter1 */ \
|
||||
subentry_t = g_list_nth_data (entry_t->subentries, 0); \
|
||||
subentry_t = g_list_nth_data (subentries, 0); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 0); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 0); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH1); \
|
||||
/* check chapter2 */ \
|
||||
subentry_t = g_list_nth_data (entry_t->subentries, 1); \
|
||||
subentry_t = g_list_nth_data (subentries, 1); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 0); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 0); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH2); \
|
||||
/* check edition2 */ \
|
||||
entry_t = g_list_nth_data (toc_t->entries, 1); \
|
||||
entry_t = g_list_nth_data (entries, 1); \
|
||||
fail_if (entry_t == NULL); \
|
||||
fail_unless (g_list_length (entry_t->subentries) == 1); \
|
||||
subentries = gst_toc_entry_get_sub_entries (entry_t); \
|
||||
fail_unless_equals_int (g_list_length (subentries), 1); \
|
||||
CHECK_TOC_ENTRY (entry_t, GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED2); \
|
||||
/* check chapter3 */ \
|
||||
subentry_t = g_list_nth_data (entry_t->subentries, 0); \
|
||||
subentry_t = g_list_nth_data (subentries, 0); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 1); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 1); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH3); \
|
||||
/* check subchapter1 */ \
|
||||
subentry_t = g_list_nth_data (subentry_t->subentries, 0); \
|
||||
subentry_t = g_list_nth_data (subentries, 0); \
|
||||
fail_if (subentry_t == NULL); \
|
||||
fail_unless (g_list_length (subentry_t->subentries) == 0); \
|
||||
subsubentries = gst_toc_entry_get_sub_entries (subentry_t); \
|
||||
fail_unless_equals_int (g_list_length (subsubentries), 0); \
|
||||
CHECK_TOC_ENTRY (subentry_t, GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_SUB1); \
|
||||
}
|
||||
|
||||
|
@ -144,95 +129,66 @@ gst_dummy_enc_init (GstDummyEnc * enc)
|
|||
static GstToc *
|
||||
create_toc (void)
|
||||
{
|
||||
GstStructure *structure;
|
||||
GstToc *toc;
|
||||
GstTocEntry *ed, *ch, *subch;
|
||||
GstTagList *tags;
|
||||
|
||||
toc = gst_toc_new ();
|
||||
gst_tag_list_add (toc->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
TOC_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_TOC,
|
||||
NULL);
|
||||
gst_structure_set (toc->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, TOC_TAG, NULL);
|
||||
gst_toc_set_tags (toc, tags);
|
||||
|
||||
/* create edition1 */
|
||||
ed = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED1);
|
||||
gst_tag_list_add (ed->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ed->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ed, tags);
|
||||
|
||||
/* append chapter1 to edition1 */
|
||||
ch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH1);
|
||||
gst_tag_list_add (ch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ch, tags);
|
||||
|
||||
ed->subentries = g_list_append (ed->subentries, ch);
|
||||
gst_toc_entry_append_sub_entry (ed, ch);
|
||||
|
||||
/* append chapter2 to edition1 */
|
||||
ch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH2);
|
||||
gst_tag_list_add (ch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ch, tags);
|
||||
|
||||
ed->subentries = g_list_append (ed->subentries, ch);
|
||||
gst_toc_entry_append_sub_entry (ed, ch);
|
||||
|
||||
/* append edition1 to the TOC */
|
||||
toc->entries = g_list_append (toc->entries, ed);
|
||||
gst_toc_append_entry (toc, ed);
|
||||
|
||||
/* create edition2 */
|
||||
ed = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_EDITION, ENTRY_ED2);
|
||||
gst_tag_list_add (ed->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ed->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ed, tags);
|
||||
|
||||
/* create chapter3 */
|
||||
ch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_CH3);
|
||||
gst_tag_list_add (ch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (ch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure, NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (ch, tags);
|
||||
|
||||
/* create subchapter1 */
|
||||
subch = gst_toc_entry_new (GST_TOC_ENTRY_TYPE_CHAPTER, ENTRY_SUB1);
|
||||
gst_tag_list_add (subch->tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE,
|
||||
ENTRY_TAG, NULL);
|
||||
structure =
|
||||
gst_structure_new (INFO_NAME, INFO_FIELD, G_TYPE_STRING, INFO_TEXT_EN,
|
||||
NULL);
|
||||
gst_structure_set (subch->info, INFO_NAME, GST_TYPE_STRUCTURE, structure,
|
||||
NULL);
|
||||
gst_structure_free (structure);
|
||||
tags = gst_tag_list_new_empty ();
|
||||
gst_tag_list_add (tags, GST_TAG_MERGE_APPEND, GST_TAG_TITLE, ENTRY_TAG, NULL);
|
||||
gst_toc_entry_set_tags (subch, tags);
|
||||
|
||||
/* append subchapter1 to chapter3 */
|
||||
ch->subentries = g_list_append (ch->subentries, subch);
|
||||
gst_toc_entry_append_sub_entry (ch, subch);
|
||||
|
||||
/* append chapter3 to edition2 */
|
||||
ed->subentries = g_list_append (ed->subentries, ch);
|
||||
gst_toc_entry_append_sub_entry (ed, ch);
|
||||
|
||||
/* finally append edition2 to the TOC */
|
||||
toc->entries = g_list_append (toc->entries, ed);
|
||||
gst_toc_append_entry (toc, ed);
|
||||
|
||||
return toc;
|
||||
}
|
||||
|
|
|
@ -468,12 +468,14 @@ print_toc_entry (gpointer data, gpointer user_data)
|
|||
GstTocEntry *entry = (GstTocEntry *) data;
|
||||
const gchar spc[MAX_INDENT + 1] = " ";
|
||||
guint indent = MIN (GPOINTER_TO_UINT (user_data), MAX_INDENT);
|
||||
const GstTagList *tags;
|
||||
GList *subentries;
|
||||
gint64 start, stop;
|
||||
|
||||
gst_toc_entry_get_start_stop (entry, &start, &stop);
|
||||
gst_toc_entry_get_start_stop_times (entry, &start, &stop);
|
||||
|
||||
PRINT ("%s%s:", &spc[MAX_INDENT - indent],
|
||||
gst_toc_entry_type_get_nick (entry->type));
|
||||
gst_toc_entry_type_get_nick (gst_toc_entry_get_entry_type (entry)));
|
||||
if (GST_CLOCK_TIME_IS_VALID (start)) {
|
||||
PRINT (" start: %" GST_TIME_FORMAT, GST_TIME_ARGS (start));
|
||||
}
|
||||
|
@ -484,12 +486,13 @@ print_toc_entry (gpointer data, gpointer user_data)
|
|||
indent += 2;
|
||||
|
||||
/* print tags */
|
||||
gst_tag_list_foreach (entry->tags, print_tag_foreach,
|
||||
GUINT_TO_POINTER (indent));
|
||||
tags = gst_toc_entry_get_tags (entry);
|
||||
if (tags)
|
||||
gst_tag_list_foreach (tags, print_tag_foreach, GUINT_TO_POINTER (indent));
|
||||
|
||||
/* loop over sub-toc entries */
|
||||
g_list_foreach (entry->subentries, print_toc_entry,
|
||||
GUINT_TO_POINTER (indent));
|
||||
subentries = gst_toc_entry_get_sub_entries (entry);
|
||||
g_list_foreach (subentries, print_toc_entry, GUINT_TO_POINTER (indent));
|
||||
}
|
||||
|
||||
#ifndef DISABLE_FAULT_HANDLER
|
||||
|
@ -669,7 +672,8 @@ event_loop (GstElement * pipeline, gboolean blocking, GstState target_state)
|
|||
break;
|
||||
case GST_MESSAGE_TOC:
|
||||
if (toc) {
|
||||
GstToc *toc_msg;
|
||||
GstToc *toc;
|
||||
GList *entries;
|
||||
gboolean updated;
|
||||
|
||||
if (GST_IS_ELEMENT (GST_MESSAGE_SRC (message))) {
|
||||
|
@ -682,11 +686,11 @@ event_loop (GstElement * pipeline, gboolean blocking, GstState target_state)
|
|||
PRINT (_("FOUND TOC\n"));
|
||||
}
|
||||
|
||||
gst_message_parse_toc (message, &toc_msg, &updated);
|
||||
gst_message_parse_toc (message, &toc, &updated);
|
||||
/* recursively loop over toc entries */
|
||||
g_list_foreach (toc_msg->entries, print_toc_entry,
|
||||
GUINT_TO_POINTER (0));
|
||||
gst_toc_unref (toc_msg);
|
||||
entries = gst_toc_get_entries (toc);
|
||||
g_list_foreach (entries, print_toc_entry, GUINT_TO_POINTER (0));
|
||||
gst_toc_unref (toc);
|
||||
}
|
||||
break;
|
||||
case GST_MESSAGE_INFO:{
|
||||
|
|
|
@ -56,8 +56,8 @@ EXPORTS
|
|||
gst_base_sink_set_sync
|
||||
gst_base_sink_set_throttle_time
|
||||
gst_base_sink_set_ts_offset
|
||||
gst_base_sink_wait
|
||||
gst_base_sink_wait_clock
|
||||
gst_base_sink_wait_eos
|
||||
gst_base_sink_wait_preroll
|
||||
gst_base_src_get_blocksize
|
||||
gst_base_src_get_do_timestamp
|
||||
|
|
|
@ -4,9 +4,6 @@ EXPORTS
|
|||
gst_net_address_meta_get_info
|
||||
gst_net_client_clock_get_type
|
||||
gst_net_client_clock_new
|
||||
gst_net_time_packet_copy
|
||||
gst_net_time_packet_free
|
||||
gst_net_time_packet_get_type
|
||||
gst_net_time_packet_new
|
||||
gst_net_time_packet_receive
|
||||
gst_net_time_packet_send
|
||||
|
|
|
@ -1133,19 +1133,29 @@ EXPORTS
|
|||
gst_task_start
|
||||
gst_task_state_get_type
|
||||
gst_task_stop
|
||||
gst_toc_append_entry
|
||||
gst_toc_entry_append_sub_entry
|
||||
gst_toc_entry_get_entry_type
|
||||
gst_toc_entry_get_start_stop
|
||||
gst_toc_entry_get_start_stop_times
|
||||
gst_toc_entry_get_sub_entries
|
||||
gst_toc_entry_get_tags
|
||||
gst_toc_entry_get_type
|
||||
gst_toc_entry_get_uid
|
||||
gst_toc_entry_is_alternative
|
||||
gst_toc_entry_is_sequence
|
||||
gst_toc_entry_merge_tags
|
||||
gst_toc_entry_new
|
||||
gst_toc_entry_new_with_pad
|
||||
gst_toc_entry_set_start_stop
|
||||
gst_toc_entry_set_start_stop_times
|
||||
gst_toc_entry_set_tags
|
||||
gst_toc_entry_type_get_nick
|
||||
gst_toc_entry_type_get_type
|
||||
gst_toc_find_entry
|
||||
gst_toc_get_entries
|
||||
gst_toc_get_tags
|
||||
gst_toc_get_type
|
||||
gst_toc_merge_tags
|
||||
gst_toc_new
|
||||
gst_toc_set_tags
|
||||
gst_toc_setter_get_toc
|
||||
gst_toc_setter_get_type
|
||||
gst_toc_setter_reset
|
||||
|
|
Loading…
Reference in a new issue