diff --git a/DOCS/interface-changes.rst b/DOCS/interface-changes.rst index 7d02d8ef46..9e883800e8 100644 --- a/DOCS/interface-changes.rst +++ b/DOCS/interface-changes.rst @@ -38,6 +38,7 @@ Interface changes - change type of `--sub-pos` to float - The remaining time printed in the terminal is now adjusted for speed by default. You can disable this with `--no-term-remaining-playtime`. + - add `playlist-path` and `playlist/N/playlist-path` properties --- mpv 0.36.0 --- - add `--target-contrast` - Target luminance value is now also applied when ICC profile is used. diff --git a/DOCS/man/input.rst b/DOCS/man/input.rst index a99fbd798e..ae8d695849 100644 --- a/DOCS/man/input.rst +++ b/DOCS/man/input.rst @@ -2776,6 +2776,11 @@ Property list ``playlist-count`` Number of total playlist entries. +``playlist-path`` + The original path of the playlist for the current entry before mpv expanded + the entries. Unavailable if the file was not originally associated with a + playlist in some way. + ``playlist`` Playlist, current entry marked. Currently, the raw property value is useless. @@ -2809,6 +2814,11 @@ Property list instance. Other commands, events, etc. use this as ``playlist_entry_id`` fields. + ``playlist/N/playlist-path`` + The original path of the playlist for this entry before mpv expanded + it. Unavailable if the file was not originally associated with a playlist + in some way. + When querying the property with the client API using ``MPV_FORMAT_NODE``, or with Lua ``mp.get_property_native``, this will return a mpv_node with the following contents: diff --git a/common/playlist.c b/common/playlist.c index ad5253bdd5..1ba8a58f32 100644 --- a/common/playlist.c +++ b/common/playlist.c @@ -142,6 +142,14 @@ void playlist_add_file(struct playlist *pl, const char *filename) playlist_add(pl, playlist_entry_new(filename)); } +void playlist_populate_playlist_path(struct playlist *pl, const char *path) +{ + for (int n = 0; n < pl->num_entries; n++) { + struct playlist_entry *e = pl->entries[n]; + e->playlist_path = talloc_strdup(e, path); + } +} + void playlist_shuffle(struct playlist *pl) { for (int n = 0; n < pl->num_entries; n++) diff --git a/common/playlist.h b/common/playlist.h index 5f84e3b413..64d1cd45f0 100644 --- a/common/playlist.h +++ b/common/playlist.h @@ -33,6 +33,7 @@ struct playlist_entry { uint64_t id; char *filename; + char *playlist_path; struct playlist_param *params; int num_params; @@ -93,6 +94,7 @@ void playlist_move(struct playlist *pl, struct playlist_entry *entry, struct playlist_entry *at); void playlist_add_file(struct playlist *pl, const char *filename); +void playlist_populate_playlist_path(struct playlist *pl, const char *path); void playlist_shuffle(struct playlist *pl); void playlist_unshuffle(struct playlist *pl); struct playlist_entry *playlist_get_first(struct playlist *pl); diff --git a/options/parse_commandline.c b/options/parse_commandline.c index b68c53acd6..93120d3ad3 100644 --- a/options/parse_commandline.c +++ b/options/parse_commandline.c @@ -194,13 +194,15 @@ int m_config_parse_mp_command_line(m_config_t *config, struct playlist *files, // append the playlist to the local args char *param0 = bstrdup0(NULL, p.param); struct playlist *pl = playlist_parse_file(param0, NULL, global); - talloc_free(param0); if (!pl) { MP_FATAL(config, "Error reading playlist '%.*s'\n", BSTR_P(p.param)); + talloc_free(param0); goto err_out; } playlist_transfer_entries(files, pl); + playlist_populate_playlist_path(files, param0); + talloc_free(param0); talloc_free(pl); continue; } diff --git a/player/command.c b/player/command.c index 28c97f0d6f..a00b42ca8c 100644 --- a/player/command.c +++ b/player/command.c @@ -3092,17 +3092,29 @@ static int get_playlist_entry(int item, int action, void *arg, void *ctx) bool current = mpctx->playlist->current == e; bool playing = mpctx->playing == e; struct m_sub_property props[] = { - {"filename", SUB_PROP_STR(e->filename)}, - {"current", SUB_PROP_BOOL(1), .unavailable = !current}, - {"playing", SUB_PROP_BOOL(1), .unavailable = !playing}, - {"title", SUB_PROP_STR(e->title), .unavailable = !e->title}, - {"id", SUB_PROP_INT64(e->id)}, + {"filename", SUB_PROP_STR(e->filename)}, + {"current", SUB_PROP_BOOL(1), .unavailable = !current}, + {"playing", SUB_PROP_BOOL(1), .unavailable = !playing}, + {"title", SUB_PROP_STR(e->title), .unavailable = !e->title}, + {"id", SUB_PROP_INT64(e->id)}, + {"playlist-path", SUB_PROP_STR(e->playlist_path), .unavailable = !e->playlist_path}, {0} }; return m_property_read_sub(props, action, arg); } +static int mp_property_playlist_path(void *ctx, struct m_property *prop, + int action, void *arg) +{ + MPContext *mpctx = ctx; + if (!mpctx->playlist->current) + return M_PROPERTY_UNAVAILABLE; + + struct playlist_entry *e = mpctx->playlist->current; + return m_property_strdup_ro(action, arg, e->playlist_path); +} + static int mp_property_playlist(void *ctx, struct m_property *prop, int action, void *arg) { @@ -3875,6 +3887,7 @@ static const struct m_property mp_properties_base[] = { {"edition-list", property_list_editions}, {"playlist", mp_property_playlist}, + {"playlist-path", mp_property_playlist_path}, {"playlist-pos", mp_property_playlist_pos}, {"playlist-pos-1", mp_property_playlist_pos_1}, {"playlist-current-pos", mp_property_playlist_current_pos}, diff --git a/player/loadfile.c b/player/loadfile.c index 851413bb06..a2f593333e 100644 --- a/player/loadfile.c +++ b/player/loadfile.c @@ -1659,6 +1659,7 @@ static void play_current_file(struct MPContext *mpctx) if (watch_later) mp_delete_watch_later_conf(mpctx, mpctx->filename); struct playlist *pl = mpctx->demuxer->playlist; + playlist_populate_playlist_path(pl, mpctx->filename); transfer_playlist(mpctx, pl, &end_event.playlist_insert_id, &end_event.playlist_insert_num_entries); mp_notify_property(mpctx, "playlist");