From b8a9a007517f939a637d515c48e4c4f42fda24be Mon Sep 17 00:00:00 2001 From: Alexey Yakovenko Date: Mon, 8 Feb 2010 22:35:34 +0100 Subject: tabbed playlist save/load --- common.h | 1 - conf.c | 3 + main.c | 24 +++----- playlist.c | 158 +++++++++++++++++++++++++++++++++++++++++--------- playlist.h | 8 +++ plugins/gtkui/gtkui.c | 1 + 6 files changed, 151 insertions(+), 44 deletions(-) diff --git a/common.h b/common.h index 0d8346c2..dfecb27a 100644 --- a/common.h +++ b/common.h @@ -24,7 +24,6 @@ // those are defined in main.c extern char confdir[1024]; // $HOME/.config extern char dbconfdir[1024]; // $HOME/.config/deadbeef -extern char defpl[1024]; // $HOME/.config/deadbeef/default.dbpl extern char sessfile[1024]; // $HOME/.config/deadbeef/session #endif // __COMMON_H diff --git a/conf.c b/conf.c index 34026763..b86e0836 100644 --- a/conf.c +++ b/conf.c @@ -160,6 +160,9 @@ conf_set_str (const char *key, const char *val) { } prev = it; } + if (!val) { + return; + } DB_conf_item_t *it = malloc (sizeof (DB_conf_item_t)); memset (it, 0, sizeof (DB_conf_item_t)); it->key = strdup (key); diff --git a/main.c b/main.c index 5e83ad3d..c5914531 100644 --- a/main.c +++ b/main.c @@ -66,7 +66,6 @@ // some common global variables char confdir[1024]; // $HOME/.config char dbconfdir[1024]; // $HOME/.config/deadbeef -char defpl[1024]; // $HOME/.config/deadbeef/default.dbpl // client-side commandline support // -1 error, program must exit with error code -1 @@ -403,7 +402,7 @@ atexit_handler (void) { fprintf (stderr, "atexit_handler\n"); if (!sigterm_handled) { fprintf (stderr, "handling atexit.\n"); - pl_save (defpl); + pl_save_all (); conf_save (); } } @@ -443,10 +442,6 @@ main (int argc, char *argv[]) { return -1; } } - if (snprintf (defpl, sizeof (defpl), "%s/deadbeef/default.dbpl", confdir) > sizeof (defpl)) { - fprintf (stderr, "fatal: out of memory while configuring\n"); - return -1; - } mkdir (confdir, 0755); if (snprintf (dbconfdir, sizeof (dbconfdir), "%s/deadbeef", confdir) > sizeof (dbconfdir)) { fprintf (stderr, "fatal: out of memory while configuring\n"); @@ -572,13 +567,6 @@ main (int argc, char *argv[]) { messagepump_init (); // required to push messages while handling commandline plug_load_all (); // required to add files to playlist from commandline - plt_add (0, "Default"); - plt_add (1, "Test"); - plt_add (2, "Test 2"); - plt_add (3, "Test 3"); - plt_add (4, "Test 4"); - plt_add (5, "Test 5"); - // execute server commands in local context int noloadpl = 0; if (argc > 1) { @@ -605,8 +593,14 @@ main (int argc, char *argv[]) { // start all subsystems volume_set_db (conf_get_float ("playback.volume", 0)); if (!noloadpl) { - pl_load (defpl); + pl_load_all (); } + //plt_add (plt_get_count (), "Test 1"); +// plt_add (plt_get_count (), "Test 2"); +// plt_add (plt_get_count (), "Test 3"); +// plt_add (plt_get_count (), "Test 4"); +// plt_add (plt_get_count (), "Test 5"); + plug_trigger_event_playlistchanged (); // this is old code left for backwards compatibility { @@ -622,7 +616,7 @@ main (int argc, char *argv[]) { player_mainloop (); // save config - pl_save (defpl); + pl_save_all (); conf_save (); { char sessfile[1024]; // $HOME/.config/deadbeef/session diff --git a/playlist.c b/playlist.c index b5086b19..b276c75f 100644 --- a/playlist.c +++ b/playlist.c @@ -39,6 +39,9 @@ #include "vfs.h" #include "conf.h" #include "utf8.h" +#include "common.h" + +#pragma GCC optimize("O0") // 1.0->1.1 changelog: // added sample-accurate seek positions for sub-tracks @@ -52,9 +55,6 @@ #define min(x,y) ((x)<(y)?(x):(y)) -static int pl_count[2]; -static float pl_totaltime = 0; - #define PLAYQUEUE_SIZE 100 static playItem_t *playqueue[100]; static int playqueue_count = 0; @@ -62,6 +62,24 @@ static int playqueue_count = 0; static int playlists_count = 0; static playlist_t *playlists_head = NULL; static playlist_t *playlist = NULL; // current playlist +static int plt_loading = 0; // disable sending event about playlist switch, config regen, etc + +static void +plt_gen_conf (void) { + if (plt_loading) { + return; + } + int cnt = plt_get_count (); + int i; + conf_remove_items ("playlist.tab."); + + playlist_t *p = playlists_head; + for (i = 0; i < cnt; i++, p = p->next) { + char s[100]; + snprintf (s, sizeof (s), "playlist.tab.%d", i); + conf_set_str (s, p->title); + } +} static void pl_item_free (playItem_t *it); @@ -80,7 +98,8 @@ plt_add (int before, const char *title) { playlist_t *p_before = NULL; playlist_t *p_after = playlists_head; - for (int i = 0; i < before; i++) { + int i; + for (i = 0; i < before; i++) { if (i >= before+1) { break; } @@ -93,7 +112,6 @@ plt_add (int before, const char *title) { } } - printf ("p_before %p, p_after %p, plt %p\n", p_before, p_after, plt); if (p_before) { p_before->next = plt; } @@ -101,13 +119,16 @@ plt_add (int before, const char *title) { playlists_head = plt; } plt->next = p_after; + playlists_count++; + if (!playlist) { playlist = plt; + if (!plt_loading) { + plug_trigger_event (DB_EV_PLAYLISTSWITCH, 0); + } } - printf ("playlists_head=%p\n", playlists_head); - - playlists_count++; + plt_gen_conf (); } void @@ -136,6 +157,8 @@ plt_remove (int plt) { free (p->title); free (p); playlists_count--; + + plt_gen_conf (); } void @@ -151,7 +174,9 @@ plt_set_curr (int plt) { } if (p != playlist) { playlist = p; - plug_trigger_event (DB_EV_PLAYLISTSWITCH, 0); + if (!plt_loading) { + plug_trigger_event (DB_EV_PLAYLISTSWITCH, 0); + } } } @@ -198,11 +223,11 @@ pl_free (void) { while (playlist->head[PL_MAIN]) { pl_remove (playlist->head[PL_MAIN]); } - if (playlist->current_row[PL_MAIN] >= pl_count[PL_MAIN]) { - playlist->current_row[PL_MAIN] = pl_count[PL_MAIN]-1; + if (playlist->current_row[PL_MAIN] >= playlist->count[PL_MAIN]) { + playlist->current_row[PL_MAIN] = playlist->count[PL_MAIN]-1; } - if (playlist->current_row[PL_SEARCH] >= pl_count[PL_SEARCH]) { - playlist->current_row[PL_SEARCH] = pl_count[PL_SEARCH]-1; + if (playlist->current_row[PL_SEARCH] >= playlist->count[PL_SEARCH]) { + playlist->current_row[PL_SEARCH] = playlist->count[PL_SEARCH]-1; } } @@ -898,7 +923,7 @@ pl_remove (playItem_t *it) { // remove from both lists list for (int iter = PL_MAIN; iter <= PL_SEARCH; iter++) { if (it->prev[iter] || it->next[iter] || playlist->head[iter] == it || playlist->tail[iter] == it) { - pl_count[iter]--; + playlist->count[iter]--; } if (it->prev[iter]) { it->prev[iter]->next[iter] = it->next[iter]; @@ -916,9 +941,9 @@ pl_remove (playItem_t *it) { // totaltime if (it->_duration > 0) { - pl_totaltime -= it->_duration; - if (pl_totaltime < 0) { - pl_totaltime = 0; + playlist->totaltime -= it->_duration; + if (playlist->totaltime < 0) { + playlist->totaltime = 0; } } pl_item_unref (it); @@ -928,7 +953,7 @@ pl_remove (playItem_t *it) { int pl_getcount (int iter) { - return pl_count[iter]; + return playlist->count[iter]; } int @@ -998,7 +1023,7 @@ pl_insert_item (playItem_t *after, playItem_t *it) { } } it->in_playlist = 1; - pl_count[PL_MAIN]++; + playlist->count[PL_MAIN]++; // shuffle it->shufflerating = rand (); @@ -1006,7 +1031,7 @@ pl_insert_item (playItem_t *after, playItem_t *it) { // totaltime if (it->_duration > 0) { - pl_totaltime += it->_duration; + playlist->totaltime += it->_duration; } return it; @@ -1225,7 +1250,7 @@ pl_save (const char *fname) { if (fwrite (&minorver, 1, 1, fp) != 1) { goto save_fail; } - uint32_t cnt = pl_count[PL_MAIN]; + uint32_t cnt = playlist->count[PL_MAIN]; if (fwrite (&cnt, 1, 4, fp) != 4) { goto save_fail; } @@ -1326,6 +1351,39 @@ save_fail: return -1; } +int +pl_save_all (void) { + playlist_t *p = playlists_head; + int i; + int cnt = plt_get_count (); + int curr = plt_get_curr (); + int err = 0; + // make folder + char path[1024]; + if (snprintf (path, sizeof (path), "%s/playlists", dbconfdir) > sizeof (path)) { + fprintf (stderr, "error: failed to make path string for playlists folder\n"); + return -1; + } + mkdir (path, 0755); + + plt_loading = 1; + for (i = 0; i < cnt; i++, p = p->next) { + plt_set_curr (i); + if (snprintf (path, sizeof (path), "%s/playlists/%d.dbpl", dbconfdir, i) > sizeof (path)) { + fprintf (stderr, "error: failed to make path string for playlists folder\n"); + err = -1; + break; + } + err = pl_save (path); + if (err < 0) { + break; + } + } + plt_set_curr (curr); + plt_loading = 0; + return err; +} + int pl_load (const char *fname) { pl_free (); @@ -1527,6 +1585,50 @@ load_fail: return -1; } +int +pl_load_all (void) { + int i = 0; + int err = 0; + char path[1024]; + DB_conf_item_t *it = conf_find ("playlist.tab.", NULL); + if (!it) { + fprintf (stderr, "INFO: loading legacy default playlist\n"); + // legacy (0.3.3 and earlier) + char defpl[1024]; // $HOME/.config/deadbeef/default.dbpl + if (snprintf (defpl, sizeof (defpl), "%s/deadbeef/default.dbpl", confdir) > sizeof (defpl)) { + fprintf (stderr, "error: cannot make string with default playlist path\n"); + return -1; + } + plt_add (plt_get_count (), "Default"); + return pl_load (defpl); + } + plt_loading = 1; + while (it) { + fprintf (stderr, "INFO: loading playlist %s\n", it->value); + if (!err) { + plt_add (plt_get_count (), it->value); + plt_set_curr (plt_get_count () - 1); + } + err = 0; + if (snprintf (path, sizeof (path), "%s/playlists/%d.dbpl", dbconfdir, i) > sizeof (path)) { + fprintf (stderr, "error: failed to make path string for playlist filename\n"); + err = -1; + } + else { + fprintf (stderr, "INFO: from file %s\n", path); + err = pl_load (path); + } + it = conf_find ("playlist.tab.", it); + fprintf (stderr, "conf_find returned %p\n", it); + i++; + } + plt_set_curr (0); + plt_loading = 0; + plt_gen_conf (); + plug_trigger_event (DB_EV_PLAYLISTSWITCH, 0); + return err; +} + void pl_select_all (void) { for (playItem_t *it = playlist->head[PL_MAIN]; it; it = it->next[PL_MAIN]) { @@ -1573,13 +1675,13 @@ pl_set_item_duration (playItem_t *it, float duration) { // if (pl_get_idx_of (it) != -1) { if (it->in_playlist) { if (it->_duration > 0) { - pl_totaltime -= it->_duration; + playlist->totaltime -= it->_duration; } if (duration > 0) { - pl_totaltime += duration; + playlist->totaltime += duration; } - if (pl_totaltime < 0) { - pl_totaltime = 0; + if (playlist->totaltime < 0) { + playlist->totaltime = 0; } } it->_duration = duration; @@ -1907,7 +2009,7 @@ pl_reset_cursor (void) { float pl_get_totaltime (void) { - return pl_totaltime; + return playlist->totaltime; } void @@ -2026,7 +2128,7 @@ pl_search_reset (void) { playlist->head[PL_SEARCH] = next; } playlist->tail[PL_SEARCH] = NULL; - pl_count[PL_SEARCH] = 0; + playlist->count[PL_SEARCH] = 0; } void @@ -2049,7 +2151,7 @@ pl_search_process (const char *text) { playlist->head[PL_SEARCH] = playlist->tail[PL_SEARCH] = it; } it->selected = 1; - pl_count[PL_SEARCH]++; + playlist->count[PL_SEARCH]++; break; } } diff --git a/playlist.h b/playlist.h index b3ea7925..4dd6909b 100644 --- a/playlist.h +++ b/playlist.h @@ -57,6 +57,8 @@ typedef struct playItem_s { typedef struct playlist_s { char *title; + int count[2]; + float totaltime; playItem_t *head[PL_MAX_ITERATORS]; // head of linked list playItem_t *tail[PL_MAX_ITERATORS]; // tail of linked list int current_row[PL_MAX_ITERATORS]; // current row (cursor) @@ -171,9 +173,15 @@ pl_crop_selected (void); int pl_save (const char *fname); +int +pl_save_all (void); + int pl_load (const char *fname); +int +pl_load_all (void); + void pl_select_all (void); diff --git a/plugins/gtkui/gtkui.c b/plugins/gtkui/gtkui.c index 28bc8c9f..0ac4ccf9 100644 --- a/plugins/gtkui/gtkui.c +++ b/plugins/gtkui/gtkui.c @@ -35,6 +35,7 @@ #include "interface.h" #include "callbacks.h" #include "support.h" +#include "tabs.h" //#define trace(...) { fprintf(stderr, __VA_ARGS__); } #define trace(fmt,...) -- cgit v1.2.3