From 57f9c098e8f5b582c8f289d181117cec1a52e653 Mon Sep 17 00:00:00 2001 From: waker Date: Wed, 31 Aug 2011 21:23:55 +0200 Subject: fixed writing non-ascii id3v1 tags --- deadbeef.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'deadbeef.h') diff --git a/deadbeef.h b/deadbeef.h index 10f50422..8b7de00a 100644 --- a/deadbeef.h +++ b/deadbeef.h @@ -633,7 +633,7 @@ typedef struct { // junk reading/writing int (*junk_id3v1_read) (DB_playItem_t *it, DB_FILE *fp); int (*junk_id3v1_find) (DB_FILE *fp); - int (*junk_id3v1_write) (FILE *fp, DB_playItem_t *it); + int (*junk_id3v1_write) (FILE *fp, DB_playItem_t *it, const char *enc); int (*junk_id3v2_find) (DB_FILE *fp, int *psize); int (*junk_id3v2_read) (DB_playItem_t *it, DB_FILE *fp); int (*junk_id3v2_read_full) (DB_playItem_t *it, DB_id3v2_tag_t *tag, DB_FILE *fp); -- cgit v1.2.3 From 76f14028b56a1cdb6627b0db0e6af0a74a9b76f3 Mon Sep 17 00:00:00 2001 From: waker Date: Fri, 17 Jun 2011 20:54:11 +0200 Subject: merge new APIs for 0.5.2 from devel --- deadbeef.h | 13 ++++++++++++- metacache.c | 12 ++++++++++++ metacache.h | 6 ++++++ playlist.c | 28 ++++++++++++++++++++++------ playlist.h | 10 ++++++++++ plugins.c | 13 ++++++++++++- 6 files changed, 74 insertions(+), 8 deletions(-) (limited to 'deadbeef.h') diff --git a/deadbeef.h b/deadbeef.h index 8b7de00a..3605c09b 100644 --- a/deadbeef.h +++ b/deadbeef.h @@ -76,7 +76,7 @@ extern "C" { // 0.1 -- deadbeef-0.2.0 #define DB_API_VERSION_MAJOR 1 -#define DB_API_VERSION_MINOR 1 +#define DB_API_VERSION_MINOR 2 #define DDB_PLUGIN_SET_API_VERSION\ .plugin.api_vmajor = DB_API_VERSION_MAJOR,\ @@ -725,6 +725,17 @@ typedef struct { int (*dsp_preset_load) (const char *fname, struct ddb_dsp_context_s **head); int (*dsp_preset_save) (const char *fname, struct ddb_dsp_context_s *head); void (*dsp_preset_free) (struct ddb_dsp_context_s *head); + + // new 1.2 APIs + ddb_playlist_t *(*plt_alloc) (const char *title); + void (*plt_free) (ddb_playlist_t *plt); + //int (*plt_insert) (ddb_playlist_t *plt, int before); + void (*plt_set_fast_mode) (ddb_playlist_t *plt, int fast); + int (*plt_is_fast_mode) (ddb_playlist_t *plt); + const char * (*metacache_add_string) (const char *str); + void (*metacache_remove_string) (const char *str); + void (*metacache_ref) (const char *str); + void (*metacache_unref) (const char *str); } DB_functions_t; enum { diff --git a/metacache.c b/metacache.c index 84acaa91..13616516 100644 --- a/metacache.c +++ b/metacache.c @@ -114,3 +114,15 @@ metacache_remove_string (const char *str) { chain = chain->next; } } + +void +metacache_ref (const char *str) { + uint32_t *refc = (uint32_t)(str-5); + *refc++; +} + +void +metacache_unref (const char *str) { + uint32_t *refc = (uint32_t *)(str-5); + *refc--; +} diff --git a/metacache.h b/metacache.h index b5187c0f..50c5cb7f 100644 --- a/metacache.h +++ b/metacache.h @@ -25,4 +25,10 @@ metacache_add_string (const char *str); void metacache_remove_string (const char *str); +void +metacache_ref (const char *str); + +void +metacache_unref (const char *str); + #endif diff --git a/playlist.c b/playlist.c index 312965fc..68accc38 100644 --- a/playlist.c +++ b/playlist.c @@ -327,6 +327,15 @@ plt_get_sel_count (int plt) { return 0; } +playlist_t * +plt_alloc (const char *title) { + playlist_t *plt = malloc (sizeof (playlist_t)); + memset (plt, 0, sizeof (playlist_t)); + plt->refc = 1; + plt->title = strdup (title); + return plt; +} + int plt_add (int before, const char *title) { assert (before >= 0); @@ -335,10 +344,7 @@ plt_add (int before, const char *title) { fprintf (stderr, "can't create more than 100 playlists. sorry.\n"); return -1; } - playlist_t *plt = malloc (sizeof (playlist_t)); - memset (plt, 0, sizeof (playlist_t)); - plt->refc = 1; - plt->title = strdup (title); + playlist_t *plt = plt_alloc (title); plt_modified (plt); LOCK; @@ -398,7 +404,7 @@ plt_add (int before, const char *title) { conf_save (); messagepump_push (DB_EV_PLAYLISTSWITCHED, 0, 0, 0); } - return playlists_count-1; + return before; } // NOTE: caller must ensure that configuration is saved after that call @@ -980,7 +986,7 @@ plt_process_cue_track (playlist_t *playlist, playItem_t *after, const char *fnam pl_set_item_replaygain (it, DDB_REPLAYGAIN_TRACKPEAK, atof (replaygain_track_peak)); } it->_flags |= DDB_IS_SUBTRACK | DDB_TAG_CUESHEET; - after = pl_insert_item (after, it); + after = plt_insert_item (playlist, after, it); pl_item_unref (it); *prev = it; return it; @@ -3904,3 +3910,13 @@ plt_init_shuffle_albums (playlist_t *plt, int r) { } pl_unlock (); } + +void +plt_set_fast_mode (playlist_t *plt, int fast) { + plt->fast_mode = (unsigned)fast; +} + +int +plt_is_fast_mode (playlist_t *plt) { + return plt->fast_mode; +} diff --git a/playlist.h b/playlist.h index 23f74459..2f9a9d6a 100644 --- a/playlist.h +++ b/playlist.h @@ -56,6 +56,7 @@ typedef struct playlist_s { int current_row[PL_MAX_ITERATORS]; // current row (cursor) struct DB_metaInfo_s *meta; // linked list storing metainfo int refc; + unsigned fast_mode : 1; } playlist_t; // global playlist control functions @@ -92,6 +93,9 @@ plt_ref (playlist_t *plt); void plt_unref (playlist_t *plt); +playlist_t * +plt_alloc (const char *title); + void plt_free (playlist_t *plt); @@ -437,4 +441,10 @@ pl_get_playlist (playItem_t *it); void plt_init_shuffle_albums (playlist_t *plt, int r); +void +plt_set_fast_mode (playlist_t *plt, int fast); + +int +plt_is_fast_mode (playlist_t *plt); + #endif // __PLAYLIST_H diff --git a/plugins.c b/plugins.c index 92b740a1..ff110913 100644 --- a/plugins.c +++ b/plugins.c @@ -45,6 +45,7 @@ #include "premix.h" #include "dsppreset.h" #include "pltmeta.h" +#include "metacache.h" #define trace(...) { fprintf(stderr, __VA_ARGS__); } //#define trace(fmt,...) @@ -316,7 +317,17 @@ static DB_functions_t deadbeef_api = { // dsp preset management .dsp_preset_load = dsp_preset_load, .dsp_preset_save = dsp_preset_save, - .dsp_preset_free = dsp_preset_free + .dsp_preset_free = dsp_preset_free, + // new 1.2 APIs + .plt_alloc = (ddb_playlist_t *(*)(const char *title))plt_alloc, + .plt_free = (void (*)(ddb_playlist_t *plt))plt_free, + //.plt_insert = plt_insert, + .plt_set_fast_mode = (void (*)(ddb_playlist_t *plt, int fast))plt_set_fast_mode, + .plt_is_fast_mode = (int (*)(ddb_playlist_t *plt))plt_is_fast_mode, + .metacache_add_string = metacache_add_string, + .metacache_remove_string = metacache_remove_string, + .metacache_ref = metacache_ref, + .metacache_unref = metacache_unref, }; DB_functions_t *deadbeef = &deadbeef_api; -- cgit v1.2.3 From ecafc1687513de35d080a9b4be14022e885a95e1 Mon Sep 17 00:00:00 2001 From: waker Date: Sat, 1 Oct 2011 10:33:47 +0200 Subject: added experimental support for metadata overrides. for example field "!NAME" will override field ":NAME", but will not be stored so after player restart, the field will be restored to original :NAME --- deadbeef.h | 8 ++++-- metacache.c | 2 +- playlist.c | 88 ++++++++++++++++++++++++++++++------------------------------- playlist.h | 4 +++ plmeta.c | 38 ++++++++++++++++++++++---- plugins.c | 1 + 6 files changed, 89 insertions(+), 52 deletions(-) (limited to 'deadbeef.h') diff --git a/deadbeef.h b/deadbeef.h index 3605c09b..74d17993 100644 --- a/deadbeef.h +++ b/deadbeef.h @@ -726,16 +726,20 @@ typedef struct { int (*dsp_preset_save) (const char *fname, struct ddb_dsp_context_s *head); void (*dsp_preset_free) (struct ddb_dsp_context_s *head); - // new 1.2 APIs + // ******* new 1.2 APIs ******** ddb_playlist_t *(*plt_alloc) (const char *title); void (*plt_free) (ddb_playlist_t *plt); - //int (*plt_insert) (ddb_playlist_t *plt, int before); + void (*plt_set_fast_mode) (ddb_playlist_t *plt, int fast); int (*plt_is_fast_mode) (ddb_playlist_t *plt); + const char * (*metacache_add_string) (const char *str); void (*metacache_remove_string) (const char *str); void (*metacache_ref) (const char *str); void (*metacache_unref) (const char *str); + + // this function must return original un-overriden value (ignoring the keys prefixed with '!') + const char *(*pl_find_meta_raw) (DB_playItem_t *it, const char *key); } DB_functions_t; enum { diff --git a/metacache.c b/metacache.c index 13616516..e7fa1619 100644 --- a/metacache.c +++ b/metacache.c @@ -117,7 +117,7 @@ metacache_remove_string (const char *str) { void metacache_ref (const char *str) { - uint32_t *refc = (uint32_t)(str-5); + uint32_t *refc = (uint32_t *)(str-5); *refc++; } diff --git a/playlist.c b/playlist.c index 68accc38..4ed52836 100644 --- a/playlist.c +++ b/playlist.c @@ -145,7 +145,7 @@ pl_free (void) { for (playItem_t *it = playlists_head->head[PL_MAIN]; it; it = it->next[PL_MAIN]) { if (it->_refc > 1) { - fprintf (stderr, "\033[0;31mWARNING: playitem %p %s(%s) has refc=%d at delete time\033[37;0m\n", it, pl_find_meta (it, ":URI"), pl_find_meta (it, "track"), it->_refc); + fprintf (stderr, "\033[0;31mWARNING: playitem %p %s(%s) has refc=%d at delete time\033[37;0m\n", it, pl_find_meta_raw (it, ":URI"), pl_find_meta_raw (it, "track"), it->_refc); } } @@ -1060,11 +1060,11 @@ plt_insert_cue_from_buffer (playlist_t *playlist, playItem_t *after, playItem_t pl_get_value_from_cue (p + 9, sizeof (date), date); } else if (!strncmp (p, "TRACK ", 6)) { - trace ("cue: adding track: %s %s %s\n", pl_find_meta (origin, ":URI"), title, track); + trace ("cue: adding track: %s %s %s\n", pl_find_meta_raw (origin, ":URI"), title, track); if (title[0]) { // add previous track - const char *filetype = pl_find_meta (origin, ":FILETYPE"); - after = plt_process_cue_track (playlist, after, pl_find_meta (origin, ":URI"), &prev, track, index00, index01, pregap, title, albumperformer, performer, albumtitle, genre, date, replaygain_album_gain, replaygain_album_peak, replaygain_track_gain, replaygain_track_peak, pl_find_meta (origin, ":DECODER"), filetype, samplerate); + const char *filetype = pl_find_meta_raw (origin, ":FILETYPE"); + after = plt_process_cue_track (playlist, after, pl_find_meta_raw (origin, ":URI"), &prev, track, index00, index01, pregap, title, albumperformer, performer, albumtitle, genre, date, replaygain_album_gain, replaygain_album_peak, replaygain_track_gain, replaygain_track_peak, pl_find_meta_raw (origin, ":DECODER"), filetype, samplerate); trace ("cue: added %p (%p)\n", after); } @@ -1108,8 +1108,8 @@ plt_insert_cue_from_buffer (playlist_t *playlist, playItem_t *after, playItem_t UNLOCK; return NULL; } - const char *filetype = pl_find_meta (origin, ":FILETYPE"); - after = plt_process_cue_track (playlist, after, pl_find_meta (origin, ":URI"), &prev, track, index00, index01, pregap, title, albumperformer, performer, albumtitle, genre, date, replaygain_album_gain, replaygain_album_peak, replaygain_track_gain, replaygain_track_peak, pl_find_meta (origin, ":DECODER"), filetype, samplerate); + const char *filetype = pl_find_meta_raw (origin, ":FILETYPE"); + after = plt_process_cue_track (playlist, after, pl_find_meta_raw (origin, ":URI"), &prev, track, index00, index01, pregap, title, albumperformer, performer, albumtitle, genre, date, replaygain_album_gain, replaygain_album_peak, replaygain_track_gain, replaygain_track_peak, pl_find_meta_raw (origin, ":DECODER"), filetype, samplerate); if (after) { trace ("last track endsample: %d\n", numsamples-1); after->endsample = numsamples-1; @@ -1127,7 +1127,7 @@ plt_insert_cue_from_buffer (playlist_t *playlist, playItem_t *after, playItem_t // copy metadata from embedded tags uint32_t f = pl_get_item_flags (origin); f |= DDB_TAG_CUESHEET | DDB_IS_SUBTRACK; - if (pl_find_meta (origin, "cuesheet")) { + if (pl_find_meta_raw (origin, "cuesheet")) { f |= DDB_HAS_EMBEDDED_CUESHEET; } pl_set_item_flags (origin, f); @@ -1139,7 +1139,7 @@ plt_insert_cue_from_buffer (playlist_t *playlist, playItem_t *after, playItem_t playItem_t * plt_insert_cue (playlist_t *plt, playItem_t *after, playItem_t *origin, int numsamples, int samplerate) { trace ("pl_insert_cue numsamples=%d, samplerate=%d\n", numsamples, samplerate); - const char *fname = pl_find_meta (origin, ":URI"); + const char *fname = pl_find_meta_raw (origin, ":URI"); int len = strlen (fname); char cuename[len+5]; strcpy (cuename, fname); @@ -1894,7 +1894,7 @@ plt_insert_item (playlist_t *playlist, playItem_t *after, playItem_t *it) { // shuffle playItem_t *prev = it->prev[PL_MAIN]; - if (pl_order == PLAYBACK_ORDER_SHUFFLE_ALBUMS && prev && pl_find_meta (prev, "album") == pl_find_meta (it, "album") && pl_find_meta (prev, "artist") == pl_find_meta (it, "artist")) { + if (pl_order == PLAYBACK_ORDER_SHUFFLE_ALBUMS && prev && pl_find_meta_raw (prev, "album") == pl_find_meta_raw (it, "album") && pl_find_meta_raw (prev, "artist") == pl_find_meta_raw (it, "artist")) { it->shufflerating = prev->shufflerating; } else { @@ -1973,7 +1973,7 @@ void pl_item_ref (playItem_t *it) { LOCK; it->_refc++; - //fprintf (stderr, "\033[0;34m+it %p: refc=%d: %s\033[37;0m\n", it, it->_refc, pl_find_meta (it, ":URI")); + //fprintf (stderr, "\033[0;34m+it %p: refc=%d: %s\033[37;0m\n", it, it->_refc, pl_find_meta_raw (it, ":URI")); UNLOCK; } @@ -1997,12 +1997,12 @@ void pl_item_unref (playItem_t *it) { LOCK; it->_refc--; - //trace ("\033[0;31m-it %p: refc=%d: %s\033[37;0m\n", it, it->_refc, pl_find_meta (it, ":URI")); + //trace ("\033[0;31m-it %p: refc=%d: %s\033[37;0m\n", it, it->_refc, pl_find_meta_raw (it, ":URI")); if (it->_refc < 0) { trace ("\033[0;31mplaylist: bad refcount on item %p\033[37;0m\n", it); } if (it->_refc <= 0) { - //printf ("\033[0;31mdeleted %s\033[37;0m\n", pl_find_meta (it, ":URI")); + //printf ("\033[0;31mdeleted %s\033[37;0m\n", pl_find_meta_raw (it, ":URI")); pl_item_free (it); } UNLOCK; @@ -2107,7 +2107,7 @@ plt_save (playlist_t *plt, playItem_t *first, playItem_t *last, const char *fnam uint16_t l; uint8_t ll; #if (PLAYLIST_MINOR_VER==2) - const char *fname = pl_find_meta (it, ":URI"); + const char *fname = pl_find_meta_raw (it, ":URI"); l = strlen (fname); if (fwrite (&l, 1, 2, fp) != 2) { goto save_fail; @@ -2115,7 +2115,7 @@ plt_save (playlist_t *plt, playItem_t *first, playItem_t *last, const char *fnam if (fwrite (fname, 1, l, fp) != l) { goto save_fail; } - const char *decoder_id = pl_find_meta (it, ":DECODER"); + const char *decoder_id = pl_find_meta_raw (it, ":DECODER"); if (decoder_id) { ll = strlen (decoder_id); if (fwrite (&ll, 1, 1, fp) != 1) { @@ -2147,7 +2147,7 @@ plt_save (playlist_t *plt, playItem_t *first, playItem_t *last, const char *fnam goto save_fail; } #if (PLAYLIST_MINOR_VER==2) - const char *filetype = pl_find_meta (it, ":FILETYPE"); + const char *filetype = pl_find_meta_raw (it, ":FILETYPE"); if (!filetype) { filetype = ""; } @@ -2184,7 +2184,7 @@ plt_save (playlist_t *plt, playItem_t *first, playItem_t *last, const char *fnam int16_t nm = 0; DB_metaInfo_t *m; for (m = it->meta; m; m = m->next) { - if (m->key[0] == '_') { + if (m->key[0] == '_' || m->key[0] == '!') { continue; // skip reserved names } nm++; @@ -2193,7 +2193,7 @@ plt_save (playlist_t *plt, playItem_t *first, playItem_t *last, const char *fnam goto save_fail; } for (m = it->meta; m; m = m->next) { - if (m->key[0] == '_') { + if (m->key[0] == '_' || m->key[0] == '!') { continue; // skip reserved names } @@ -2698,7 +2698,7 @@ plt_reshuffle (playlist_t *playlist, playItem_t **ppmin, playItem_t **ppmax) { playItem_t *pmax = NULL; playItem_t *prev = NULL; for (playItem_t *it = playlist->head[PL_MAIN]; it; it = it->next[PL_MAIN]) { - if (pl_order == PLAYBACK_ORDER_SHUFFLE_ALBUMS && prev && pl_find_meta (prev, "album") == pl_find_meta (it, "album") && pl_find_meta (prev, "artist") == pl_find_meta (it, "artist")) { + if (pl_order == PLAYBACK_ORDER_SHUFFLE_ALBUMS && prev && pl_find_meta_raw (prev, "album") == pl_find_meta_raw (it, "album") && pl_find_meta_raw (prev, "artist") == pl_find_meta_raw (it, "artist")) { it->shufflerating = prev->shufflerating; } else { @@ -2725,7 +2725,7 @@ plt_reshuffle (playlist_t *playlist, playItem_t **ppmin, playItem_t **ppmax) { void plt_set_item_duration (playlist_t *playlist, playItem_t *it, float duration) { LOCK; - if (it->in_playlist) { + if (it->in_playlist && playlist) { if (it->_duration > 0) { playlist->totaltime -= it->_duration; } @@ -2794,7 +2794,7 @@ pl_format_item_queue (playItem_t *it, char *s, int size) { LOCK; *s = 0; int initsize = size; - const char *val = pl_find_meta (it, "_playing"); + const char *val = pl_find_meta_raw (it, "_playing"); while (val && *val) { while (*val && *val != '=') { val++; @@ -2984,7 +2984,7 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, l = min (l, sizeof (nm)-1); strncpy (nm, fmt+1, l); nm[l] = 0; - meta = pl_find_meta (it, nm); + meta = pl_find_meta_raw (it, nm); if (!meta) { meta = "?"; } @@ -2992,15 +2992,15 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, } } else if (*fmt == 'a') { - meta = pl_find_meta (it, "artist"); + meta = pl_find_meta_raw (it, "artist"); if (!meta) { meta = "Unknown artist"; } } else if (*fmt == 't') { - meta = pl_find_meta (it, "title"); + meta = pl_find_meta_raw (it, "title"); if (!meta) { - const char *f = pl_find_meta (it, ":URI"); + const char *f = pl_find_meta_raw (it, ":URI"); if (f) { const char *start = strrchr (f, '/'); if (start) { @@ -3027,28 +3027,28 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, } } else if (*fmt == 'b') { - meta = pl_find_meta (it, "album"); + meta = pl_find_meta_raw (it, "album"); if (!meta) { meta = "Unknown album"; } } else if (*fmt == 'B') { - meta = pl_find_meta (it, "band"); + meta = pl_find_meta_raw (it, "band"); if (!meta) { - meta = pl_find_meta (it, "album artist"); + meta = pl_find_meta_raw (it, "album artist"); if (!meta) { - meta = pl_find_meta (it, "albumartist"); + meta = pl_find_meta_raw (it, "albumartist"); if (!meta) { - meta = pl_find_meta (it, "artist"); + meta = pl_find_meta_raw (it, "artist"); } } } } else if (*fmt == 'C') { - meta = pl_find_meta (it, "composer"); + meta = pl_find_meta_raw (it, "composer"); } else if (*fmt == 'n') { - meta = pl_find_meta (it, "track"); + meta = pl_find_meta_raw (it, "track"); if (meta) { // check if it's numbers only const char *p = meta; @@ -3065,19 +3065,19 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, } } else if (*fmt == 'N') { - meta = pl_find_meta (it, "numtracks"); + meta = pl_find_meta_raw (it, "numtracks"); } else if (*fmt == 'y') { - meta = pl_find_meta (it, "year"); + meta = pl_find_meta_raw (it, "year"); } else if (*fmt == 'g') { - meta = pl_find_meta (it, "genre"); + meta = pl_find_meta_raw (it, "genre"); } else if (*fmt == 'c') { - meta = pl_find_meta (it, "comment"); + meta = pl_find_meta_raw (it, "comment"); } else if (*fmt == 'r') { - meta = pl_find_meta (it, "copyright"); + meta = pl_find_meta_raw (it, "copyright"); } else if (*fmt == 'l') { const char *value = (duration = pl_format_duration (it, duration, dur, sizeof (dur))); @@ -3095,7 +3095,7 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, } } else if (*fmt == 'f') { - const char *f = pl_find_meta (it, ":URI"); + const char *f = pl_find_meta_raw (it, ":URI"); meta = strrchr (f, '/'); if (meta) { meta++; @@ -3105,7 +3105,7 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, } } else if (*fmt == 'F') { - meta = pl_find_meta (it, ":URI"); + meta = pl_find_meta_raw (it, ":URI"); } else if (*fmt == 'T') { char *t = tags; @@ -3152,7 +3152,7 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, } else if (*fmt == 'd') { // directory - const char *f = pl_find_meta (it, ":URI"); + const char *f = pl_find_meta_raw (it, ":URI"); const char *end = strrchr (f, '/'); if (!end) { meta = ""; // got relative path without folder (should not happen) @@ -3177,7 +3177,7 @@ pl_format_title_int (const char *escape_chars, playItem_t *it, int idx, char *s, } } else if (*fmt == 'D') { - const char *f = pl_find_meta (it, ":URI"); + const char *f = pl_find_meta_raw (it, ":URI"); // directory with path const char *end = strrchr (f, '/'); if (!end) { @@ -3314,14 +3314,14 @@ pl_sort_compare_str (playItem_t *a, playItem_t *b) { int t1; int t2; const char *t; - t = pl_find_meta (a, "track"); + t = pl_find_meta_raw (a, "track"); if (t && !isdigit (*t)) { t1 = 999999; } else { t1 = t ? atoi (t) : -1; } - t = pl_find_meta (b, "track"); + t = pl_find_meta_raw (b, "track"); if (t && !isdigit (*t)) { t2 = 999999; } @@ -3663,7 +3663,7 @@ plt_search_process (playlist_t *playlist, const char *text) { if (*text) { DB_metaInfo_t *m = NULL; for (m = it->meta; m; m = m->next) { - if (m->key[0] == ':' || m->key[0] == '_') { + if (m->key[0] == ':' || m->key[0] == '_' || m->key[0] == '!') { break; } if (m->key!=cuesheet && m->key!=log) { @@ -3685,7 +3685,7 @@ plt_search_process (playlist_t *playlist, const char *text) { } } else if (utfcasestr_fast (m->value, lc)) { - //fprintf (stderr, "%s -> %s match (%s.%s)\n", text, m->value, pl_find_meta (it, ":URI"), m->key); + //fprintf (stderr, "%s -> %s match (%s.%s)\n", text, m->value, pl_find_meta_raw (it, ":URI"), m->key); // add to list it->next[PL_SEARCH] = NULL; if (playlist->tail[PL_SEARCH]) { diff --git a/playlist.h b/playlist.h index 2f9a9d6a..a517930b 100644 --- a/playlist.h +++ b/playlist.h @@ -244,9 +244,13 @@ pl_append_meta (playItem_t *it, const char *key, const char *value); // must be used in explicit pl_lock/unlock block // that makes it possible to avoid copying metadata on every access +// pl_find_meta may return overriden value (where the key is prefixed with '!') const char * pl_find_meta (playItem_t *it, const char *key); +const char * +pl_find_meta_raw (playItem_t *it, const char *key); + int pl_find_meta_int (playItem_t *it, const char *key, int def); diff --git a/plmeta.c b/plmeta.c index 21de208c..6f667a89 100644 --- a/plmeta.c +++ b/plmeta.c @@ -41,10 +41,10 @@ pl_add_meta (playItem_t *it, const char *key, const char *value) { return; } // find end of normal metadata - if (!normaltail && (m->key[0] == ':' || m->key[0] == '_')) { + if (!normaltail && (m->key[0] == ':' || m->key[0] == '_' || m->key[0] == '!')) { normaltail = tail; propstart = m; - if (key[0] != ':' && key[0] != '_') { + if (key[0] != ':' && key[0] != '_' && key[0] != '!') { break; } } @@ -63,7 +63,7 @@ pl_add_meta (playItem_t *it, const char *key, const char *value) { m->key = metacache_add_string (key); m->value = metacache_add_string (value); - if (key[0] == ':' || key[0] == '_') { + if (key[0] == ':' || key[0] == '_' || key[0] == '!') { if (tail) { tail->next = m; } @@ -86,7 +86,7 @@ pl_add_meta (playItem_t *it, const char *key, const char *value) { void pl_append_meta (playItem_t *it, const char *key, const char *value) { pl_lock (); - const char *old = pl_find_meta (it, key); + const char *old = pl_find_meta_raw (it, key); if (old && (!strcasecmp (key, "cuesheet") || !strcasecmp (key, "log"))) { pl_unlock (); @@ -192,6 +192,34 @@ const char * pl_find_meta (playItem_t *it, const char *key) { pl_lock (); DB_metaInfo_t *m = it->meta; + + if (key && key[0] == ':') { + // try to find an override + while (m) { + if (m->key[0] == '!' && !strcasecmp (key+1, m->key+1)) { + pl_unlock (); + return m->value; + } + m = m->next; + } + } + + m = it->meta; + while (m) { + if (!strcasecmp (key, m->key)) { + pl_unlock (); + return m->value; + } + m = m->next; + } + pl_unlock (); + return NULL; +} + +const char * +pl_find_meta_raw (playItem_t *it, const char *key) { + pl_lock (); + DB_metaInfo_t *m = it->meta; while (m) { if (!strcasecmp (key, m->key)) { pl_unlock (); @@ -257,7 +285,7 @@ pl_delete_all_meta (playItem_t *it) { DB_metaInfo_t *prev = NULL; while (m) { DB_metaInfo_t *next = m->next; - if (m->key[0] == ':') { + if (m->key[0] == ':' || m->key[0] == '_' || m->key[0] == '!') { prev = m; } else { diff --git a/plugins.c b/plugins.c index ff110913..d41b0777 100644 --- a/plugins.c +++ b/plugins.c @@ -328,6 +328,7 @@ static DB_functions_t deadbeef_api = { .metacache_remove_string = metacache_remove_string, .metacache_ref = metacache_ref, .metacache_unref = metacache_unref, + .pl_find_meta_raw = (const char *(*) (DB_playItem_t *it, const char *key))pl_find_meta_raw, }; DB_functions_t *deadbeef = &deadbeef_api; -- cgit v1.2.3