2 * Copyright (C) 2003 Benjamin Otte <in7y118@public.uni-hamburg.de>
4 * gsttaglist.c: tag support (aka metadata)
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Library General Public
8 * License as published by the Free Software Foundation; either
9 * version 2 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Library General Public License for more details.
16 * You should have received a copy of the GNU Library General Public
17 * License along with this library; if not, write to the
18 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
19 * Boston, MA 02111-1307, USA.
24 * @short_description: List of tags and values used to describe media metadata
26 * List of tags and values used to describe media metadata.
28 * Strings must be in ASCII or UTF-8 encoding. No other encodings are allowed.
30 * Last reviewed on 2009-06-09 (0.10.23)
37 #include "gst_private.h"
38 #include "gst-i18n-lib.h"
39 #include "gsttaglist.h"
42 #include "gstbuffer.h"
45 #include <gobject/gvaluecollector.h>
48 #define GST_TAG_IS_VALID(tag) (gst_tag_get_info (tag) != NULL)
50 /* FIXME 0.11: use GParamSpecs or something similar for tag registrations,
51 * possibly even gst_tag_register(). Especially value ranges might be
52 * useful for some tags. */
56 GType type; /* type the data is in */
58 gchar *nick; /* translated name */
59 gchar *blurb; /* translated description of type */
61 GstTagMergeFunc merge_func; /* functions to merge the values */
62 GstTagFlag flag; /* type of tag */
66 static GMutex *__tag_mutex;
68 static GHashTable *__tags;
70 #define TAG_LOCK g_mutex_lock (__tag_mutex)
71 #define TAG_UNLOCK g_mutex_unlock (__tag_mutex)
74 gst_tag_list_get_type (void)
76 static GType _gst_tag_list_type = 0;
78 if (G_UNLIKELY (_gst_tag_list_type == 0)) {
79 _gst_tag_list_type = g_boxed_type_register_static ("GstTagList",
80 (GBoxedCopyFunc) gst_tag_list_copy, (GBoxedFreeFunc) gst_tag_list_free);
83 g_value_register_transform_func (_gst_tag_list_type, G_TYPE_STRING,
84 _gst_structure_transform_to_string);
88 return _gst_tag_list_type;
92 _gst_tag_initialize (void)
94 __tag_mutex = g_mutex_new ();
95 __tags = g_hash_table_new (g_direct_hash, g_direct_equal);
96 gst_tag_register (GST_TAG_TITLE, GST_TAG_FLAG_META,
98 _("title"), _("commonly used title"), gst_tag_merge_strings_with_comma);
99 gst_tag_register (GST_TAG_TITLE_SORTNAME, GST_TAG_FLAG_META,
101 _("title sortname"), _("commonly used title for sorting purposes"), NULL);
102 gst_tag_register (GST_TAG_ARTIST, GST_TAG_FLAG_META,
105 _("person(s) responsible for the recording"),
106 gst_tag_merge_strings_with_comma);
107 gst_tag_register (GST_TAG_ARTIST_SORTNAME, GST_TAG_FLAG_META,
109 _("artist sortname"),
110 _("person(s) responsible for the recording for sorting purposes"), NULL);
111 gst_tag_register (GST_TAG_ALBUM, GST_TAG_FLAG_META,
114 _("album containing this data"), gst_tag_merge_strings_with_comma);
115 gst_tag_register (GST_TAG_ALBUM_SORTNAME, GST_TAG_FLAG_META,
118 _("album containing this data for sorting purposes"), NULL);
119 gst_tag_register (GST_TAG_ALBUM_ARTIST, GST_TAG_FLAG_META,
122 _("The artist of the entire album, as it should be displayed"),
123 gst_tag_merge_strings_with_comma);
124 gst_tag_register (GST_TAG_ALBUM_ARTIST_SORTNAME, GST_TAG_FLAG_META,
126 _("album artist sortname"),
127 _("The artist of the entire album, as it should be sorted"), NULL);
128 gst_tag_register (GST_TAG_DATE, GST_TAG_FLAG_META, GST_TYPE_DATE,
129 _("date"), _("date the data was created (as a GDate structure)"), NULL);
130 gst_tag_register (GST_TAG_GENRE, GST_TAG_FLAG_META,
133 _("genre this data belongs to"), gst_tag_merge_strings_with_comma);
134 gst_tag_register (GST_TAG_COMMENT, GST_TAG_FLAG_META,
137 _("free text commenting the data"), gst_tag_merge_use_first);
138 gst_tag_register (GST_TAG_EXTENDED_COMMENT, GST_TAG_FLAG_META,
140 _("extended comment"),
141 _("free text commenting the data in key=value or key[en]=comment form"),
142 gst_tag_merge_use_first);
143 gst_tag_register (GST_TAG_TRACK_NUMBER, GST_TAG_FLAG_META,
146 _("track number inside a collection"), gst_tag_merge_use_first);
147 gst_tag_register (GST_TAG_TRACK_COUNT, GST_TAG_FLAG_META,
150 _("count of tracks inside collection this track belongs to"),
151 gst_tag_merge_use_first);
152 gst_tag_register (GST_TAG_ALBUM_VOLUME_NUMBER, GST_TAG_FLAG_META,
155 _("disc number inside a collection"), gst_tag_merge_use_first);
156 gst_tag_register (GST_TAG_ALBUM_VOLUME_COUNT, GST_TAG_FLAG_META,
159 _("count of discs inside collection this disc belongs to"),
160 gst_tag_merge_use_first);
161 gst_tag_register (GST_TAG_LOCATION, GST_TAG_FLAG_META,
165 ("Origin of media as a URI (location, where the original of the file or stream is hosted)"),
166 gst_tag_merge_strings_with_comma);
167 gst_tag_register (GST_TAG_HOMEPAGE, GST_TAG_FLAG_META,
171 ("Homepage for this media (i.e. artist or movie homepage)"),
172 gst_tag_merge_strings_with_comma);
173 gst_tag_register (GST_TAG_DESCRIPTION, GST_TAG_FLAG_META, G_TYPE_STRING,
174 _("description"), _("short text describing the content of the data"),
175 gst_tag_merge_strings_with_comma);
176 gst_tag_register (GST_TAG_VERSION, GST_TAG_FLAG_META, G_TYPE_STRING,
177 _("version"), _("version of this data"), NULL);
178 gst_tag_register (GST_TAG_ISRC, GST_TAG_FLAG_META, G_TYPE_STRING, _("ISRC"),
180 ("International Standard Recording Code - see http://www.ifpi.org/isrc/"),
182 gst_tag_register (GST_TAG_ORGANIZATION, GST_TAG_FLAG_META, G_TYPE_STRING, _("organization"), _("organization"), /* FIXME */
183 gst_tag_merge_strings_with_comma);
184 gst_tag_register (GST_TAG_COPYRIGHT, GST_TAG_FLAG_META,
185 G_TYPE_STRING, _("copyright"), _("copyright notice of the data"), NULL);
186 gst_tag_register (GST_TAG_COPYRIGHT_URI, GST_TAG_FLAG_META,
187 G_TYPE_STRING, _("copyright uri"),
188 _("URI to the copyright notice of the data"), NULL);
189 gst_tag_register (GST_TAG_CONTACT, GST_TAG_FLAG_META,
191 _("contact"), _("contact information"), gst_tag_merge_strings_with_comma);
192 gst_tag_register (GST_TAG_LICENSE, GST_TAG_FLAG_META,
193 G_TYPE_STRING, _("license"), _("license of data"), NULL);
194 gst_tag_register (GST_TAG_LICENSE_URI, GST_TAG_FLAG_META,
195 G_TYPE_STRING, _("license uri"),
196 _("URI to the license of the data"), NULL);
197 gst_tag_register (GST_TAG_PERFORMER, GST_TAG_FLAG_META,
200 _("person(s) performing"), gst_tag_merge_strings_with_comma);
201 gst_tag_register (GST_TAG_COMPOSER, GST_TAG_FLAG_META,
204 _("person(s) who composed the recording"),
205 gst_tag_merge_strings_with_comma);
206 gst_tag_register (GST_TAG_DURATION, GST_TAG_FLAG_DECODED,
208 _("duration"), _("length in GStreamer time units (nanoseconds)"), NULL);
209 gst_tag_register (GST_TAG_CODEC, GST_TAG_FLAG_ENCODED,
212 _("codec the data is stored in"), gst_tag_merge_strings_with_comma);
213 gst_tag_register (GST_TAG_VIDEO_CODEC, GST_TAG_FLAG_ENCODED,
215 _("video codec"), _("codec the video data is stored in"), NULL);
216 gst_tag_register (GST_TAG_AUDIO_CODEC, GST_TAG_FLAG_ENCODED,
218 _("audio codec"), _("codec the audio data is stored in"), NULL);
219 gst_tag_register (GST_TAG_SUBTITLE_CODEC, GST_TAG_FLAG_ENCODED,
221 _("subtitle codec"), _("codec the subtitle data is stored in"), NULL);
222 gst_tag_register (GST_TAG_CONTAINER_FORMAT, GST_TAG_FLAG_ENCODED,
223 G_TYPE_STRING, _("container format"),
224 _("container format the data is stored in"), NULL);
225 gst_tag_register (GST_TAG_BITRATE, GST_TAG_FLAG_ENCODED,
226 G_TYPE_UINT, _("bitrate"), _("exact or average bitrate in bits/s"), NULL);
227 gst_tag_register (GST_TAG_NOMINAL_BITRATE, GST_TAG_FLAG_ENCODED,
228 G_TYPE_UINT, _("nominal bitrate"), _("nominal bitrate in bits/s"), NULL);
229 gst_tag_register (GST_TAG_MINIMUM_BITRATE, GST_TAG_FLAG_ENCODED,
230 G_TYPE_UINT, _("minimum bitrate"), _("minimum bitrate in bits/s"), NULL);
231 gst_tag_register (GST_TAG_MAXIMUM_BITRATE, GST_TAG_FLAG_ENCODED,
232 G_TYPE_UINT, _("maximum bitrate"), _("maximum bitrate in bits/s"), NULL);
233 gst_tag_register (GST_TAG_ENCODER, GST_TAG_FLAG_ENCODED,
235 _("encoder"), _("encoder used to encode this stream"), NULL);
236 gst_tag_register (GST_TAG_ENCODER_VERSION, GST_TAG_FLAG_ENCODED,
238 _("encoder version"),
239 _("version of the encoder used to encode this stream"), NULL);
240 gst_tag_register (GST_TAG_SERIAL, GST_TAG_FLAG_ENCODED,
241 G_TYPE_UINT, _("serial"), _("serial number of track"), NULL);
242 gst_tag_register (GST_TAG_TRACK_GAIN, GST_TAG_FLAG_META,
243 G_TYPE_DOUBLE, _("replaygain track gain"), _("track gain in db"), NULL);
244 gst_tag_register (GST_TAG_TRACK_PEAK, GST_TAG_FLAG_META,
245 G_TYPE_DOUBLE, _("replaygain track peak"), _("peak of the track"), NULL);
246 gst_tag_register (GST_TAG_ALBUM_GAIN, GST_TAG_FLAG_META,
247 G_TYPE_DOUBLE, _("replaygain album gain"), _("album gain in db"), NULL);
248 gst_tag_register (GST_TAG_ALBUM_PEAK, GST_TAG_FLAG_META,
249 G_TYPE_DOUBLE, _("replaygain album peak"), _("peak of the album"), NULL);
250 gst_tag_register (GST_TAG_REFERENCE_LEVEL, GST_TAG_FLAG_META,
251 G_TYPE_DOUBLE, _("replaygain reference level"),
252 _("reference level of track and album gain values"), NULL);
253 gst_tag_register (GST_TAG_LANGUAGE_CODE, GST_TAG_FLAG_META, G_TYPE_STRING,
255 _("language code for this stream, conforming to ISO-639-1"), NULL);
256 gst_tag_register (GST_TAG_IMAGE, GST_TAG_FLAG_META, GST_TYPE_BUFFER,
257 _("image"), _("image related to this stream"), gst_tag_merge_use_first);
258 gst_tag_register (GST_TAG_PREVIEW_IMAGE, GST_TAG_FLAG_META, GST_TYPE_BUFFER,
259 _("preview image"), _("preview image related to this stream"), NULL);
260 gst_tag_register (GST_TAG_ATTACHMENT, GST_TAG_FLAG_META, GST_TYPE_BUFFER,
261 _("attachment"), _("file attached to this stream"),
262 gst_tag_merge_use_first);
263 gst_tag_register (GST_TAG_BEATS_PER_MINUTE, GST_TAG_FLAG_META, G_TYPE_DOUBLE,
264 _("beats per minute"), _("number of beats per minute in audio"), NULL);
265 gst_tag_register (GST_TAG_KEYWORDS, GST_TAG_FLAG_META, G_TYPE_STRING,
266 _("keywords"), _("comma separated keywords describing the content"),
267 gst_tag_merge_strings_with_comma);
268 gst_tag_register (GST_TAG_GEO_LOCATION_NAME, GST_TAG_FLAG_META, G_TYPE_STRING,
269 _("geo location name"),
271 ("human readable descriptive location of where the media has been recorded or produced"),
273 gst_tag_register (GST_TAG_GEO_LOCATION_LATITUDE, GST_TAG_FLAG_META,
274 G_TYPE_DOUBLE, _("geo location latitude"),
276 ("geo latitude location of where the media has been recorded or produced in degrees according to WGS84 (zero at the equator, negative values for southern latitudes)"),
278 gst_tag_register (GST_TAG_GEO_LOCATION_LONGITUDE, GST_TAG_FLAG_META,
279 G_TYPE_DOUBLE, _("geo location longitude"),
281 ("geo longitude location of where the media has been recorded or produced in degrees according to WGS84 (zero at the prime meridian in Greenwich/UK, negative values for western longitudes)"),
283 gst_tag_register (GST_TAG_GEO_LOCATION_ELEVATION, GST_TAG_FLAG_META,
284 G_TYPE_DOUBLE, _("geo location elevation"),
286 ("geo elevation of where the media has been recorded or produced in meters according to WGS84 (zero is average sea level)"),
288 gst_tag_register (GST_TAG_SHOW_NAME, GST_TAG_FLAG_META, G_TYPE_STRING,
290 _("Name of the tv/podcast/series show the media is from"),
291 gst_tag_merge_strings_with_comma);
292 gst_tag_register (GST_TAG_SHOW_SORTNAME, GST_TAG_FLAG_META, G_TYPE_STRING,
294 _("Name of the tv/podcast/series show the media is from, for sorting "
296 gst_tag_register (GST_TAG_SHOW_EPISODE_NUMBER, GST_TAG_FLAG_META, G_TYPE_UINT,
298 _("The episode number in the season the media is part of"),
299 gst_tag_merge_use_first);
300 gst_tag_register (GST_TAG_SHOW_SEASON_NUMBER, GST_TAG_FLAG_META, G_TYPE_UINT,
302 _("The season number of the show the media is part of"),
303 gst_tag_merge_use_first);
304 gst_tag_register (GST_TAG_LYRICS, GST_TAG_FLAG_META, G_TYPE_STRING,
305 _("lyrics"), _("The lyrics of the media, commonly used for songs"),
306 gst_tag_merge_strings_with_comma);
307 gst_tag_register (GST_TAG_COMPOSER_SORTNAME, GST_TAG_FLAG_META, G_TYPE_STRING,
308 _("composer sortname"),
309 _("person(s) who composed the recording, for sorting purposes"), NULL);
310 gst_tag_register (GST_TAG_GROUPING, GST_TAG_FLAG_META, G_TYPE_STRING,
312 _("Groups related media that spans multiple tracks, like the different "
313 "pieces of a concerto. It is a higher level than a track, "
314 "but lower than an album"), NULL);
318 * gst_tag_merge_use_first:
319 * @dest: uninitialized GValue to store result in
320 * @src: GValue to copy from
322 * This is a convenience function for the func argument of gst_tag_register().
323 * It creates a copy of the first value from the list.
326 gst_tag_merge_use_first (GValue * dest, const GValue * src)
328 const GValue *ret = gst_value_list_get_value (src, 0);
330 g_value_init (dest, G_VALUE_TYPE (ret));
331 g_value_copy (ret, dest);
335 * gst_tag_merge_strings_with_comma:
336 * @dest: uninitialized GValue to store result in
337 * @src: GValue to copy from
339 * This is a convenience function for the func argument of gst_tag_register().
340 * It concatenates all given strings using a comma. The tag must be registered
341 * as a G_TYPE_STRING or this function will fail.
344 gst_tag_merge_strings_with_comma (GValue * dest, const GValue * src)
350 count = gst_value_list_get_size (src);
351 str = g_string_new (g_value_get_string (gst_value_list_get_value (src, 0)));
352 for (i = 1; i < count; i++) {
353 /* seperator between two string */
354 str = g_string_append (str, _(", "));
356 g_string_append (str, g_value_get_string (gst_value_list_get_value (src,
360 g_value_init (dest, G_TYPE_STRING);
361 g_value_take_string (dest, str->str);
362 g_string_free (str, FALSE);
366 gst_tag_lookup (GQuark entry)
371 ret = g_hash_table_lookup (__tags, GUINT_TO_POINTER (entry));
379 * @name: the name or identifier string
380 * @flag: a flag describing the type of tag info
381 * @type: the type this data is in
382 * @nick: human-readable name
383 * @blurb: a human-readable description about this tag
384 * @func: function for merging multiple values of this tag, or NULL
386 * Registers a new tag type for the use with GStreamer's type system. If a type
387 * with that name is already registered, that one is used.
388 * The old registration may have used a different type however. So don't rely
389 * on your supplied values.
391 * Important: if you do not supply a merge function the implication will be
392 * that there can only be one single value for this tag in a tag list and
393 * any additional values will silenty be discarded when being added (unless
394 * #GST_TAG_MERGE_REPLACE, #GST_TAG_MERGE_REPLACE_ALL, or
395 * #GST_TAG_MERGE_PREPEND is used as merge mode, in which case the new
396 * value will replace the old one in the list).
398 * The merge function will be called from gst_tag_list_copy_value() when
399 * it is required that one or more values for a tag be condensed into
400 * one single value. This may happen from gst_tag_list_get_string(),
401 * gst_tag_list_get_int(), gst_tag_list_get_double() etc. What will happen
402 * exactly in that case depends on how the tag was registered and if a
403 * merge function was supplied and if so which one.
405 * Two default merge functions are provided: gst_tag_merge_use_first() and
406 * gst_tag_merge_strings_with_comma().
409 gst_tag_register (const gchar * name, GstTagFlag flag, GType type,
410 const gchar * nick, const gchar * blurb, GstTagMergeFunc func)
416 g_return_if_fail (name != NULL);
417 g_return_if_fail (nick != NULL);
418 g_return_if_fail (blurb != NULL);
419 g_return_if_fail (type != 0 && type != GST_TYPE_LIST);
421 key = g_quark_from_string (name);
422 info = gst_tag_lookup (key);
425 g_return_if_fail (info->type == type);
429 info = g_new (GstTagInfo, 1);
432 info->nick = g_strdup (nick);
433 info->blurb = g_strdup (blurb);
434 info->merge_func = func;
437 g_hash_table_insert (__tags, GUINT_TO_POINTER (key), info);
443 * @tag: name of the tag
445 * Checks if the given type is already registered.
447 * Returns: TRUE if the type is already registered
450 gst_tag_exists (const gchar * tag)
452 g_return_val_if_fail (tag != NULL, FALSE);
454 return gst_tag_lookup (g_quark_from_string (tag)) != NULL;
461 * Gets the #GType used for this tag.
463 * Returns: the #GType of this tag
466 gst_tag_get_type (const gchar * tag)
470 g_return_val_if_fail (tag != NULL, 0);
471 info = gst_tag_lookup (g_quark_from_string (tag));
472 g_return_val_if_fail (info != NULL, 0);
481 * Returns the human-readable name of this tag, You must not change or free
484 * Returns: the human-readable name of this tag
487 gst_tag_get_nick (const gchar * tag)
491 g_return_val_if_fail (tag != NULL, NULL);
492 info = gst_tag_lookup (g_quark_from_string (tag));
493 g_return_val_if_fail (info != NULL, NULL);
499 * gst_tag_get_description:
502 * Returns the human-readable description of this tag, You must not change or
505 * Returns: the human-readable description of this tag
508 gst_tag_get_description (const gchar * tag)
512 g_return_val_if_fail (tag != NULL, NULL);
513 info = gst_tag_lookup (g_quark_from_string (tag));
514 g_return_val_if_fail (info != NULL, NULL);
523 * Gets the flag of @tag.
525 * Returns: the flag of this tag.
528 gst_tag_get_flag (const gchar * tag)
532 g_return_val_if_fail (tag != NULL, GST_TAG_FLAG_UNDEFINED);
533 info = gst_tag_lookup (g_quark_from_string (tag));
534 g_return_val_if_fail (info != NULL, GST_TAG_FLAG_UNDEFINED);
543 * Checks if the given tag is fixed. A fixed tag can only contain one value.
544 * Unfixed tags can contain lists of values.
546 * Returns: TRUE, if the given tag is fixed.
549 gst_tag_is_fixed (const gchar * tag)
553 g_return_val_if_fail (tag != NULL, FALSE);
554 info = gst_tag_lookup (g_quark_from_string (tag));
555 g_return_val_if_fail (info != NULL, FALSE);
557 return info->merge_func == NULL;
563 * Creates a new empty GstTagList.
565 * Returns: An empty tag list
568 gst_tag_list_new (void)
570 return GST_TAG_LIST (gst_structure_id_empty_new (GST_QUARK (TAGLIST)));
574 * gst_tag_list_new_full:
576 * @...: NULL-terminated list of values to set
578 * Creates a new taglist and appends the values for the given tags. It expects
579 * tag-value pairs like gst_tag_list_add(), and a NULL terminator after the
580 * last pair. The type of the values is implicit and is documented in the API
581 * reference, but can also be queried at runtime with gst_tag_get_type(). It
582 * is an error to pass a value of a type not matching the tag type into this
583 * function. The tag list will make copies of any arguments passed
584 * (e.g. strings, buffers).
586 * Returns: a new #GstTagList. Free with gst_tag_list_free() when no longer
591 /* FIXME 0.11: rename gst_tag_list_new_full to _new and _new to _new_empty */
593 gst_tag_list_new_full (const gchar * tag, ...)
598 g_return_val_if_fail (tag != NULL, NULL);
600 list = gst_tag_list_new ();
601 va_start (args, tag);
602 gst_tag_list_add_valist (list, GST_TAG_MERGE_APPEND, tag, args);
609 * gst_tag_list_new_full_valist:
610 * @var_args: tag / value pairs to set
612 * Just like gst_tag_list_new_full(), only that it takes a va_list argument.
613 * Useful mostly for language bindings.
615 * Returns: a new #GstTagList. Free with gst_tag_list_free() when no longer
621 gst_tag_list_new_full_valist (va_list var_args)
626 list = gst_tag_list_new ();
628 tag = va_arg (var_args, gchar *);
629 gst_tag_list_add_valist (list, GST_TAG_MERGE_APPEND, tag, var_args);
635 * gst_tag_list_is_empty:
636 * @list: A #GstTagList.
638 * Checks if the given taglist is empty.
640 * Returns: TRUE if the taglist is empty, otherwise FALSE.
645 gst_tag_list_is_empty (const GstTagList * list)
647 g_return_val_if_fail (list != NULL, FALSE);
648 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
650 return (gst_structure_n_fields ((GstStructure *) list) == 0);
655 * @p: Object that might be a taglist
657 * Checks if the given pointer is a taglist.
659 * Returns: TRUE, if the given pointer is a taglist
662 gst_is_tag_list (gconstpointer p)
664 GstStructure *s = (GstStructure *) p;
666 g_return_val_if_fail (p != NULL, FALSE);
668 return (GST_IS_STRUCTURE (s) && s->name == GST_QUARK (TAGLIST));
674 GstTagMergeMode mode;
679 gst_tag_list_add_value_internal (GstStructure * list, GstTagMergeMode mode,
680 GQuark tag, const GValue * value, GstTagInfo * info)
682 const GValue *value2;
685 info = gst_tag_lookup (tag);
686 if (G_UNLIKELY (info == NULL)) {
687 g_warning ("unknown tag '%s'", g_quark_to_string (tag));
693 && (value2 = gst_structure_id_get_value (list, tag)) != NULL) {
694 GValue dest = { 0, };
697 case GST_TAG_MERGE_REPLACE_ALL:
698 case GST_TAG_MERGE_REPLACE:
699 gst_structure_id_set_value (list, tag, value);
701 case GST_TAG_MERGE_PREPEND:
702 gst_value_list_concat (&dest, value, value2);
703 gst_structure_id_set_value (list, tag, &dest);
704 g_value_unset (&dest);
706 case GST_TAG_MERGE_APPEND:
707 gst_value_list_concat (&dest, value2, value);
708 gst_structure_id_set_value (list, tag, &dest);
709 g_value_unset (&dest);
711 case GST_TAG_MERGE_KEEP:
712 case GST_TAG_MERGE_KEEP_ALL:
715 g_assert_not_reached ();
720 case GST_TAG_MERGE_APPEND:
721 case GST_TAG_MERGE_KEEP:
722 if (gst_structure_id_get_value (list, tag) != NULL)
725 case GST_TAG_MERGE_REPLACE_ALL:
726 case GST_TAG_MERGE_REPLACE:
727 case GST_TAG_MERGE_PREPEND:
728 gst_structure_id_set_value (list, tag, value);
730 case GST_TAG_MERGE_KEEP_ALL:
733 g_assert_not_reached ();
740 gst_tag_list_copy_foreach (GQuark tag, const GValue * value, gpointer user_data)
742 GstTagCopyData *copy = (GstTagCopyData *) user_data;
744 gst_tag_list_add_value_internal (copy->list, copy->mode, tag, value, NULL);
750 * gst_tag_list_insert:
751 * @into: list to merge into
752 * @from: list to merge from
753 * @mode: the mode to use
755 * Inserts the tags of the @from list into the first list using the given mode.
758 gst_tag_list_insert (GstTagList * into, const GstTagList * from,
759 GstTagMergeMode mode)
763 g_return_if_fail (GST_IS_TAG_LIST (into));
764 g_return_if_fail (GST_IS_TAG_LIST (from));
765 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
767 data.list = (GstStructure *) into;
769 if (mode == GST_TAG_MERGE_REPLACE_ALL) {
770 gst_structure_remove_all_fields (data.list);
772 gst_structure_foreach ((GstStructure *) from, gst_tag_list_copy_foreach,
778 * @list: list to copy
780 * Copies a given #GstTagList.
782 * Returns: copy of the given list
785 gst_tag_list_copy (const GstTagList * list)
787 g_return_val_if_fail (GST_IS_TAG_LIST (list), NULL);
789 return GST_TAG_LIST (gst_structure_copy ((GstStructure *) list));
793 * gst_tag_list_merge:
794 * @list1: first list to merge
795 * @list2: second list to merge
796 * @mode: the mode to use
798 * Merges the two given lists into a new list. If one of the lists is NULL, a
799 * copy of the other is returned. If both lists are NULL, NULL is returned.
801 * Returns: the new list
804 gst_tag_list_merge (const GstTagList * list1, const GstTagList * list2,
805 GstTagMergeMode mode)
807 GstTagList *list1_cp;
808 const GstTagList *list2_cp;
810 g_return_val_if_fail (list1 == NULL || GST_IS_TAG_LIST (list1), NULL);
811 g_return_val_if_fail (list2 == NULL || GST_IS_TAG_LIST (list2), NULL);
812 g_return_val_if_fail (GST_TAG_MODE_IS_VALID (mode), NULL);
814 /* nothing to merge */
815 if (!list1 && !list2) {
819 /* create empty list, we need to do this to correctly handling merge modes */
820 list1_cp = (list1) ? gst_tag_list_copy (list1) : gst_tag_list_new ();
821 list2_cp = (list2) ? list2 : gst_tag_list_new ();
823 gst_tag_list_insert (list1_cp, list2_cp, mode);
826 gst_tag_list_free ((GstTagList *) list2_cp);
833 * @list: the list to free
835 * Frees the given list and all associated values.
838 gst_tag_list_free (GstTagList * list)
840 g_return_if_fail (GST_IS_TAG_LIST (list));
841 gst_structure_free ((GstStructure *) list);
845 * gst_tag_list_get_tag_size:
847 * @tag: the tag to query
849 * Checks how many value are stored in this tag list for the given tag.
851 * Returns: The number of tags stored
854 gst_tag_list_get_tag_size (const GstTagList * list, const gchar * tag)
858 g_return_val_if_fail (GST_IS_TAG_LIST (list), 0);
860 value = gst_structure_get_value ((GstStructure *) list, tag);
863 if (G_VALUE_TYPE (value) != GST_TYPE_LIST)
866 return gst_value_list_get_size (value);
871 * @list: list to set tags in
872 * @mode: the mode to use
874 * @...: NULL-terminated list of values to set
876 * Sets the values for the given tags using the specified mode.
879 gst_tag_list_add (GstTagList * list, GstTagMergeMode mode, const gchar * tag,
884 g_return_if_fail (GST_IS_TAG_LIST (list));
885 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
886 g_return_if_fail (tag != NULL);
888 va_start (args, tag);
889 gst_tag_list_add_valist (list, mode, tag, args);
894 * gst_tag_list_add_values:
895 * @list: list to set tags in
896 * @mode: the mode to use
898 * @...: GValues to set
900 * Sets the GValues for the given tags using the specified mode.
903 gst_tag_list_add_values (GstTagList * list, GstTagMergeMode mode,
904 const gchar * tag, ...)
908 g_return_if_fail (GST_IS_TAG_LIST (list));
909 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
910 g_return_if_fail (tag != NULL);
912 va_start (args, tag);
913 gst_tag_list_add_valist_values (list, mode, tag, args);
918 * gst_tag_list_add_valist:
919 * @list: list to set tags in
920 * @mode: the mode to use
922 * @var_args: tag / value pairs to set
924 * Sets the values for the given tags using the specified mode.
927 gst_tag_list_add_valist (GstTagList * list, GstTagMergeMode mode,
928 const gchar * tag, va_list var_args)
934 g_return_if_fail (GST_IS_TAG_LIST (list));
935 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
936 g_return_if_fail (tag != NULL);
938 if (mode == GST_TAG_MERGE_REPLACE_ALL) {
939 gst_structure_remove_all_fields (list);
942 while (tag != NULL) {
943 GValue value = { 0, };
945 quark = g_quark_from_string (tag);
946 info = gst_tag_lookup (quark);
947 if (G_UNLIKELY (info == NULL)) {
948 g_warning ("unknown tag '%s'", tag);
951 g_value_init (&value, info->type);
952 G_VALUE_COLLECT (&value, var_args, 0, &error);
954 g_warning ("%s: %s", G_STRLOC, error);
956 /* we purposely leak the value here, it might not be
957 * in a sane state if an error condition occoured
961 gst_tag_list_add_value_internal (list, mode, quark, &value, info);
962 g_value_unset (&value);
963 tag = va_arg (var_args, gchar *);
968 * gst_tag_list_add_valist_values:
969 * @list: list to set tags in
970 * @mode: the mode to use
972 * @var_args: tag / GValue pairs to set
974 * Sets the GValues for the given tags using the specified mode.
977 gst_tag_list_add_valist_values (GstTagList * list, GstTagMergeMode mode,
978 const gchar * tag, va_list var_args)
982 g_return_if_fail (GST_IS_TAG_LIST (list));
983 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
984 g_return_if_fail (tag != NULL);
986 if (mode == GST_TAG_MERGE_REPLACE_ALL) {
987 gst_structure_remove_all_fields (list);
990 while (tag != NULL) {
991 quark = g_quark_from_string (tag);
992 g_return_if_fail (gst_tag_lookup (quark) != NULL);
993 gst_tag_list_add_value_internal (list, mode, quark, va_arg (var_args,
995 tag = va_arg (var_args, gchar *);
1000 * gst_tag_list_add_value:
1001 * @list: list to set tags in
1002 * @mode: the mode to use
1004 * @value: GValue for this tag
1006 * Sets the GValue for a given tag using the specified mode.
1011 gst_tag_list_add_value (GstTagList * list, GstTagMergeMode mode,
1012 const gchar * tag, const GValue * value)
1014 g_return_if_fail (GST_IS_TAG_LIST (list));
1015 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
1016 g_return_if_fail (tag != NULL);
1018 gst_tag_list_add_value_internal (list, mode, g_quark_from_string (tag),
1023 * gst_tag_list_remove_tag:
1024 * @list: list to remove tag from
1025 * @tag: tag to remove
1027 * Removes the given tag from the taglist.
1030 gst_tag_list_remove_tag (GstTagList * list, const gchar * tag)
1032 g_return_if_fail (GST_IS_TAG_LIST (list));
1033 g_return_if_fail (tag != NULL);
1035 gst_structure_remove_field ((GstStructure *) list, tag);
1040 GstTagForeachFunc func;
1041 const GstTagList *tag_list;
1047 structure_foreach_wrapper (GQuark field_id, const GValue * value,
1050 TagForeachData *data = (TagForeachData *) user_data;
1052 data->func (data->tag_list, g_quark_to_string (field_id), data->data);
1057 * gst_tag_list_foreach:
1058 * @list: list to iterate over
1059 * @func: function to be called for each tag
1060 * @user_data: user specified data
1062 * Calls the given function for each tag inside the tag list. Note that if there
1063 * is no tag, the function won't be called at all.
1066 gst_tag_list_foreach (const GstTagList * list, GstTagForeachFunc func,
1069 TagForeachData data;
1071 g_return_if_fail (GST_IS_TAG_LIST (list));
1072 g_return_if_fail (func != NULL);
1075 data.tag_list = list;
1076 data.data = user_data;
1077 gst_structure_foreach ((GstStructure *) list, structure_foreach_wrapper,
1082 * gst_tag_list_get_value_index:
1083 * @list: a #GstTagList
1084 * @tag: tag to read out
1085 * @index: number of entry to read out
1087 * Gets the value that is at the given index for the given tag in the given
1090 * Returns: The GValue for the specified entry or NULL if the tag wasn't
1091 * available or the tag doesn't have as many entries
1093 G_CONST_RETURN GValue *
1094 gst_tag_list_get_value_index (const GstTagList * list, const gchar * tag,
1097 const GValue *value;
1099 g_return_val_if_fail (GST_IS_TAG_LIST (list), NULL);
1100 g_return_val_if_fail (tag != NULL, NULL);
1102 value = gst_structure_get_value ((GstStructure *) list, tag);
1106 if (GST_VALUE_HOLDS_LIST (value)) {
1107 if (index >= gst_value_list_get_size (value))
1109 return gst_value_list_get_value (value, index);
1118 * gst_tag_list_copy_value:
1119 * @dest: uninitialized #GValue to copy into
1120 * @list: list to get the tag from
1121 * @tag: tag to read out
1123 * Copies the contents for the given tag into the value,
1124 * merging multiple values into one if multiple values are associated
1126 * You must g_value_unset() the value after use.
1128 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1132 gst_tag_list_copy_value (GValue * dest, const GstTagList * list,
1137 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1138 g_return_val_if_fail (tag != NULL, FALSE);
1139 g_return_val_if_fail (dest != NULL, FALSE);
1140 g_return_val_if_fail (G_VALUE_TYPE (dest) == 0, FALSE);
1142 src = gst_structure_get_value ((GstStructure *) list, tag);
1146 if (G_VALUE_TYPE (src) == GST_TYPE_LIST) {
1147 GstTagInfo *info = gst_tag_lookup (g_quark_from_string (tag));
1152 /* must be there or lists aren't allowed */
1153 g_assert (info->merge_func);
1154 info->merge_func (dest, src);
1156 g_value_init (dest, G_VALUE_TYPE (src));
1157 g_value_copy (src, dest);
1162 /* FIXME 0.11: this whole merge function business is overdesigned, and the
1163 * _get_foo() API is misleading as well - how many application developers will
1164 * expect gst_tag_list_get_string (list, GST_TAG_ARTIST, &val) might return a
1165 * string with multiple comma-separated artists? _get_foo() should just be
1166 * a convenience wrapper around _get_foo_index (list, tag, 0, &val),
1167 * supplemented by a special _tag_list_get_string_merged() function if needed
1168 * (unless someone can actually think of real use cases where the merge
1169 * function is not 'use first' for non-strings and merge for strings) */
1171 /***** evil macros to get all the gst_tag_list_get_*() functions right *****/
1173 #define TAG_MERGE_FUNCS(name,type,ret) \
1175 gst_tag_list_get_ ## name (const GstTagList *list, const gchar *tag, \
1178 GValue v = { 0, }; \
1180 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE); \
1181 g_return_val_if_fail (tag != NULL, FALSE); \
1182 g_return_val_if_fail (value != NULL, FALSE); \
1184 if (!gst_tag_list_copy_value (&v, list, tag)) \
1186 *value = COPY_FUNC (g_value_get_ ## name (&v)); \
1187 g_value_unset (&v); \
1192 gst_tag_list_get_ ## name ## _index (const GstTagList *list, \
1194 guint index, type *value) \
1198 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE); \
1199 g_return_val_if_fail (tag != NULL, FALSE); \
1200 g_return_val_if_fail (value != NULL, FALSE); \
1202 if ((v = gst_tag_list_get_value_index (list, tag, index)) == NULL) \
1204 *value = COPY_FUNC (g_value_get_ ## name (v)); \
1208 /* FIXME 0.11: maybe get rid of _get_char*(), _get_uchar*(), _get_long*(),
1209 * _get_ulong*() and _get_pointer*()? - they are not really useful/common
1210 * enough to warrant convenience accessor functions */
1212 #define COPY_FUNC /**/
1214 * gst_tag_list_get_char:
1215 * @list: a #GstTagList to get the tag from
1216 * @tag: tag to read out
1217 * @value: location for the result
1219 * Copies the contents for the given tag into the value, merging multiple values
1220 * into one if multiple values are associated with the tag.
1222 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1226 * gst_tag_list_get_char_index:
1227 * @list: a #GstTagList to get the tag from
1228 * @tag: tag to read out
1229 * @index: number of entry to read out
1230 * @value: location for the result
1232 * Gets the value that is at the given index for the given tag in the given
1235 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1238 TAG_MERGE_FUNCS (char, gchar, TRUE)
1240 * gst_tag_list_get_uchar:
1241 * @list: a #GstTagList to get the tag from
1242 * @tag: tag to read out
1243 * @value: location for the result
1245 * Copies the contents for the given tag into the value, merging multiple values
1246 * into one if multiple values are associated with the tag.
1248 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1252 * gst_tag_list_get_uchar_index:
1253 * @list: a #GstTagList to get the tag from
1254 * @tag: tag to read out
1255 * @index: number of entry to read out
1256 * @value: location for the result
1258 * Gets the value that is at the given index for the given tag in the given
1261 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1264 TAG_MERGE_FUNCS (uchar, guchar, TRUE)
1266 * gst_tag_list_get_boolean:
1267 * @list: a #GstTagList to get the tag from
1268 * @tag: tag to read out
1269 * @value: location for the result
1271 * Copies the contents for the given tag into the value, merging multiple values
1272 * into one if multiple values are associated with the tag.
1274 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1278 * gst_tag_list_get_boolean_index:
1279 * @list: a #GstTagList to get the tag from
1280 * @tag: tag to read out
1281 * @index: number of entry to read out
1282 * @value: location for the result
1284 * Gets the value that is at the given index for the given tag in the given
1287 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1290 TAG_MERGE_FUNCS (boolean, gboolean, TRUE)
1292 * gst_tag_list_get_int:
1293 * @list: a #GstTagList to get the tag from
1294 * @tag: tag to read out
1295 * @value: location for the result
1297 * Copies the contents for the given tag into the value, merging multiple values
1298 * into one if multiple values are associated with the tag.
1300 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1304 * gst_tag_list_get_int_index:
1305 * @list: a #GstTagList to get the tag from
1306 * @tag: tag to read out
1307 * @index: number of entry to read out
1308 * @value: location for the result
1310 * Gets the value that is at the given index for the given tag in the given
1313 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1316 TAG_MERGE_FUNCS (int, gint, TRUE)
1318 * gst_tag_list_get_uint:
1319 * @list: a #GstTagList to get the tag from
1320 * @tag: tag to read out
1321 * @value: location for the result
1323 * Copies the contents for the given tag into the value, merging multiple values
1324 * into one if multiple values are associated with the tag.
1326 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1330 * gst_tag_list_get_uint_index:
1331 * @list: a #GstTagList to get the tag from
1332 * @tag: tag to read out
1333 * @index: number of entry to read out
1334 * @value: location for the result
1336 * Gets the value that is at the given index for the given tag in the given
1339 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1342 TAG_MERGE_FUNCS (uint, guint, TRUE)
1344 * gst_tag_list_get_long:
1345 * @list: a #GstTagList to get the tag from
1346 * @tag: tag to read out
1347 * @value: location for the result
1349 * Copies the contents for the given tag into the value, merging multiple values
1350 * into one if multiple values are associated with the tag.
1352 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1356 * gst_tag_list_get_long_index:
1357 * @list: a #GstTagList to get the tag from
1358 * @tag: tag to read out
1359 * @index: number of entry to read out
1360 * @value: location for the result
1362 * Gets the value that is at the given index for the given tag in the given
1365 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1368 TAG_MERGE_FUNCS (long, glong, TRUE)
1370 * gst_tag_list_get_ulong:
1371 * @list: a #GstTagList to get the tag from
1372 * @tag: tag to read out
1373 * @value: location for the result
1375 * Copies the contents for the given tag into the value, merging multiple values
1376 * into one if multiple values are associated with the tag.
1378 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1382 * gst_tag_list_get_ulong_index:
1383 * @list: a #GstTagList to get the tag from
1384 * @tag: tag to read out
1385 * @index: number of entry to read out
1386 * @value: location for the result
1388 * Gets the value that is at the given index for the given tag in the given
1391 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1394 TAG_MERGE_FUNCS (ulong, gulong, TRUE)
1396 * gst_tag_list_get_int64:
1397 * @list: a #GstTagList to get the tag from
1398 * @tag: tag to read out
1399 * @value: location for the result
1401 * Copies the contents for the given tag into the value, merging multiple values
1402 * into one if multiple values are associated with the tag.
1404 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1408 * gst_tag_list_get_int64_index:
1409 * @list: a #GstTagList to get the tag from
1410 * @tag: tag to read out
1411 * @index: number of entry to read out
1412 * @value: location for the result
1414 * Gets the value that is at the given index for the given tag in the given
1417 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1420 TAG_MERGE_FUNCS (int64, gint64, TRUE)
1422 * gst_tag_list_get_uint64:
1423 * @list: a #GstTagList to get the tag from
1424 * @tag: tag to read out
1425 * @value: location for the result
1427 * Copies the contents for the given tag into the value, merging multiple values
1428 * into one if multiple values are associated with the tag.
1430 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1434 * gst_tag_list_get_uint64_index:
1435 * @list: a #GstTagList to get the tag from
1436 * @tag: tag to read out
1437 * @index: number of entry to read out
1438 * @value: location for the result
1440 * Gets the value that is at the given index for the given tag in the given
1443 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1446 TAG_MERGE_FUNCS (uint64, guint64, TRUE)
1448 * gst_tag_list_get_float:
1449 * @list: a #GstTagList to get the tag from
1450 * @tag: tag to read out
1451 * @value: location for the result
1453 * Copies the contents for the given tag into the value, merging multiple values
1454 * into one if multiple values are associated with the tag.
1456 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1460 * gst_tag_list_get_float_index:
1461 * @list: a #GstTagList to get the tag from
1462 * @tag: tag to read out
1463 * @index: number of entry to read out
1464 * @value: location for the result
1466 * Gets the value that is at the given index for the given tag in the given
1469 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1472 TAG_MERGE_FUNCS (float, gfloat, TRUE)
1474 * gst_tag_list_get_double:
1475 * @list: a #GstTagList to get the tag from
1476 * @tag: tag to read out
1477 * @value: location for the result
1479 * Copies the contents for the given tag into the value, merging multiple values
1480 * into one if multiple values are associated with the tag.
1482 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1486 * gst_tag_list_get_double_index:
1487 * @list: a #GstTagList to get the tag from
1488 * @tag: tag to read out
1489 * @index: number of entry to read out
1490 * @value: location for the result
1492 * Gets the value that is at the given index for the given tag in the given
1495 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1498 TAG_MERGE_FUNCS (double, gdouble, TRUE)
1500 * gst_tag_list_get_pointer:
1501 * @list: a #GstTagList to get the tag from
1502 * @tag: tag to read out
1503 * @value: location for the result
1505 * Copies the contents for the given tag into the value, merging multiple values
1506 * into one if multiple values are associated with the tag.
1508 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1512 * gst_tag_list_get_pointer_index:
1513 * @list: a #GstTagList to get the tag from
1514 * @tag: tag to read out
1515 * @index: number of entry to read out
1516 * @value: location for the result
1518 * Gets the value that is at the given index for the given tag in the given
1521 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1524 TAG_MERGE_FUNCS (pointer, gpointer, (*value != NULL))
1526 #define COPY_FUNC g_strdup
1528 * gst_tag_list_get_string:
1529 * @list: a #GstTagList to get the tag from
1530 * @tag: tag to read out
1531 * @value: location for the result
1533 * Copies the contents for the given tag into the value, possibly merging
1534 * multiple values into one if multiple values are associated with the tag.
1536 * Use gst_tag_list_get_string_index (list, tag, 0, value) if you want
1537 * to retrieve the first string associated with this tag unmodified.
1539 * The resulting string in @value will be in UTF-8 encoding and should be
1540 * freed by the caller using g_free when no longer needed. Since 0.10.24 the
1541 * returned string is also guaranteed to be non-NULL and non-empty.
1543 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1547 * gst_tag_list_get_string_index:
1548 * @list: a #GstTagList to get the tag from
1549 * @tag: tag to read out
1550 * @index: number of entry to read out
1551 * @value: location for the result
1553 * Gets the value that is at the given index for the given tag in the given
1556 * The resulting string in @value will be in UTF-8 encoding and should be
1557 * freed by the caller using g_free when no longer needed. Since 0.10.24 the
1558 * returned string is also guaranteed to be non-NULL and non-empty.
1560 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1563 TAG_MERGE_FUNCS (string, gchar *, (*value != NULL && **value != '\0'))
1566 * gst_tag_list_get_date:
1567 * @list: a #GstTagList to get the tag from
1568 * @tag: tag to read out
1569 * @value: address of a GDate pointer variable to store the result into
1571 * Copies the first date for the given tag in the taglist into the variable
1572 * pointed to by @value. Free the date with g_date_free() when it is no longer
1575 * Returns: TRUE, if a date was copied, FALSE if the tag didn't exist in the
1576 * given list or if it was #NULL.
1579 gst_tag_list_get_date (const GstTagList * list, const gchar * tag,
1584 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1585 g_return_val_if_fail (tag != NULL, FALSE);
1586 g_return_val_if_fail (value != NULL, FALSE);
1588 if (!gst_tag_list_copy_value (&v, list, tag))
1590 *value = (GDate *) g_value_dup_boxed (&v);
1592 return (*value != NULL);
1596 * gst_tag_list_get_date_index:
1597 * @list: a #GstTagList to get the tag from
1598 * @tag: tag to read out
1599 * @index: number of entry to read out
1600 * @value: location for the result
1602 * Gets the date that is at the given index for the given tag in the given
1603 * list and copies it into the variable pointed to by @value. Free the date
1604 * with g_date_free() when it is no longer needed.
1606 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1607 * given list or if it was #NULL.
1610 gst_tag_list_get_date_index (const GstTagList * list,
1611 const gchar * tag, guint index, GDate ** value)
1615 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1616 g_return_val_if_fail (tag != NULL, FALSE);
1617 g_return_val_if_fail (value != NULL, FALSE);
1619 if ((v = gst_tag_list_get_value_index (list, tag, index)) == NULL)
1621 *value = (GDate *) g_value_dup_boxed (v);
1622 return (*value != NULL);
1626 * gst_tag_list_get_buffer:
1627 * @list: a #GstTagList to get the tag from
1628 * @tag: tag to read out
1629 * @value: address of a GstBuffer pointer variable to store the result into
1631 * Copies the first buffer for the given tag in the taglist into the variable
1632 * pointed to by @value. Free the buffer with gst_buffer_unref() when it is
1635 * Returns: TRUE, if a buffer was copied, FALSE if the tag didn't exist in the
1636 * given list or if it was #NULL.
1641 gst_tag_list_get_buffer (const GstTagList * list, const gchar * tag,
1646 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1647 g_return_val_if_fail (tag != NULL, FALSE);
1648 g_return_val_if_fail (value != NULL, FALSE);
1650 if (!gst_tag_list_copy_value (&v, list, tag))
1652 *value = (GstBuffer *) gst_value_dup_mini_object (&v);
1654 return (*value != NULL);
1658 * gst_tag_list_get_buffer_index:
1659 * @list: a #GstTagList to get the tag from
1660 * @tag: tag to read out
1661 * @index: number of entry to read out
1662 * @value: address of a GstBuffer pointer variable to store the result into
1664 * Gets the buffer that is at the given index for the given tag in the given
1665 * list and copies it into the variable pointed to by @value. Free the buffer
1666 * with gst_buffer_unref() when it is no longer needed.
1668 * Returns: TRUE, if a buffer was copied, FALSE if the tag didn't exist in the
1669 * given list or if it was #NULL.
1674 gst_tag_list_get_buffer_index (const GstTagList * list,
1675 const gchar * tag, guint index, GstBuffer ** value)
1679 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1680 g_return_val_if_fail (tag != NULL, FALSE);
1681 g_return_val_if_fail (value != NULL, FALSE);
1683 if ((v = gst_tag_list_get_value_index (list, tag, index)) == NULL)
1685 *value = (GstBuffer *) gst_value_dup_mini_object (v);
1686 return (*value != NULL);