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,
163 _("location"), _("Origin of media as a URI (location, where the "
164 "original of the file or stream is hosted)"),
165 gst_tag_merge_strings_with_comma);
166 gst_tag_register (GST_TAG_HOMEPAGE, GST_TAG_FLAG_META,
169 _("Homepage for this media (i.e. artist or movie homepage)"),
170 gst_tag_merge_strings_with_comma);
171 gst_tag_register (GST_TAG_DESCRIPTION, GST_TAG_FLAG_META, G_TYPE_STRING,
172 _("description"), _("short text describing the content of the data"),
173 gst_tag_merge_strings_with_comma);
174 gst_tag_register (GST_TAG_VERSION, GST_TAG_FLAG_META, G_TYPE_STRING,
175 _("version"), _("version of this data"), NULL);
176 gst_tag_register (GST_TAG_ISRC, GST_TAG_FLAG_META, G_TYPE_STRING, _("ISRC"),
178 ("International Standard Recording Code - see http://www.ifpi.org/isrc/"),
180 /* FIXME: organization (fix what? tpm) */
181 gst_tag_register (GST_TAG_ORGANIZATION, GST_TAG_FLAG_META, G_TYPE_STRING,
182 _("organization"), _("organization"), gst_tag_merge_strings_with_comma);
183 gst_tag_register (GST_TAG_COPYRIGHT, GST_TAG_FLAG_META,
184 G_TYPE_STRING, _("copyright"), _("copyright notice of the data"), NULL);
185 gst_tag_register (GST_TAG_COPYRIGHT_URI, GST_TAG_FLAG_META,
186 G_TYPE_STRING, _("copyright uri"),
187 _("URI to the copyright notice of the data"), NULL);
188 gst_tag_register (GST_TAG_CONTACT, GST_TAG_FLAG_META,
190 _("contact"), _("contact information"), gst_tag_merge_strings_with_comma);
191 gst_tag_register (GST_TAG_LICENSE, GST_TAG_FLAG_META,
192 G_TYPE_STRING, _("license"), _("license of data"), NULL);
193 gst_tag_register (GST_TAG_LICENSE_URI, GST_TAG_FLAG_META,
194 G_TYPE_STRING, _("license uri"),
195 _("URI to the license of the data"), NULL);
196 gst_tag_register (GST_TAG_PERFORMER, GST_TAG_FLAG_META,
199 _("person(s) performing"), gst_tag_merge_strings_with_comma);
200 gst_tag_register (GST_TAG_COMPOSER, GST_TAG_FLAG_META,
203 _("person(s) who composed the recording"),
204 gst_tag_merge_strings_with_comma);
205 gst_tag_register (GST_TAG_DURATION, GST_TAG_FLAG_DECODED,
207 _("duration"), _("length in GStreamer time units (nanoseconds)"), NULL);
208 gst_tag_register (GST_TAG_CODEC, GST_TAG_FLAG_ENCODED,
211 _("codec the data is stored in"), gst_tag_merge_strings_with_comma);
212 gst_tag_register (GST_TAG_VIDEO_CODEC, GST_TAG_FLAG_ENCODED,
214 _("video codec"), _("codec the video data is stored in"), NULL);
215 gst_tag_register (GST_TAG_AUDIO_CODEC, GST_TAG_FLAG_ENCODED,
217 _("audio codec"), _("codec the audio data is stored in"), NULL);
218 gst_tag_register (GST_TAG_SUBTITLE_CODEC, GST_TAG_FLAG_ENCODED,
220 _("subtitle codec"), _("codec the subtitle data is stored in"), NULL);
221 gst_tag_register (GST_TAG_CONTAINER_FORMAT, GST_TAG_FLAG_ENCODED,
222 G_TYPE_STRING, _("container format"),
223 _("container format the data is stored in"), NULL);
224 gst_tag_register (GST_TAG_BITRATE, GST_TAG_FLAG_ENCODED,
225 G_TYPE_UINT, _("bitrate"), _("exact or average bitrate in bits/s"), NULL);
226 gst_tag_register (GST_TAG_NOMINAL_BITRATE, GST_TAG_FLAG_ENCODED,
227 G_TYPE_UINT, _("nominal bitrate"), _("nominal bitrate in bits/s"), NULL);
228 gst_tag_register (GST_TAG_MINIMUM_BITRATE, GST_TAG_FLAG_ENCODED,
229 G_TYPE_UINT, _("minimum bitrate"), _("minimum bitrate in bits/s"), NULL);
230 gst_tag_register (GST_TAG_MAXIMUM_BITRATE, GST_TAG_FLAG_ENCODED,
231 G_TYPE_UINT, _("maximum bitrate"), _("maximum bitrate in bits/s"), NULL);
232 gst_tag_register (GST_TAG_ENCODER, GST_TAG_FLAG_ENCODED,
234 _("encoder"), _("encoder used to encode this stream"), NULL);
235 gst_tag_register (GST_TAG_ENCODER_VERSION, GST_TAG_FLAG_ENCODED,
237 _("encoder version"),
238 _("version of the encoder used to encode this stream"), NULL);
239 gst_tag_register (GST_TAG_SERIAL, GST_TAG_FLAG_ENCODED,
240 G_TYPE_UINT, _("serial"), _("serial number of track"), NULL);
241 gst_tag_register (GST_TAG_TRACK_GAIN, GST_TAG_FLAG_META,
242 G_TYPE_DOUBLE, _("replaygain track gain"), _("track gain in db"), NULL);
243 gst_tag_register (GST_TAG_TRACK_PEAK, GST_TAG_FLAG_META,
244 G_TYPE_DOUBLE, _("replaygain track peak"), _("peak of the track"), NULL);
245 gst_tag_register (GST_TAG_ALBUM_GAIN, GST_TAG_FLAG_META,
246 G_TYPE_DOUBLE, _("replaygain album gain"), _("album gain in db"), NULL);
247 gst_tag_register (GST_TAG_ALBUM_PEAK, GST_TAG_FLAG_META,
248 G_TYPE_DOUBLE, _("replaygain album peak"), _("peak of the album"), NULL);
249 gst_tag_register (GST_TAG_REFERENCE_LEVEL, GST_TAG_FLAG_META,
250 G_TYPE_DOUBLE, _("replaygain reference level"),
251 _("reference level of track and album gain values"), NULL);
252 gst_tag_register (GST_TAG_LANGUAGE_CODE, GST_TAG_FLAG_META, G_TYPE_STRING,
254 _("language code for this stream, conforming to ISO-639-1"), NULL);
255 gst_tag_register (GST_TAG_IMAGE, GST_TAG_FLAG_META, GST_TYPE_BUFFER,
256 _("image"), _("image related to this stream"), gst_tag_merge_use_first);
257 gst_tag_register (GST_TAG_PREVIEW_IMAGE, GST_TAG_FLAG_META, GST_TYPE_BUFFER,
258 /* TRANSLATORS: 'preview image' = image that shows a preview of the full image */
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"), _("human readable descriptive location of where "
270 "the media has been recorded or produced"), NULL);
271 gst_tag_register (GST_TAG_GEO_LOCATION_LATITUDE, GST_TAG_FLAG_META,
272 G_TYPE_DOUBLE, _("geo location latitude"),
273 _("geo latitude location of where the media has been recorded or "
274 "produced in degrees according to WGS84 (zero at the equator, "
275 "negative values for southern latitudes)"), NULL);
276 gst_tag_register (GST_TAG_GEO_LOCATION_LONGITUDE, GST_TAG_FLAG_META,
277 G_TYPE_DOUBLE, _("geo location longitude"),
278 _("geo longitude location of where the media has been recorded or "
279 "produced in degrees according to WGS84 (zero at the prime meridian "
280 "in Greenwich/UK, negative values for western longitudes)"), NULL);
281 gst_tag_register (GST_TAG_GEO_LOCATION_ELEVATION, GST_TAG_FLAG_META,
282 G_TYPE_DOUBLE, _("geo location elevation"),
283 _("geo elevation of where the media has been recorded or produced in "
284 "meters according to WGS84 (zero is average sea level)"), NULL);
285 gst_tag_register (GST_TAG_GEO_LOCATION_COUNTRY, GST_TAG_FLAG_META,
286 G_TYPE_STRING, _("geo location country"),
287 _("country (english name) where the media has been recorded "
288 "or produced"), NULL);
289 gst_tag_register (GST_TAG_GEO_LOCATION_CITY, GST_TAG_FLAG_META,
290 G_TYPE_STRING, _("geo location city"),
291 _("city (english name) where the media has been recorded "
292 "or produced"), NULL);
293 gst_tag_register (GST_TAG_GEO_LOCATION_SUBLOCATION, GST_TAG_FLAG_META,
294 G_TYPE_STRING, _("geo location sublocation"),
295 _("a location whithin a city where the media has been produced "
296 "or created (e.g. the neighborhood)"), NULL);
297 gst_tag_register (GST_TAG_SHOW_NAME, GST_TAG_FLAG_META, G_TYPE_STRING,
298 /* TRANSLATORS: 'show name' = 'TV/radio/podcast show name' here */
300 _("Name of the tv/podcast/series show the media is from"),
301 gst_tag_merge_strings_with_comma);
302 gst_tag_register (GST_TAG_SHOW_SORTNAME, GST_TAG_FLAG_META, G_TYPE_STRING,
303 /* TRANSLATORS: 'show sortname' = 'TV/radio/podcast show name as used for sorting purposes' here */
305 _("Name of the tv/podcast/series show the media is from, for sorting "
307 gst_tag_register (GST_TAG_SHOW_EPISODE_NUMBER, GST_TAG_FLAG_META, G_TYPE_UINT,
309 _("The episode number in the season the media is part of"),
310 gst_tag_merge_use_first);
311 gst_tag_register (GST_TAG_SHOW_SEASON_NUMBER, GST_TAG_FLAG_META, G_TYPE_UINT,
313 _("The season number of the show the media is part of"),
314 gst_tag_merge_use_first);
315 gst_tag_register (GST_TAG_LYRICS, GST_TAG_FLAG_META, G_TYPE_STRING,
316 _("lyrics"), _("The lyrics of the media, commonly used for songs"),
317 gst_tag_merge_strings_with_comma);
318 gst_tag_register (GST_TAG_COMPOSER_SORTNAME, GST_TAG_FLAG_META, G_TYPE_STRING,
319 _("composer sortname"),
320 _("person(s) who composed the recording, for sorting purposes"), NULL);
321 gst_tag_register (GST_TAG_GROUPING, GST_TAG_FLAG_META, G_TYPE_STRING,
323 _("Groups related media that spans multiple tracks, like the different "
324 "pieces of a concerto. It is a higher level than a track, "
325 "but lower than an album"), NULL);
326 gst_tag_register (GST_TAG_USER_RATING, GST_TAG_FLAG_META, G_TYPE_UINT,
328 _("Rating attributed by a user. The higher the rank, "
329 "the more the user likes this media"), NULL);
333 * gst_tag_merge_use_first:
334 * @dest: uninitialized GValue to store result in
335 * @src: GValue to copy from
337 * This is a convenience function for the func argument of gst_tag_register().
338 * It creates a copy of the first value from the list.
341 gst_tag_merge_use_first (GValue * dest, const GValue * src)
343 const GValue *ret = gst_value_list_get_value (src, 0);
345 g_value_init (dest, G_VALUE_TYPE (ret));
346 g_value_copy (ret, dest);
350 * gst_tag_merge_strings_with_comma:
351 * @dest: uninitialized GValue to store result in
352 * @src: GValue to copy from
354 * This is a convenience function for the func argument of gst_tag_register().
355 * It concatenates all given strings using a comma. The tag must be registered
356 * as a G_TYPE_STRING or this function will fail.
359 gst_tag_merge_strings_with_comma (GValue * dest, const GValue * src)
364 count = gst_value_list_get_size (src);
365 str = g_string_new (g_value_get_string (gst_value_list_get_value (src, 0)));
366 for (i = 1; i < count; i++) {
367 /* seperator between two string */
368 str = g_string_append (str, _(", "));
370 g_string_append (str, g_value_get_string (gst_value_list_get_value (src,
374 g_value_init (dest, G_TYPE_STRING);
375 g_value_take_string (dest, str->str);
376 g_string_free (str, FALSE);
380 gst_tag_lookup (GQuark entry)
385 ret = g_hash_table_lookup (__tags, GUINT_TO_POINTER (entry));
393 * @name: the name or identifier string
394 * @flag: a flag describing the type of tag info
395 * @type: the type this data is in
396 * @nick: human-readable name
397 * @blurb: a human-readable description about this tag
398 * @func: function for merging multiple values of this tag, or NULL
400 * Registers a new tag type for the use with GStreamer's type system. If a type
401 * with that name is already registered, that one is used.
402 * The old registration may have used a different type however. So don't rely
403 * on your supplied values.
405 * Important: if you do not supply a merge function the implication will be
406 * that there can only be one single value for this tag in a tag list and
407 * any additional values will silenty be discarded when being added (unless
408 * #GST_TAG_MERGE_REPLACE, #GST_TAG_MERGE_REPLACE_ALL, or
409 * #GST_TAG_MERGE_PREPEND is used as merge mode, in which case the new
410 * value will replace the old one in the list).
412 * The merge function will be called from gst_tag_list_copy_value() when
413 * it is required that one or more values for a tag be condensed into
414 * one single value. This may happen from gst_tag_list_get_string(),
415 * gst_tag_list_get_int(), gst_tag_list_get_double() etc. What will happen
416 * exactly in that case depends on how the tag was registered and if a
417 * merge function was supplied and if so which one.
419 * Two default merge functions are provided: gst_tag_merge_use_first() and
420 * gst_tag_merge_strings_with_comma().
423 gst_tag_register (const gchar * name, GstTagFlag flag, GType type,
424 const gchar * nick, const gchar * blurb, GstTagMergeFunc func)
429 g_return_if_fail (name != NULL);
430 g_return_if_fail (nick != NULL);
431 g_return_if_fail (blurb != NULL);
432 g_return_if_fail (type != 0 && type != GST_TYPE_LIST);
434 key = g_quark_from_string (name);
435 info = gst_tag_lookup (key);
438 g_return_if_fail (info->type == type);
442 info = g_new (GstTagInfo, 1);
445 info->nick = g_strdup (nick);
446 info->blurb = g_strdup (blurb);
447 info->merge_func = func;
450 g_hash_table_insert (__tags, GUINT_TO_POINTER (key), info);
456 * @tag: name of the tag
458 * Checks if the given type is already registered.
460 * Returns: TRUE if the type is already registered
463 gst_tag_exists (const gchar * tag)
465 g_return_val_if_fail (tag != NULL, FALSE);
467 return gst_tag_lookup (g_quark_from_string (tag)) != NULL;
474 * Gets the #GType used for this tag.
476 * Returns: the #GType of this tag
479 gst_tag_get_type (const gchar * tag)
483 g_return_val_if_fail (tag != NULL, 0);
484 info = gst_tag_lookup (g_quark_from_string (tag));
485 g_return_val_if_fail (info != NULL, 0);
494 * Returns the human-readable name of this tag, You must not change or free
497 * Returns: the human-readable name of this tag
500 gst_tag_get_nick (const gchar * tag)
504 g_return_val_if_fail (tag != NULL, NULL);
505 info = gst_tag_lookup (g_quark_from_string (tag));
506 g_return_val_if_fail (info != NULL, NULL);
512 * gst_tag_get_description:
515 * Returns the human-readable description of this tag, You must not change or
518 * Returns: the human-readable description of this tag
521 gst_tag_get_description (const gchar * tag)
525 g_return_val_if_fail (tag != NULL, NULL);
526 info = gst_tag_lookup (g_quark_from_string (tag));
527 g_return_val_if_fail (info != NULL, NULL);
536 * Gets the flag of @tag.
538 * Returns: the flag of this tag.
541 gst_tag_get_flag (const gchar * tag)
545 g_return_val_if_fail (tag != NULL, GST_TAG_FLAG_UNDEFINED);
546 info = gst_tag_lookup (g_quark_from_string (tag));
547 g_return_val_if_fail (info != NULL, GST_TAG_FLAG_UNDEFINED);
556 * Checks if the given tag is fixed. A fixed tag can only contain one value.
557 * Unfixed tags can contain lists of values.
559 * Returns: TRUE, if the given tag is fixed.
562 gst_tag_is_fixed (const gchar * tag)
566 g_return_val_if_fail (tag != NULL, FALSE);
567 info = gst_tag_lookup (g_quark_from_string (tag));
568 g_return_val_if_fail (info != NULL, FALSE);
570 return info->merge_func == NULL;
576 * Creates a new empty GstTagList.
578 * Returns: An empty tag list
581 gst_tag_list_new (void)
583 return GST_TAG_LIST (gst_structure_id_empty_new (GST_QUARK (TAGLIST)));
587 * gst_tag_list_new_full:
589 * @...: NULL-terminated list of values to set
591 * Creates a new taglist and appends the values for the given tags. It expects
592 * tag-value pairs like gst_tag_list_add(), and a NULL terminator after the
593 * last pair. The type of the values is implicit and is documented in the API
594 * reference, but can also be queried at runtime with gst_tag_get_type(). It
595 * is an error to pass a value of a type not matching the tag type into this
596 * function. The tag list will make copies of any arguments passed
597 * (e.g. strings, buffers).
599 * Returns: a new #GstTagList. Free with gst_tag_list_free() when no longer
604 /* FIXME 0.11: rename gst_tag_list_new_full to _new and _new to _new_empty */
606 gst_tag_list_new_full (const gchar * tag, ...)
611 g_return_val_if_fail (tag != NULL, NULL);
613 list = gst_tag_list_new ();
614 va_start (args, tag);
615 gst_tag_list_add_valist (list, GST_TAG_MERGE_APPEND, tag, args);
622 * gst_tag_list_new_full_valist:
623 * @var_args: tag / value pairs to set
625 * Just like gst_tag_list_new_full(), only that it takes a va_list argument.
626 * Useful mostly for language bindings.
628 * Returns: a new #GstTagList. Free with gst_tag_list_free() when no longer
634 gst_tag_list_new_full_valist (va_list var_args)
639 list = gst_tag_list_new ();
641 tag = va_arg (var_args, gchar *);
642 gst_tag_list_add_valist (list, GST_TAG_MERGE_APPEND, tag, var_args);
648 * gst_tag_list_is_empty:
649 * @list: A #GstTagList.
651 * Checks if the given taglist is empty.
653 * Returns: TRUE if the taglist is empty, otherwise FALSE.
658 gst_tag_list_is_empty (const GstTagList * list)
660 g_return_val_if_fail (list != NULL, FALSE);
661 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
663 return (gst_structure_n_fields ((GstStructure *) list) == 0);
668 * @p: Object that might be a taglist
670 * Checks if the given pointer is a taglist.
672 * Returns: TRUE, if the given pointer is a taglist
675 gst_is_tag_list (gconstpointer p)
677 GstStructure *s = (GstStructure *) p;
679 g_return_val_if_fail (p != NULL, FALSE);
681 return (GST_IS_STRUCTURE (s) && s->name == GST_QUARK (TAGLIST));
687 GstTagMergeMode mode;
692 gst_tag_list_add_value_internal (GstStructure * list, GstTagMergeMode mode,
693 GQuark tag, const GValue * value, GstTagInfo * info)
695 const GValue *value2;
698 info = gst_tag_lookup (tag);
699 if (G_UNLIKELY (info == NULL)) {
700 g_warning ("unknown tag '%s'", g_quark_to_string (tag));
706 && (value2 = gst_structure_id_get_value (list, tag)) != NULL) {
707 GValue dest = { 0, };
710 case GST_TAG_MERGE_REPLACE_ALL:
711 case GST_TAG_MERGE_REPLACE:
712 gst_structure_id_set_value (list, tag, value);
714 case GST_TAG_MERGE_PREPEND:
715 gst_value_list_concat (&dest, value, value2);
716 gst_structure_id_set_value (list, tag, &dest);
717 g_value_unset (&dest);
719 case GST_TAG_MERGE_APPEND:
720 gst_value_list_concat (&dest, value2, value);
721 gst_structure_id_set_value (list, tag, &dest);
722 g_value_unset (&dest);
724 case GST_TAG_MERGE_KEEP:
725 case GST_TAG_MERGE_KEEP_ALL:
728 g_assert_not_reached ();
733 case GST_TAG_MERGE_APPEND:
734 case GST_TAG_MERGE_KEEP:
735 if (gst_structure_id_get_value (list, tag) != NULL)
738 case GST_TAG_MERGE_REPLACE_ALL:
739 case GST_TAG_MERGE_REPLACE:
740 case GST_TAG_MERGE_PREPEND:
741 gst_structure_id_set_value (list, tag, value);
743 case GST_TAG_MERGE_KEEP_ALL:
746 g_assert_not_reached ();
753 gst_tag_list_copy_foreach (GQuark tag, const GValue * value, gpointer user_data)
755 GstTagCopyData *copy = (GstTagCopyData *) user_data;
757 gst_tag_list_add_value_internal (copy->list, copy->mode, tag, value, NULL);
763 * gst_tag_list_insert:
764 * @into: list to merge into
765 * @from: list to merge from
766 * @mode: the mode to use
768 * Inserts the tags of the @from list into the first list using the given mode.
771 gst_tag_list_insert (GstTagList * into, const GstTagList * from,
772 GstTagMergeMode mode)
776 g_return_if_fail (GST_IS_TAG_LIST (into));
777 g_return_if_fail (GST_IS_TAG_LIST (from));
778 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
780 data.list = (GstStructure *) into;
782 if (mode == GST_TAG_MERGE_REPLACE_ALL) {
783 gst_structure_remove_all_fields (data.list);
785 gst_structure_foreach ((GstStructure *) from, gst_tag_list_copy_foreach,
791 * @list: list to copy
793 * Copies a given #GstTagList.
795 * Returns: copy of the given list
798 gst_tag_list_copy (const GstTagList * list)
800 g_return_val_if_fail (GST_IS_TAG_LIST (list), NULL);
802 return GST_TAG_LIST (gst_structure_copy ((GstStructure *) list));
806 * gst_tag_list_merge:
807 * @list1: first list to merge
808 * @list2: second list to merge
809 * @mode: the mode to use
811 * Merges the two given lists into a new list. If one of the lists is NULL, a
812 * copy of the other is returned. If both lists are NULL, NULL is returned.
814 * Returns: the new list
817 gst_tag_list_merge (const GstTagList * list1, const GstTagList * list2,
818 GstTagMergeMode mode)
820 GstTagList *list1_cp;
821 const GstTagList *list2_cp;
823 g_return_val_if_fail (list1 == NULL || GST_IS_TAG_LIST (list1), NULL);
824 g_return_val_if_fail (list2 == NULL || GST_IS_TAG_LIST (list2), NULL);
825 g_return_val_if_fail (GST_TAG_MODE_IS_VALID (mode), NULL);
827 /* nothing to merge */
828 if (!list1 && !list2) {
832 /* create empty list, we need to do this to correctly handling merge modes */
833 list1_cp = (list1) ? gst_tag_list_copy (list1) : gst_tag_list_new ();
834 list2_cp = (list2) ? list2 : gst_tag_list_new ();
836 gst_tag_list_insert (list1_cp, list2_cp, mode);
839 gst_tag_list_free ((GstTagList *) list2_cp);
846 * @list: the list to free
848 * Frees the given list and all associated values.
851 gst_tag_list_free (GstTagList * list)
853 g_return_if_fail (GST_IS_TAG_LIST (list));
854 gst_structure_free ((GstStructure *) list);
858 * gst_tag_list_get_tag_size:
860 * @tag: the tag to query
862 * Checks how many value are stored in this tag list for the given tag.
864 * Returns: The number of tags stored
867 gst_tag_list_get_tag_size (const GstTagList * list, const gchar * tag)
871 g_return_val_if_fail (GST_IS_TAG_LIST (list), 0);
873 value = gst_structure_get_value ((GstStructure *) list, tag);
876 if (G_VALUE_TYPE (value) != GST_TYPE_LIST)
879 return gst_value_list_get_size (value);
884 * @list: list to set tags in
885 * @mode: the mode to use
887 * @...: NULL-terminated list of values to set
889 * Sets the values for the given tags using the specified mode.
892 gst_tag_list_add (GstTagList * list, GstTagMergeMode mode, const gchar * tag,
897 g_return_if_fail (GST_IS_TAG_LIST (list));
898 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
899 g_return_if_fail (tag != NULL);
901 va_start (args, tag);
902 gst_tag_list_add_valist (list, mode, tag, args);
907 * gst_tag_list_add_values:
908 * @list: list to set tags in
909 * @mode: the mode to use
911 * @...: GValues to set
913 * Sets the GValues for the given tags using the specified mode.
916 gst_tag_list_add_values (GstTagList * list, GstTagMergeMode mode,
917 const gchar * tag, ...)
921 g_return_if_fail (GST_IS_TAG_LIST (list));
922 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
923 g_return_if_fail (tag != NULL);
925 va_start (args, tag);
926 gst_tag_list_add_valist_values (list, mode, tag, args);
931 * gst_tag_list_add_valist:
932 * @list: list to set tags in
933 * @mode: the mode to use
935 * @var_args: tag / value pairs to set
937 * Sets the values for the given tags using the specified mode.
940 gst_tag_list_add_valist (GstTagList * list, GstTagMergeMode mode,
941 const gchar * tag, va_list var_args)
947 g_return_if_fail (GST_IS_TAG_LIST (list));
948 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
949 g_return_if_fail (tag != NULL);
951 if (mode == GST_TAG_MERGE_REPLACE_ALL) {
952 gst_structure_remove_all_fields (list);
955 while (tag != NULL) {
956 GValue value = { 0, };
958 quark = g_quark_from_string (tag);
959 info = gst_tag_lookup (quark);
960 if (G_UNLIKELY (info == NULL)) {
961 g_warning ("unknown tag '%s'", tag);
964 #if GLIB_CHECK_VERSION(2,23,3)
965 G_VALUE_COLLECT_INIT (&value, info->type, var_args, 0, &error);
967 g_value_init (&value, info->type);
968 G_VALUE_COLLECT (&value, var_args, 0, &error);
971 g_warning ("%s: %s", G_STRLOC, error);
973 /* we purposely leak the value here, it might not be
974 * in a sane state if an error condition occoured
978 gst_tag_list_add_value_internal (list, mode, quark, &value, info);
979 g_value_unset (&value);
980 tag = va_arg (var_args, gchar *);
985 * gst_tag_list_add_valist_values:
986 * @list: list to set tags in
987 * @mode: the mode to use
989 * @var_args: tag / GValue pairs to set
991 * Sets the GValues for the given tags using the specified mode.
994 gst_tag_list_add_valist_values (GstTagList * list, GstTagMergeMode mode,
995 const gchar * tag, va_list var_args)
999 g_return_if_fail (GST_IS_TAG_LIST (list));
1000 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
1001 g_return_if_fail (tag != NULL);
1003 if (mode == GST_TAG_MERGE_REPLACE_ALL) {
1004 gst_structure_remove_all_fields (list);
1007 while (tag != NULL) {
1008 quark = g_quark_from_string (tag);
1009 g_return_if_fail (gst_tag_lookup (quark) != NULL);
1010 gst_tag_list_add_value_internal (list, mode, quark, va_arg (var_args,
1012 tag = va_arg (var_args, gchar *);
1017 * gst_tag_list_add_value:
1018 * @list: list to set tags in
1019 * @mode: the mode to use
1021 * @value: GValue for this tag
1023 * Sets the GValue for a given tag using the specified mode.
1028 gst_tag_list_add_value (GstTagList * list, GstTagMergeMode mode,
1029 const gchar * tag, const GValue * value)
1031 g_return_if_fail (GST_IS_TAG_LIST (list));
1032 g_return_if_fail (GST_TAG_MODE_IS_VALID (mode));
1033 g_return_if_fail (tag != NULL);
1035 gst_tag_list_add_value_internal (list, mode, g_quark_from_string (tag),
1040 * gst_tag_list_remove_tag:
1041 * @list: list to remove tag from
1042 * @tag: tag to remove
1044 * Removes the given tag from the taglist.
1047 gst_tag_list_remove_tag (GstTagList * list, const gchar * tag)
1049 g_return_if_fail (GST_IS_TAG_LIST (list));
1050 g_return_if_fail (tag != NULL);
1052 gst_structure_remove_field ((GstStructure *) list, tag);
1057 GstTagForeachFunc func;
1058 const GstTagList *tag_list;
1064 structure_foreach_wrapper (GQuark field_id, const GValue * value,
1067 TagForeachData *data = (TagForeachData *) user_data;
1069 data->func (data->tag_list, g_quark_to_string (field_id), data->data);
1074 * gst_tag_list_foreach:
1075 * @list: list to iterate over
1076 * @func: function to be called for each tag
1077 * @user_data: user specified data
1079 * Calls the given function for each tag inside the tag list. Note that if there
1080 * is no tag, the function won't be called at all.
1083 gst_tag_list_foreach (const GstTagList * list, GstTagForeachFunc func,
1086 TagForeachData data;
1088 g_return_if_fail (GST_IS_TAG_LIST (list));
1089 g_return_if_fail (func != NULL);
1092 data.tag_list = list;
1093 data.data = user_data;
1094 gst_structure_foreach ((GstStructure *) list, structure_foreach_wrapper,
1099 * gst_tag_list_get_value_index:
1100 * @list: a #GstTagList
1101 * @tag: tag to read out
1102 * @index: number of entry to read out
1104 * Gets the value that is at the given index for the given tag in the given
1107 * Returns: The GValue for the specified entry or NULL if the tag wasn't
1108 * available or the tag doesn't have as many entries
1110 G_CONST_RETURN GValue *
1111 gst_tag_list_get_value_index (const GstTagList * list, const gchar * tag,
1114 const GValue *value;
1116 g_return_val_if_fail (GST_IS_TAG_LIST (list), NULL);
1117 g_return_val_if_fail (tag != NULL, NULL);
1119 value = gst_structure_get_value ((GstStructure *) list, tag);
1123 if (GST_VALUE_HOLDS_LIST (value)) {
1124 if (index >= gst_value_list_get_size (value))
1126 return gst_value_list_get_value (value, index);
1135 * gst_tag_list_copy_value:
1136 * @dest: uninitialized #GValue to copy into
1137 * @list: list to get the tag from
1138 * @tag: tag to read out
1140 * Copies the contents for the given tag into the value,
1141 * merging multiple values into one if multiple values are associated
1143 * You must g_value_unset() the value after use.
1145 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1149 gst_tag_list_copy_value (GValue * dest, const GstTagList * list,
1154 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1155 g_return_val_if_fail (tag != NULL, FALSE);
1156 g_return_val_if_fail (dest != NULL, FALSE);
1157 g_return_val_if_fail (G_VALUE_TYPE (dest) == 0, FALSE);
1159 src = gst_structure_get_value ((GstStructure *) list, tag);
1163 if (G_VALUE_TYPE (src) == GST_TYPE_LIST) {
1164 GstTagInfo *info = gst_tag_lookup (g_quark_from_string (tag));
1169 /* must be there or lists aren't allowed */
1170 g_assert (info->merge_func);
1171 info->merge_func (dest, src);
1173 g_value_init (dest, G_VALUE_TYPE (src));
1174 g_value_copy (src, dest);
1179 /* FIXME 0.11: this whole merge function business is overdesigned, and the
1180 * _get_foo() API is misleading as well - how many application developers will
1181 * expect gst_tag_list_get_string (list, GST_TAG_ARTIST, &val) might return a
1182 * string with multiple comma-separated artists? _get_foo() should just be
1183 * a convenience wrapper around _get_foo_index (list, tag, 0, &val),
1184 * supplemented by a special _tag_list_get_string_merged() function if needed
1185 * (unless someone can actually think of real use cases where the merge
1186 * function is not 'use first' for non-strings and merge for strings) */
1188 /***** evil macros to get all the gst_tag_list_get_*() functions right *****/
1190 #define TAG_MERGE_FUNCS(name,type,ret) \
1192 gst_tag_list_get_ ## name (const GstTagList *list, const gchar *tag, \
1195 GValue v = { 0, }; \
1197 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE); \
1198 g_return_val_if_fail (tag != NULL, FALSE); \
1199 g_return_val_if_fail (value != NULL, FALSE); \
1201 if (!gst_tag_list_copy_value (&v, list, tag)) \
1203 *value = COPY_FUNC (g_value_get_ ## name (&v)); \
1204 g_value_unset (&v); \
1209 gst_tag_list_get_ ## name ## _index (const GstTagList *list, \
1211 guint index, type *value) \
1215 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE); \
1216 g_return_val_if_fail (tag != NULL, FALSE); \
1217 g_return_val_if_fail (value != NULL, FALSE); \
1219 if ((v = gst_tag_list_get_value_index (list, tag, index)) == NULL) \
1221 *value = COPY_FUNC (g_value_get_ ## name (v)); \
1225 /* FIXME 0.11: maybe get rid of _get_char*(), _get_uchar*(), _get_long*(),
1226 * _get_ulong*() and _get_pointer*()? - they are not really useful/common
1227 * enough to warrant convenience accessor functions */
1229 #define COPY_FUNC /**/
1231 * gst_tag_list_get_char:
1232 * @list: a #GstTagList to get the tag from
1233 * @tag: tag to read out
1234 * @value: location for the result
1236 * Copies the contents for the given tag into the value, merging multiple values
1237 * into one if multiple values are associated with the tag.
1239 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1243 * gst_tag_list_get_char_index:
1244 * @list: a #GstTagList to get the tag from
1245 * @tag: tag to read out
1246 * @index: number of entry to read out
1247 * @value: location for the result
1249 * Gets the value that is at the given index for the given tag in the given
1252 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1255 TAG_MERGE_FUNCS (char, gchar, TRUE)
1257 * gst_tag_list_get_uchar:
1258 * @list: a #GstTagList to get the tag from
1259 * @tag: tag to read out
1260 * @value: location for the result
1262 * Copies the contents for the given tag into the value, merging multiple values
1263 * into one if multiple values are associated with the tag.
1265 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1269 * gst_tag_list_get_uchar_index:
1270 * @list: a #GstTagList to get the tag from
1271 * @tag: tag to read out
1272 * @index: number of entry to read out
1273 * @value: location for the result
1275 * Gets the value that is at the given index for the given tag in the given
1278 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1281 TAG_MERGE_FUNCS (uchar, guchar, TRUE)
1283 * gst_tag_list_get_boolean:
1284 * @list: a #GstTagList to get the tag from
1285 * @tag: tag to read out
1286 * @value: location for the result
1288 * Copies the contents for the given tag into the value, merging multiple values
1289 * into one if multiple values are associated with the tag.
1291 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1295 * gst_tag_list_get_boolean_index:
1296 * @list: a #GstTagList to get the tag from
1297 * @tag: tag to read out
1298 * @index: number of entry to read out
1299 * @value: location for the result
1301 * Gets the value that is at the given index for the given tag in the given
1304 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1307 TAG_MERGE_FUNCS (boolean, gboolean, TRUE)
1309 * gst_tag_list_get_int:
1310 * @list: a #GstTagList to get the tag from
1311 * @tag: tag to read out
1312 * @value: location for the result
1314 * Copies the contents for the given tag into the value, merging multiple values
1315 * into one if multiple values are associated with the tag.
1317 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1321 * gst_tag_list_get_int_index:
1322 * @list: a #GstTagList to get the tag from
1323 * @tag: tag to read out
1324 * @index: number of entry to read out
1325 * @value: location for the result
1327 * Gets the value that is at the given index for the given tag in the given
1330 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1333 TAG_MERGE_FUNCS (int, gint, TRUE)
1335 * gst_tag_list_get_uint:
1336 * @list: a #GstTagList to get the tag from
1337 * @tag: tag to read out
1338 * @value: location for the result
1340 * Copies the contents for the given tag into the value, merging multiple values
1341 * into one if multiple values are associated with the tag.
1343 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1347 * gst_tag_list_get_uint_index:
1348 * @list: a #GstTagList to get the tag from
1349 * @tag: tag to read out
1350 * @index: number of entry to read out
1351 * @value: location for the result
1353 * Gets the value that is at the given index for the given tag in the given
1356 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1359 TAG_MERGE_FUNCS (uint, guint, TRUE)
1361 * gst_tag_list_get_long:
1362 * @list: a #GstTagList to get the tag from
1363 * @tag: tag to read out
1364 * @value: location for the result
1366 * Copies the contents for the given tag into the value, merging multiple values
1367 * into one if multiple values are associated with the tag.
1369 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1373 * gst_tag_list_get_long_index:
1374 * @list: a #GstTagList to get the tag from
1375 * @tag: tag to read out
1376 * @index: number of entry to read out
1377 * @value: location for the result
1379 * Gets the value that is at the given index for the given tag in the given
1382 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1385 TAG_MERGE_FUNCS (long, glong, TRUE)
1387 * gst_tag_list_get_ulong:
1388 * @list: a #GstTagList to get the tag from
1389 * @tag: tag to read out
1390 * @value: location for the result
1392 * Copies the contents for the given tag into the value, merging multiple values
1393 * into one if multiple values are associated with the tag.
1395 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1399 * gst_tag_list_get_ulong_index:
1400 * @list: a #GstTagList to get the tag from
1401 * @tag: tag to read out
1402 * @index: number of entry to read out
1403 * @value: location for the result
1405 * Gets the value that is at the given index for the given tag in the given
1408 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1411 TAG_MERGE_FUNCS (ulong, gulong, TRUE)
1413 * gst_tag_list_get_int64:
1414 * @list: a #GstTagList to get the tag from
1415 * @tag: tag to read out
1416 * @value: location for the result
1418 * Copies the contents for the given tag into the value, merging multiple values
1419 * into one if multiple values are associated with the tag.
1421 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1425 * gst_tag_list_get_int64_index:
1426 * @list: a #GstTagList to get the tag from
1427 * @tag: tag to read out
1428 * @index: number of entry to read out
1429 * @value: location for the result
1431 * Gets the value that is at the given index for the given tag in the given
1434 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1437 TAG_MERGE_FUNCS (int64, gint64, TRUE)
1439 * gst_tag_list_get_uint64:
1440 * @list: a #GstTagList to get the tag from
1441 * @tag: tag to read out
1442 * @value: location for the result
1444 * Copies the contents for the given tag into the value, merging multiple values
1445 * into one if multiple values are associated with the tag.
1447 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1451 * gst_tag_list_get_uint64_index:
1452 * @list: a #GstTagList to get the tag from
1453 * @tag: tag to read out
1454 * @index: number of entry to read out
1455 * @value: location for the result
1457 * Gets the value that is at the given index for the given tag in the given
1460 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1463 TAG_MERGE_FUNCS (uint64, guint64, TRUE)
1465 * gst_tag_list_get_float:
1466 * @list: a #GstTagList to get the tag from
1467 * @tag: tag to read out
1468 * @value: location for the result
1470 * Copies the contents for the given tag into the value, merging multiple values
1471 * into one if multiple values are associated with the tag.
1473 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1477 * gst_tag_list_get_float_index:
1478 * @list: a #GstTagList to get the tag from
1479 * @tag: tag to read out
1480 * @index: number of entry to read out
1481 * @value: location for the result
1483 * Gets the value that is at the given index for the given tag in the given
1486 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1489 TAG_MERGE_FUNCS (float, gfloat, TRUE)
1491 * gst_tag_list_get_double:
1492 * @list: a #GstTagList to get the tag from
1493 * @tag: tag to read out
1494 * @value: location for the result
1496 * Copies the contents for the given tag into the value, merging multiple values
1497 * into one if multiple values are associated with the tag.
1499 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1503 * gst_tag_list_get_double_index:
1504 * @list: a #GstTagList to get the tag from
1505 * @tag: tag to read out
1506 * @index: number of entry to read out
1507 * @value: location for the result
1509 * Gets the value that is at the given index for the given tag in the given
1512 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1515 TAG_MERGE_FUNCS (double, gdouble, TRUE)
1517 * gst_tag_list_get_pointer:
1518 * @list: a #GstTagList to get the tag from
1519 * @tag: tag to read out
1520 * @value: location for the result
1522 * Copies the contents for the given tag into the value, merging multiple values
1523 * into one if multiple values are associated with the tag.
1525 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1529 * gst_tag_list_get_pointer_index:
1530 * @list: a #GstTagList to get the tag from
1531 * @tag: tag to read out
1532 * @index: number of entry to read out
1533 * @value: location for the result
1535 * Gets the value that is at the given index for the given tag in the given
1538 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1541 TAG_MERGE_FUNCS (pointer, gpointer, (*value != NULL))
1543 #define COPY_FUNC g_strdup
1545 * gst_tag_list_get_string:
1546 * @list: a #GstTagList to get the tag from
1547 * @tag: tag to read out
1548 * @value: location for the result
1550 * Copies the contents for the given tag into the value, possibly merging
1551 * multiple values into one if multiple values are associated with the tag.
1553 * Use gst_tag_list_get_string_index (list, tag, 0, value) if you want
1554 * to retrieve the first string associated with this tag unmodified.
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
1564 * gst_tag_list_get_string_index:
1565 * @list: a #GstTagList to get the tag from
1566 * @tag: tag to read out
1567 * @index: number of entry to read out
1568 * @value: location for the result
1570 * Gets the value that is at the given index for the given tag in the given
1573 * The resulting string in @value will be in UTF-8 encoding and should be
1574 * freed by the caller using g_free when no longer needed. Since 0.10.24 the
1575 * returned string is also guaranteed to be non-NULL and non-empty.
1577 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1580 TAG_MERGE_FUNCS (string, gchar *, (*value != NULL && **value != '\0'))
1583 * gst_tag_list_get_date:
1584 * @list: a #GstTagList to get the tag from
1585 * @tag: tag to read out
1586 * @value: address of a GDate pointer variable to store the result into
1588 * Copies the first date for the given tag in the taglist into the variable
1589 * pointed to by @value. Free the date with g_date_free() when it is no longer
1592 * Returns: TRUE, if a date was copied, FALSE if the tag didn't exist in the
1593 * given list or if it was #NULL.
1596 gst_tag_list_get_date (const GstTagList * list, const gchar * tag,
1601 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1602 g_return_val_if_fail (tag != NULL, FALSE);
1603 g_return_val_if_fail (value != NULL, FALSE);
1605 if (!gst_tag_list_copy_value (&v, list, tag))
1607 *value = (GDate *) g_value_dup_boxed (&v);
1609 return (*value != NULL);
1613 * gst_tag_list_get_date_index:
1614 * @list: a #GstTagList to get the tag from
1615 * @tag: tag to read out
1616 * @index: number of entry to read out
1617 * @value: location for the result
1619 * Gets the date that is at the given index for the given tag in the given
1620 * list and copies it into the variable pointed to by @value. Free the date
1621 * with g_date_free() when it is no longer needed.
1623 * Returns: TRUE, if a value was copied, FALSE if the tag didn't exist in the
1624 * given list or if it was #NULL.
1627 gst_tag_list_get_date_index (const GstTagList * list,
1628 const gchar * tag, guint index, GDate ** value)
1632 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1633 g_return_val_if_fail (tag != NULL, FALSE);
1634 g_return_val_if_fail (value != NULL, FALSE);
1636 if ((v = gst_tag_list_get_value_index (list, tag, index)) == NULL)
1638 *value = (GDate *) g_value_dup_boxed (v);
1639 return (*value != NULL);
1643 * gst_tag_list_get_buffer:
1644 * @list: a #GstTagList to get the tag from
1645 * @tag: tag to read out
1646 * @value: address of a GstBuffer pointer variable to store the result into
1648 * Copies the first buffer for the given tag in the taglist into the variable
1649 * pointed to by @value. Free the buffer with gst_buffer_unref() when it is
1652 * Returns: TRUE, if a buffer was copied, FALSE if the tag didn't exist in the
1653 * given list or if it was #NULL.
1658 gst_tag_list_get_buffer (const GstTagList * list, const gchar * tag,
1663 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1664 g_return_val_if_fail (tag != NULL, FALSE);
1665 g_return_val_if_fail (value != NULL, FALSE);
1667 if (!gst_tag_list_copy_value (&v, list, tag))
1669 *value = (GstBuffer *) gst_value_dup_mini_object (&v);
1671 return (*value != NULL);
1675 * gst_tag_list_get_buffer_index:
1676 * @list: a #GstTagList to get the tag from
1677 * @tag: tag to read out
1678 * @index: number of entry to read out
1679 * @value: address of a GstBuffer pointer variable to store the result into
1681 * Gets the buffer that is at the given index for the given tag in the given
1682 * list and copies it into the variable pointed to by @value. Free the buffer
1683 * with gst_buffer_unref() when it is no longer needed.
1685 * Returns: TRUE, if a buffer was copied, FALSE if the tag didn't exist in the
1686 * given list or if it was #NULL.
1691 gst_tag_list_get_buffer_index (const GstTagList * list,
1692 const gchar * tag, guint index, GstBuffer ** value)
1696 g_return_val_if_fail (GST_IS_TAG_LIST (list), FALSE);
1697 g_return_val_if_fail (tag != NULL, FALSE);
1698 g_return_val_if_fail (value != NULL, FALSE);
1700 if ((v = gst_tag_list_get_value_index (list, tag, index)) == NULL)
1702 *value = (GstBuffer *) gst_value_dup_mini_object (v);
1703 return (*value != NULL);