From a3794f8c3bed60d2bfe6c8fccd3956b9e863a0ac Mon Sep 17 00:00:00 2001 From: jcorporation Date: Thu, 8 Feb 2024 21:26:28 +0100 Subject: [PATCH] Allow range in listplaylist and listplaylistinfo --- NEWS | 1 + doc/protocol.rst | 10 ++++++---- src/command/AllCommands.cxx | 4 ++-- src/command/PlaylistCommands.cxx | 8 ++++++-- src/playlist/Print.cxx | 23 +++++++++++++++++++---- src/playlist/Print.hxx | 4 +++- 6 files changed, 37 insertions(+), 13 deletions(-) diff --git a/NEWS b/NEWS index 1c801f3a3..eb2d18a0d 100644 --- a/NEWS +++ b/NEWS @@ -12,6 +12,7 @@ ver 0.24 (not yet released) - stickers on playlists and some tag types - new command "stickernames" - new "search"/"find" filter "added-since" + - allow range in listplaylist and listplaylistinfo * database - attribute "added" shows when each song was added to the database - proxy: require MPD 0.21 or later diff --git a/doc/protocol.rst b/doc/protocol.rst index 5fca9496b..bfd301ec8 100644 --- a/doc/protocol.rst +++ b/doc/protocol.rst @@ -944,15 +944,17 @@ remote playlists (absolute URI with a supported scheme). .. _command_listplaylist: -:command:`listplaylist {NAME}` +:command:`listplaylist {NAME} [{START:END}]` Lists the songs in the playlist. Playlist plugins are - supported. + supported. A range may be specified to list + only a part of the playlist. [#since_0_24]_ .. _command_listplaylistinfo: -:command:`listplaylistinfo {NAME}` +:command:`listplaylistinfo {NAME} [{START:END}]` Lists the songs with metadata in the playlist. Playlist - plugins are supported. + plugins are supported. A range may be specified to list + only a part of the playlist. [#since_0_24]_ .. _command_listplaylists: diff --git a/src/command/AllCommands.cxx b/src/command/AllCommands.cxx index ddfe9a2b9..54bb186e8 100644 --- a/src/command/AllCommands.cxx +++ b/src/command/AllCommands.cxx @@ -117,8 +117,8 @@ static constexpr struct command commands[] = { { "listneighbors", PERMISSION_READ, 0, 0, handle_listneighbors }, #endif { "listpartitions", PERMISSION_READ, 0, 0, handle_listpartitions }, - { "listplaylist", PERMISSION_READ, 1, 1, handle_listplaylist }, - { "listplaylistinfo", PERMISSION_READ, 1, 1, handle_listplaylistinfo }, + { "listplaylist", PERMISSION_READ, 1, 2, handle_listplaylist }, + { "listplaylistinfo", PERMISSION_READ, 1, 2, handle_listplaylistinfo }, { "listplaylists", PERMISSION_READ, 0, 0, handle_listplaylists }, { "load", PERMISSION_ADD, 1, 3, handle_load }, { "lsinfo", PERMISSION_READ, 0, 1, handle_lsinfo }, diff --git a/src/command/PlaylistCommands.cxx b/src/command/PlaylistCommands.cxx index 65dbe4044..1d75e27be 100644 --- a/src/command/PlaylistCommands.cxx +++ b/src/command/PlaylistCommands.cxx @@ -125,8 +125,10 @@ handle_listplaylist(Client &client, Request args, Response &r) #endif ); + RangeArg range = args.ParseOptional(1, RangeArg::All()); + if (playlist_file_print(r, client.GetPartition(), SongLoader(client), - name, false)) + name, range.start, range.end, false)) return CommandResult::OK; throw PlaylistError::NoSuchList(); @@ -142,8 +144,10 @@ handle_listplaylistinfo(Client &client, Request args, Response &r) #endif ); + RangeArg range = args.ParseOptional(1, RangeArg::All()); + if (playlist_file_print(r, client.GetPartition(), SongLoader(client), - name, true)) + name, range.start, range.end, true)) return CommandResult::OK; throw PlaylistError::NoSuchList(); diff --git a/src/playlist/Print.cxx b/src/playlist/Print.cxx index e05437666..070eff1bf 100644 --- a/src/playlist/Print.cxx +++ b/src/playlist/Print.cxx @@ -18,14 +18,25 @@ static void playlist_provider_print(Response &r, const SongLoader &loader, const char *uri, - SongEnumerator &e, bool detail) noexcept + SongEnumerator &e, + unsigned start_index, + unsigned end_index, + bool detail) noexcept { const auto base_uri = uri != nullptr ? PathTraitsUTF8::GetParent(uri) : "."; std::unique_ptr song; - while ((song = e.NextSong()) != nullptr) { + + for (unsigned i = 0; + i < end_index && (song = e.NextSong()) != nullptr; + ++i) { + if (i < start_index) { + /* skip songs before the start index */ + continue; + } + if (playlist_check_translate_song(*song, base_uri, loader) && detail) @@ -40,7 +51,10 @@ playlist_provider_print(Response &r, bool playlist_file_print(Response &r, Partition &partition, const SongLoader &loader, - const LocatedUri &uri, bool detail) + const LocatedUri &uri, + unsigned start_index, + unsigned end_index, + bool detail) { Mutex mutex; @@ -56,6 +70,7 @@ playlist_file_print(Response &r, Partition &partition, if (playlist == nullptr) return false; - playlist_provider_print(r, loader, uri.canonical_uri, *playlist, detail); + playlist_provider_print(r, loader, uri.canonical_uri, *playlist, + start_index, end_index, detail); return true; } diff --git a/src/playlist/Print.hxx b/src/playlist/Print.hxx index 1bed3592e..e3049796a 100644 --- a/src/playlist/Print.hxx +++ b/src/playlist/Print.hxx @@ -18,6 +18,8 @@ struct Partition; bool playlist_file_print(Response &r, Partition &partition, const SongLoader &loader, - const LocatedUri &uri, bool detail); + const LocatedUri &uri, + unsigned start_index, unsigned end_index, + bool detail); #endif