diff --git a/src/scrobbler/plugin.c b/src/scrobbler/plugin.c index 5924b56..28263d3 100644 --- a/src/scrobbler/plugin.c +++ b/src/scrobbler/plugin.c @@ -53,37 +53,45 @@ static void aud_hook_playback_begin(gpointer hook_data, gpointer user_data) gint playlist = aud_playlist_get_playing(); gint pos = aud_playlist_get_position(playlist); - if (aud_playlist_entry_get_length (playlist, pos, FALSE) < 30) - { - AUDDBG(" *** not submitting due to entry->length < 30"); - return; - } - gchar * filename = aud_playlist_entry_get_filename (playlist, pos); - if (ishttp (filename)) + gboolean is_http_source = ishttp (filename); + str_unref (filename); + + if (aud_playlist_entry_get_length (playlist, pos, FALSE) < 30 + && !is_http_source) { - AUDDBG(" *** not submitting due to HTTP source"); - str_unref (filename); + AUDDBG(" *** not submitting due to entry->length < 30"); return; } - str_unref (filename); sc_idle(m_scrobbler); if (submit_tuple) tuple_unref (submit_tuple); - submit_tuple = aud_playlist_entry_get_tuple (playlist, pos, FALSE); - if (! submit_tuple) - return; + { + Tuple *temp_tuple = aud_playlist_entry_get_tuple (playlist, pos, FALSE); + if (! temp_tuple) + return; + submit_tuple = tuple_copy (temp_tuple); + tuple_unref (temp_tuple); + } - sc_addentry(m_scrobbler, submit_tuple, tuple_get_int(submit_tuple, FIELD_LENGTH, NULL) / 1000); + if (is_http_source) + { + if (tuple_get_int(submit_tuple, FIELD_LENGTH, NULL) <= 0) + tuple_set_int(submit_tuple, FIELD_LENGTH, NULL, 240000); + } + + sc_addentry(m_scrobbler, submit_tuple, tuple_get_int(submit_tuple, FIELD_LENGTH, NULL) / 1000, is_http_source); if (!track_timeout) - track_timeout = g_timeout_add_seconds(1, sc_timeout, NULL); + track_timeout = g_timeout_add_seconds(1, sc_timeout, (gpointer)m_scrobbler); } static void aud_hook_playback_end(gpointer aud_hook_data, gpointer user_data) { + sc_playback_end(m_scrobbler); + sc_idle(m_scrobbler); if (track_timeout) diff --git a/src/scrobbler/scrobbler.c b/src/scrobbler/scrobbler.c index 1ac17ee..684101e 100644 --- a/src/scrobbler/scrobbler.c +++ b/src/scrobbler/scrobbler.c @@ -14,6 +14,7 @@ #include #include #include +#include #define SCROBBLER_CLI_ID "aud" #define SCROBBLER_HS_WAIT 1800 @@ -63,6 +64,7 @@ typedef struct { int utctime, track, len; int timeplayed; int numtries; + gboolean is_http_source; void *next; } item_t; @@ -172,6 +174,8 @@ static item_t *create_item(Tuple *tuple, int len) else item->album = fmt_escape(""); + item->is_http_source = FALSE; + item->next = NULL; return item; @@ -190,14 +194,17 @@ static item_t *q_put(Tuple *tuple, int t, int len) return q_additem(item); } -static item_t *set_np(Tuple *tuple, int len) +static item_t *set_np(Tuple *tuple, int len, gboolean is_http_source) { if (np_item != NULL) q_item_free (np_item); if ((np_item = create_item (tuple, len)) != NULL) + { AUDDBG ("Tracking now-playing track: %s - %s\n", np_item->artist, np_item->title); + np_item->is_http_source = is_http_source; + } return np_item; } @@ -262,6 +269,7 @@ static void q_free(void) while (q_get()); } +static int sc_submit_np(Tuple * tuple); /* isn't there better way for that? --desowin */ gboolean sc_timeout(gpointer data) @@ -271,6 +279,8 @@ gboolean sc_timeout(gpointer data) if (aud_drct_get_playing() && !aud_drct_get_paused()) np_item->timeplayed+=1; + if (!np_item->is_http_source) + { /* * Check our now-playing track to see if it should go into the queue */ @@ -284,10 +294,91 @@ gboolean sc_timeout(gpointer data) dump_queue(); } } + else + { + /* + * It is possibly a stream. So check if the track info has changed. + * This is for sure not the most efficient way to do this. + * But it is straight forward for now... + */ + + gint playlist = aud_playlist_get_playing(); + gint pos = aud_playlist_get_position(playlist); + + Tuple *submit_tuple = NULL; + { + Tuple *temp_tuple = aud_playlist_entry_get_tuple (playlist, pos, FALSE); + if (! temp_tuple) + return TRUE; + submit_tuple = tuple_copy (temp_tuple); + tuple_unref (temp_tuple); + } + + item_t* current_item = create_item(submit_tuple, tuple_get_int(submit_tuple, FIELD_LENGTH, NULL) / 1000); + if (! current_item) + return TRUE; + + AUDDBG("np: %s\ncurrent: %s\n", np_item->title, current_item->title); + + if ( strcmp(np_item->artist, current_item->artist) + || strcmp(np_item->title, current_item->title) + || strcmp(np_item->album, current_item->album) + || np_item->track != current_item->track ) + { + AUDDBG("submitting!!!\n"); + + current_item->is_http_source = TRUE; + + if (tuple_get_int(submit_tuple, FIELD_LENGTH, NULL) <= 0) + { + tuple_set_int(submit_tuple, FIELD_LENGTH, NULL, 240000); + current_item->len = 240; + } + + np_item->len = np_item->timeplayed; + + q_additem(np_item); + np_item = current_item; + dump_queue(); + + sc_idle((GMutex*)data); + + sc_submit_np(submit_tuple); + } + else + { + q_item_free(current_item); + + if (np_item->timeplayed > np_item->len) + { + /* Make sure that the track stays on now playing. */ + tuple_set_int(submit_tuple, FIELD_LENGTH, NULL, np_item->len * 1000); + sc_submit_np(submit_tuple); + np_item->len *= 2; + } + } + + tuple_unref (submit_tuple); + } + } return TRUE; } +void sc_playback_end(GMutex *mutex) +{ + if (np_item && np_item->is_http_source) + { + AUDDBG("submitting!!!\n"); + + np_item->len = np_item->timeplayed; + + q_additem(np_item); + np_item = NULL; + dump_queue(); + } +} + /* Error functions */ static void sc_throw_error(char *errortxt) @@ -1126,12 +1217,14 @@ void sc_init(char *uname, char *pwd, char *url) AUDDBG("scrobbler starting up\n"); } -void sc_addentry(GMutex *mutex, Tuple *tuple, int len) +void sc_addentry(GMutex *mutex, Tuple *tuple, int len, gboolean is_http_source) { g_mutex_lock(mutex); + AUDDBG("length: %d, %d\n", tuple_get_int(tuple, FIELD_LENGTH, NULL), len); + sc_submit_np(tuple); - set_np(tuple, len); + set_np(tuple, len, is_http_source); /* * This will help make sure the queue will be saved on a nasty diff --git a/src/scrobbler/scrobbler.h b/src/scrobbler/scrobbler.h index 2203696..545ae1a 100644 --- a/src/scrobbler/scrobbler.h +++ b/src/scrobbler/scrobbler.h @@ -14,9 +14,10 @@ gboolean sc_timeout(gpointer data); int sc_idle(GMutex *); void sc_init(char *, char *, char *); -void sc_addentry(GMutex *, Tuple *, int); +void sc_addentry(GMutex *, Tuple *, int, gboolean); void sc_cleaner(void); int sc_catch_error(void); char *sc_fetch_error(void); void sc_clear_error(void); +void sc_playback_end(GMutex *); #endif