mirror of https://code.videolan.org/videolan/vlc
playlist: assign unique id to playlist items
Playlist items are intended to be handled by index (with lock held) or by instance (vlc_playlist_item_t *). Some modules, like http, require to reference playlist items "remotely". To simplify their implementation, assign an id, unique within a playlist instance, to every items. Signed-off-by: Thomas Guillem <thomas@gllm.fr>
This commit is contained in:
parent
f322ccbbcb
commit
ab9b8df2dd
|
@ -316,6 +316,12 @@ vlc_playlist_item_Release(vlc_playlist_item_t *);
|
|||
VLC_API input_item_t *
|
||||
vlc_playlist_item_GetMedia(vlc_playlist_item_t *);
|
||||
|
||||
/**
|
||||
* Return a unique id for the playlist item instance.
|
||||
*/
|
||||
VLC_API uint64_t
|
||||
vlc_playlist_item_GetId(vlc_playlist_item_t *);
|
||||
|
||||
/* Playlist */
|
||||
|
||||
/**
|
||||
|
@ -655,6 +661,16 @@ vlc_playlist_IndexOf(vlc_playlist_t *playlist, const vlc_playlist_item_t *item);
|
|||
VLC_API ssize_t
|
||||
vlc_playlist_IndexOfMedia(vlc_playlist_t *playlist, const input_item_t *media);
|
||||
|
||||
/**
|
||||
* Return the index of a given item id.
|
||||
*
|
||||
* \param playlist the playlist, locked
|
||||
* \param id the id to locate
|
||||
* \return the index of the playlist item having the id (-1 if not found)
|
||||
*/
|
||||
VLC_API ssize_t
|
||||
vlc_playlist_IndexOfId(vlc_playlist_t *playlist, uint64_t id);
|
||||
|
||||
/**
|
||||
* Return the playback "repeat" mode.
|
||||
*
|
||||
|
|
|
@ -936,6 +936,7 @@ vlc_player_vout_Snapshot
|
|||
vlc_playlist_item_Hold
|
||||
vlc_playlist_item_Release
|
||||
vlc_playlist_item_GetMedia
|
||||
vlc_playlist_item_GetId
|
||||
vlc_playlist_New
|
||||
vlc_playlist_Delete
|
||||
vlc_playlist_Lock
|
||||
|
@ -955,6 +956,7 @@ vlc_playlist_Shuffle
|
|||
vlc_playlist_Sort
|
||||
vlc_playlist_IndexOf
|
||||
vlc_playlist_IndexOfMedia
|
||||
vlc_playlist_IndexOfId
|
||||
vlc_playlist_GetPlaybackRepeat
|
||||
vlc_playlist_GetPlaybackOrder
|
||||
vlc_playlist_SetPlaybackRepeat
|
||||
|
|
|
@ -205,6 +205,18 @@ vlc_playlist_IndexOfMedia(vlc_playlist_t *playlist, const input_item_t *media)
|
|||
return -1;
|
||||
}
|
||||
|
||||
ssize_t
|
||||
vlc_playlist_IndexOfId(vlc_playlist_t *playlist, uint64_t id)
|
||||
{
|
||||
vlc_playlist_AssertLocked(playlist);
|
||||
|
||||
playlist_item_vector_t *items = &playlist->items;
|
||||
for (size_t i = 0; i < items->size; ++i)
|
||||
if (items->data[i]->id == id)
|
||||
return i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
void
|
||||
vlc_playlist_Clear(vlc_playlist_t *playlist)
|
||||
{
|
||||
|
@ -218,13 +230,15 @@ vlc_playlist_Clear(vlc_playlist_t *playlist)
|
|||
}
|
||||
|
||||
static int
|
||||
vlc_playlist_MediaToItems(input_item_t *const media[], size_t count,
|
||||
vlc_playlist_item_t *items[])
|
||||
vlc_playlist_MediaToItems(vlc_playlist_t *playlist, input_item_t *const media[],
|
||||
size_t count, vlc_playlist_item_t *items[])
|
||||
{
|
||||
vlc_playlist_AssertLocked(playlist);
|
||||
size_t i;
|
||||
for (i = 0; i < count; ++i)
|
||||
{
|
||||
items[i] = vlc_playlist_item_New(media[i]);
|
||||
uint64_t id = playlist->idgen++;
|
||||
items[i] = vlc_playlist_item_New(media[i], id);
|
||||
if (unlikely(!items[i]))
|
||||
break;
|
||||
}
|
||||
|
@ -250,7 +264,7 @@ vlc_playlist_Insert(vlc_playlist_t *playlist, size_t index,
|
|||
return VLC_ENOMEM;
|
||||
|
||||
/* create playlist items in place */
|
||||
int ret = vlc_playlist_MediaToItems(media, count,
|
||||
int ret = vlc_playlist_MediaToItems(playlist, media, count,
|
||||
&playlist->items.data[index]);
|
||||
if (ret != VLC_SUCCESS)
|
||||
{
|
||||
|
@ -307,7 +321,8 @@ vlc_playlist_Replace(vlc_playlist_t *playlist, size_t index,
|
|||
vlc_playlist_AssertLocked(playlist);
|
||||
assert(index < playlist->items.size);
|
||||
|
||||
vlc_playlist_item_t *item = vlc_playlist_item_New(media);
|
||||
uint64_t id = playlist->idgen++;
|
||||
vlc_playlist_item_t *item = vlc_playlist_item_New(media, id);
|
||||
if (!item)
|
||||
return VLC_ENOMEM;
|
||||
|
||||
|
@ -347,7 +362,7 @@ vlc_playlist_Expand(vlc_playlist_t *playlist, size_t index,
|
|||
return VLC_ENOMEM;
|
||||
|
||||
/* create playlist items in place */
|
||||
ret = vlc_playlist_MediaToItems(&media[1], count - 1,
|
||||
ret = vlc_playlist_MediaToItems(playlist, &media[1], count - 1,
|
||||
&playlist->items.data[index + 1]);
|
||||
if (ret != VLC_SUCCESS)
|
||||
{
|
||||
|
|
|
@ -28,13 +28,14 @@
|
|||
#include <vlc_input_item.h>
|
||||
|
||||
vlc_playlist_item_t *
|
||||
vlc_playlist_item_New(input_item_t *media)
|
||||
vlc_playlist_item_New(input_item_t *media, uint64_t id)
|
||||
{
|
||||
vlc_playlist_item_t *item = malloc(sizeof(*item));
|
||||
if (unlikely(!item))
|
||||
return NULL;
|
||||
|
||||
vlc_atomic_rc_init(&item->rc);
|
||||
item->id = id;
|
||||
item->media = media;
|
||||
input_item_Hold(media);
|
||||
return item;
|
||||
|
@ -61,3 +62,9 @@ vlc_playlist_item_GetMedia(vlc_playlist_item_t *item)
|
|||
{
|
||||
return item->media;
|
||||
}
|
||||
|
||||
uint64_t
|
||||
vlc_playlist_item_GetId(vlc_playlist_item_t *item)
|
||||
{
|
||||
return item->id;
|
||||
}
|
||||
|
|
|
@ -29,11 +29,12 @@ typedef struct input_item_t input_item_t;
|
|||
struct vlc_playlist_item
|
||||
{
|
||||
input_item_t *media;
|
||||
uint64_t id;
|
||||
vlc_atomic_rc_t rc;
|
||||
};
|
||||
|
||||
/* _New() is private, it is called when inserting new media in the playlist */
|
||||
vlc_playlist_item_t *
|
||||
vlc_playlist_item_New(input_item_t *media);
|
||||
vlc_playlist_item_New(input_item_t *media, uint64_t id);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -52,6 +52,7 @@ vlc_playlist_New(vlc_object_t *parent)
|
|||
vlc_list_init(&playlist->listeners);
|
||||
playlist->repeat = VLC_PLAYLIST_PLAYBACK_REPEAT_NONE;
|
||||
playlist->order = VLC_PLAYLIST_PLAYBACK_ORDER_NORMAL;
|
||||
playlist->idgen = 0;
|
||||
|
||||
return playlist;
|
||||
}
|
||||
|
|
|
@ -57,6 +57,7 @@ struct vlc_playlist
|
|||
struct vlc_list listeners; /**< list of vlc_playlist_listener_id.node */
|
||||
enum vlc_playlist_playback_repeat repeat;
|
||||
enum vlc_playlist_playback_order order;
|
||||
uint64_t idgen;
|
||||
};
|
||||
|
||||
static inline void
|
||||
|
|
|
@ -32,14 +32,17 @@
|
|||
typedef struct VLC_VECTOR(input_item_t *) media_vector_t;
|
||||
|
||||
static void
|
||||
vlc_playlist_CollectChildren(media_vector_t *dest, input_item_node_t *node)
|
||||
vlc_playlist_CollectChildren(vlc_playlist_t *playlist,
|
||||
media_vector_t *dest,
|
||||
input_item_node_t *node)
|
||||
{
|
||||
vlc_playlist_AssertLocked(playlist);
|
||||
for (int i = 0; i < node->i_children; ++i)
|
||||
{
|
||||
input_item_node_t *child = node->pp_children[i];
|
||||
input_item_t *media = child->p_item;
|
||||
vlc_vector_push(dest, media);
|
||||
vlc_playlist_CollectChildren(dest, child);
|
||||
vlc_playlist_CollectChildren(playlist, dest, child);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -50,7 +53,7 @@ vlc_playlist_ExpandItem(vlc_playlist_t *playlist, size_t index,
|
|||
vlc_playlist_AssertLocked(playlist);
|
||||
|
||||
media_vector_t flatten = VLC_VECTOR_INITIALIZER;
|
||||
vlc_playlist_CollectChildren(&flatten, node);
|
||||
vlc_playlist_CollectChildren(playlist, &flatten, node);
|
||||
|
||||
int ret = vlc_playlist_Expand(playlist, index, flatten.data, flatten.size);
|
||||
vlc_vector_destroy(&flatten);
|
||||
|
|
|
@ -1504,7 +1504,7 @@ test_request_remove_adapt(void)
|
|||
vlc_playlist_AddListener(playlist, &cbs, &ctx, false);
|
||||
assert(listener);
|
||||
|
||||
vlc_playlist_item_t *dummy = vlc_playlist_item_New(media[10]);
|
||||
vlc_playlist_item_t *dummy = vlc_playlist_item_New(media[10], 0);
|
||||
assert(dummy);
|
||||
|
||||
/* remove items in a wrong order at wrong position, as if the playlist had
|
||||
|
@ -1702,7 +1702,7 @@ test_request_move_adapt(void)
|
|||
vlc_playlist_AddListener(playlist, &cbs, &ctx, false);
|
||||
assert(listener);
|
||||
|
||||
vlc_playlist_item_t *dummy = vlc_playlist_item_New(media[15]);
|
||||
vlc_playlist_item_t *dummy = vlc_playlist_item_New(media[15], 0);
|
||||
assert(dummy);
|
||||
|
||||
/* move items in a wrong order at wrong position, as if the playlist had
|
||||
|
|
Loading…
Reference in New Issue