From 5f7cf0c4c8f80a6d20a69a54844c34a0939735d0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Dzi=C4=99giel?= Date: Thu, 18 Dec 2025 15:32:04 +0100 Subject: [PATCH] clapper: Fallback to stream tags for single stream content In cases where audio file is played, there may not be separate global tags due to only single stream. In this cases we should also use stream tags as if they were global ones, but at the same time prioritize global tags if any are available. --- src/lib/clapper/clapper-media-item-private.h | 2 +- src/lib/clapper/clapper-media-item.c | 26 ++++++++---------- src/lib/clapper/clapper-playbin-bus.c | 29 +++++++++++++++++--- src/lib/clapper/clapper-player-private.h | 1 + src/lib/clapper/clapper-player.c | 1 + 5 files changed, 39 insertions(+), 20 deletions(-) diff --git a/src/lib/clapper/clapper-media-item-private.h b/src/lib/clapper/clapper-media-item-private.h index c48467ff..1aa11b5f 100644 --- a/src/lib/clapper/clapper-media-item-private.h +++ b/src/lib/clapper/clapper-media-item-private.h @@ -28,7 +28,7 @@ G_BEGIN_DECLS G_GNUC_INTERNAL -void clapper_media_item_update_from_tag_list (ClapperMediaItem *item, const GstTagList *tags, ClapperPlayer *player); +void clapper_media_item_update_from_tag_list (ClapperMediaItem *item, const GstTagList *tags, gboolean allow_overwrite, ClapperPlayer *player); G_GNUC_INTERNAL void clapper_media_item_update_from_discoverer_info (ClapperMediaItem *self, GstDiscovererInfo *info); diff --git a/src/lib/clapper/clapper-media-item.c b/src/lib/clapper/clapper-media-item.c index 0aa128f5..a3513479 100644 --- a/src/lib/clapper/clapper-media-item.c +++ b/src/lib/clapper/clapper-media-item.c @@ -652,22 +652,18 @@ clapper_media_item_get_timeline (ClapperMediaItem *self) void clapper_media_item_update_from_tag_list (ClapperMediaItem *self, const GstTagList *tags, - ClapperPlayer *player) + gboolean allow_overwrite, ClapperPlayer *player) { - GstTagScope scope = gst_tag_list_get_scope (tags); + ClapperReactableItemUpdatedFlags flags = 0; + gboolean changed = clapper_media_item_insert_tags_internal (self, tags, player->app_bus, allow_overwrite, &flags); - if (scope == GST_TAG_SCOPE_GLOBAL) { - ClapperReactableItemUpdatedFlags flags = 0; - gboolean changed = clapper_media_item_insert_tags_internal (self, tags, player->app_bus, TRUE, &flags); + if (changed) { + ClapperFeaturesManager *features_manager; - if (changed) { - ClapperFeaturesManager *features_manager; - - if (player->reactables_manager) - clapper_reactables_manager_trigger_item_updated (player->reactables_manager, self, flags); - if ((features_manager = clapper_player_get_features_manager (player))) - clapper_features_manager_trigger_item_updated (features_manager, self); - } + if (player->reactables_manager) + clapper_reactables_manager_trigger_item_updated (player->reactables_manager, self, flags); + if ((features_manager = clapper_player_get_features_manager (player))) + clapper_features_manager_trigger_item_updated (features_manager, self); } } @@ -783,8 +779,8 @@ clapper_media_item_update_from_parsed_playlist (ClapperMediaItem *self, GListSto GST_OBJECT_LOCK (other_item); - if (other_item->tags) - clapper_media_item_update_from_tag_list (self, other_item->tags, player); + if (other_item->tags) // Tags are always GLOBAL here + clapper_media_item_update_from_tag_list (self, other_item->tags, TRUE, player); /* Since its redirect now, we have to update title to describe new file instead of * being a playlist title. If other item had parsed title, it also means that tags diff --git a/src/lib/clapper/clapper-playbin-bus.c b/src/lib/clapper/clapper-playbin-bus.c index 090f5de1..d8f998f3 100644 --- a/src/lib/clapper/clapper-playbin-bus.c +++ b/src/lib/clapper/clapper-playbin-bus.c @@ -1038,7 +1038,9 @@ _handle_tag_msg (GstMessage *msg, ClapperPlayer *player) } player->pending_tags = gst_tag_list_ref (tags); } else if (G_LIKELY (player->played_item != NULL)) { - clapper_media_item_update_from_tag_list (player->played_item, tags, player); + gboolean is_global = (gst_tag_list_get_scope (tags) == GST_TAG_SCOPE_GLOBAL); + if (is_global || player->stream_tags_allowed) + clapper_media_item_update_from_tag_list (player->played_item, tags, is_global, player); } gst_tag_list_unref (tags); @@ -1116,10 +1118,28 @@ static inline void _handle_stream_collection_msg (GstMessage *msg, ClapperPlayer *player) { GstStreamCollection *collection = NULL; + guint i, n_streams, n_video = 0, n_audio = 0, n_text = 0; GST_INFO_OBJECT (player, "Stream collection"); gst_message_parse_stream_collection (msg, &collection); + n_streams = gst_stream_collection_get_size (collection); + + for (i = 0; i < n_streams; ++i) { + GstStream *stream = gst_stream_collection_get_stream (collection, i); + GstStreamType stream_type = gst_stream_get_stream_type (stream); + + if ((stream_type & GST_STREAM_TYPE_VIDEO) == GST_STREAM_TYPE_VIDEO) + n_video++; + else if ((stream_type & GST_STREAM_TYPE_AUDIO) == GST_STREAM_TYPE_AUDIO) + n_audio++; + else if ((stream_type & GST_STREAM_TYPE_TEXT) == GST_STREAM_TYPE_TEXT) + n_text++; + } + + player->stream_tags_allowed = (n_video + n_audio + n_text == 1); + GST_DEBUG_OBJECT (player, "Stream tags allowed: %s", (player->stream_tags_allowed) ? "yes" : "no"); + clapper_player_take_stream_collection (player, collection); } @@ -1214,9 +1234,10 @@ _handle_stream_start_msg (GstMessage *msg, ClapperPlayer *player) clapper_player_playbin_update_current_decoders (player); if (player->pending_tags) { - if (G_LIKELY (player->played_item != NULL)) - clapper_media_item_update_from_tag_list (player->played_item, player->pending_tags, player); - + if (G_LIKELY (player->played_item != NULL)) { + /* Pending tags come from "extractablesrc" and are always GLOBAL (preferred) */ + clapper_media_item_update_from_tag_list (player->played_item, player->pending_tags, TRUE, player); + } gst_clear_tag_list (&player->pending_tags); } if (player->pending_toc) { diff --git a/src/lib/clapper/clapper-player-private.h b/src/lib/clapper/clapper-player-private.h index a2f7a1eb..ee2afb9e 100644 --- a/src/lib/clapper/clapper-player-private.h +++ b/src/lib/clapper/clapper-player-private.h @@ -61,6 +61,7 @@ struct _ClapperPlayer /* Pending tags/toc that arrive before stream start. * To be applied to "played_item", thus no lock needed. */ + gboolean stream_tags_allowed; GstTagList *pending_tags; GstToc *pending_toc; diff --git a/src/lib/clapper/clapper-player.c b/src/lib/clapper/clapper-player.c index dc9e6058..b80070b7 100644 --- a/src/lib/clapper/clapper-player.c +++ b/src/lib/clapper/clapper-player.c @@ -780,6 +780,7 @@ clapper_player_reset (ClapperPlayer *self, gboolean pending_dispose) GST_OBJECT_UNLOCK (self); + self->stream_tags_allowed = FALSE; gst_clear_tag_list (&self->pending_tags); if (self->pending_toc) {