nega0 / pianobarfly

pandora2[mp3|m4a]
https://github.com/nega0/pianobarfly
Other
62 stars 31 forks source link

Only rip "loved" songs (patch included) #64

Open fengshaun opened 8 years ago

fengshaun commented 8 years ago

It would be nice to be able to only rip the "loved" songs as to not fill up the local collection quickly with every song that's played.

fengshaun commented 8 years ago

preliminary patch. It deletes a file if a song is not rated by the end of its play time. I haven't looked into how to modify player->fly from BarUi since BarUi handles when a song gets rated and is separate from BarFly, so I resorted to updating fly->loved after every input processing.

This patch also adds a new option: download_only_loved which is a boolean and defaults to true.

Hope it's useful. Feel free to modify and fix anything.

diff --git a/src/fly.c b/src/fly.c
index 581a1a1..ea93929 100644
--- a/src/fly.c
+++ b/src/fly.c
@@ -290,7 +290,7 @@ static int _BarFlyFileDelete(BarFly_t const* fly,
        /*
         * Delete the file.
         */
-       BarUiMsg(settings, MSG_INFO, "Deleting partially recorded file (%s).\n",
+       BarUiMsg(settings, MSG_INFO, "Deleting partial or unloved recorded file (%s).\n",
                fly->audio_file_path);
        status = unlink(fly->audio_file_path);
        if (status != 0) {
@@ -1138,9 +1138,9 @@ int BarFlyClose(BarFly_t* fly, BarSettings_t const* settings)
        }

        /*
-        * Delete the file if it was not complete.
+        * Delete the file if it was not complete or not loved.
         */
-       if (!fly->completed) {
+       if (!fly->completed || (settings->downloadOnlyLoved && !fly->loved)) {
            fly->status = DELETING;
            status = _BarFlyFileDelete(fly, settings);
            if (status != 0) {
@@ -1292,6 +1292,7 @@ int BarFlyOpen(BarFly_t* fly, PianoSong_t const* song,
    memset(&output_fly, 0, sizeof(BarFly_t));
    output_fly.audio_file = NULL;
    output_fly.completed = false;
+   output_fly.loved = false;
    output_fly.status = NOT_RECORDING;

    /*
@@ -1306,6 +1307,7 @@ int BarFlyOpen(BarFly_t* fly, PianoSong_t const* song,
    output_fly.audio_format = song->audioFormat;
    strncpy(output_fly.stationName, fly->stationName, strlen(fly->stationName) + 1);
    output_fly.stationName[BAR_FLY_NAME_LENGTH - 1] = '\0';
+   output_fly.loved = song->rating == 1 ? true : false;

    output_fly.cover_art_url = strdup(song->coverArt);
    if (output_fly.cover_art_url == NULL) {
@@ -1415,7 +1417,7 @@ char const* BarFlyStatusGet(BarFly_t* fly)
            break;

        case (DELETING):
-           string = "Deleting (partial file)";
+           string = "Deleting";
            break;

        case (TAGGING):
@@ -1469,6 +1471,10 @@ int BarFlyWrite(BarFly_t* fly, void const* data, size_t data_size)
     * Write the given data buffer to the audio file.
     */
    if (!fly->completed) {
+       if (data_size == 0) {
+           goto end;
+       }
+
        assert(fly->audio_file != NULL);
        status = fwrite(data, data_size, 1, fly->audio_file);
        if (status != 1) {
diff --git a/src/fly.h b/src/fly.h
index 0fd92db..e200512 100644
--- a/src/fly.h
+++ b/src/fly.h
@@ -85,6 +85,11 @@ typedef struct BarFly {
     * set to true from the start.
     */
    bool completed;
+
+   /**
+    * Whether the song is loved
+    */
+   bool loved;

    /**
     * The song's artist.
diff --git a/src/main.c b/src/main.c
index ce3f736..d6e0423 100644
--- a/src/main.c
+++ b/src/main.c
@@ -396,6 +396,7 @@ static void BarMainLoop (BarApp_t *app) {
        }

        BarMainHandleUserInput (app);
+       app->player.fly.loved = app->playlist->rating == 1 ? true : false;

        /* show time */
        if (app->player.mode < PLAYER_FINISHED_PLAYBACK) {
diff --git a/src/player.c b/src/player.c
index b4f0c9b..3c2cfdb 100644
--- a/src/player.c
+++ b/src/player.c
@@ -102,6 +102,13 @@ static inline signed short int applyReplayGain (const signed short int value,
  */
 static inline int BarPlayerBufferFill (struct audioPlayer *player,
        const char *data, const size_t dataSize) {
+   /* dataSize is 0 at the beginning of the song, but everything
+    * works anyway
+    */
+   if (dataSize == 0) {
+       return 1;
+   }
+
    /* fill buffer */
    if (player->bufferFilled + dataSize > BAR_PLAYER_BUFSIZE) {
        BarUiMsg (player->settings, MSG_ERR, "Buffer overflow!\n");
diff --git a/src/settings.c b/src/settings.c
index 37da926..a3452e0 100644
--- a/src/settings.c
+++ b/src/settings.c
@@ -128,6 +128,7 @@ void BarSettingsRead (BarSettings_t *settings) {
    /* apply defaults */
    settings->audioQuality = PIANO_AQ_HIGH;
    settings->autoselect = true;
+   settings->downloadOnlyLoved = true;
    settings->history = 5;
    settings->volume = 0;
    settings->maxPlayerErrors = 5;
@@ -309,6 +310,8 @@ void BarSettingsRead (BarSettings_t *settings) {
                settings->fifo = strdup (val);
            } else if (streq ("autoselect", key)) {
                settings->autoselect = atoi (val);
+           } else if (streq ("download_only_loved", key)) {
+               settings->downloadOnlyLoved = atoi (val);
            } else if (streq ("tls_fingerprint", key)) {
                /* expects 40 byte hex-encoded sha1 */
                if (strlen (val) == 40) {
diff --git a/src/settings.h b/src/settings.h
index 5115ff3..5c9467f 100644
--- a/src/settings.h
+++ b/src/settings.h
@@ -85,6 +85,7 @@ typedef struct {

 typedef struct {
    bool autoselect;
+   bool downloadOnlyLoved;
    unsigned int history, maxPlayerErrors;
    int volume;
    BarStationSorting_t sortOrder;