Add scrobbler with support for Last.fm, Libre.fm and ListenBrainz

This commit is contained in:
Jonas Kvinge
2018-12-23 18:54:27 +01:00
parent 517285085a
commit 0d7e12e781
43 changed files with 3565 additions and 169 deletions

View File

@@ -68,6 +68,7 @@
#include "core/mimedata.h"
#include "core/tagreaderclient.h"
#include "core/song.h"
#include "core/timeconstants.h"
#include "collection/collection.h"
#include "collection/collectionbackend.h"
#include "collection/collectionplaylistitem.h"
@@ -116,6 +117,9 @@ const char *Playlist::kWriteMetadata = "write_metadata";
const int Playlist::kUndoStackSize = 20;
const int Playlist::kUndoItemLimit = 500;
const qint64 Playlist::kMinScrobblePointNsecs = 1ll * kNsecPerSec;
const qint64 Playlist::kMaxScrobblePointNsecs = 240ll * kNsecPerSec;
Playlist::Playlist(PlaylistBackend *backend, TaskManager *task_manager, CollectionBackend *collection, int id, const QString &special_type, bool favorite, QObject *parent)
: QAbstractListModel(parent),
is_loading_(false),
@@ -133,7 +137,10 @@ Playlist::Playlist(PlaylistBackend *backend, TaskManager *task_manager, Collecti
ignore_sorting_(false),
undo_stack_(new QUndoStack(this)),
special_type_(special_type),
cancel_restore_(false) {
cancel_restore_(false),
scrobbled_(false),
nowplaying_(false),
scrobble_point_(-1) {
undo_stack_->setUndoLimit(kUndoStackSize);
@@ -612,6 +619,9 @@ void Playlist::set_current_row(int i, bool is_stopping) {
Save();
}
UpdateScrobblePoint();
nowplaying_ = false;
}
Qt::ItemFlags Playlist::flags(const QModelIndex &index) const {
@@ -1488,6 +1498,8 @@ void Playlist::SetStreamMetadata(const QUrl &url, const Song &song) {
InformOfCurrentSongChange();
UpdateScrobblePoint();
}
void Playlist::ClearStreamMetadata() {
@@ -1495,6 +1507,7 @@ void Playlist::ClearStreamMetadata() {
if (!current_item()) return;
current_item()->ClearTemporaryMetadata();
UpdateScrobblePoint();
emit dataChanged(index(current_item_index_.row(), 0), index(current_item_index_.row(), ColumnCount-1));
@@ -1944,3 +1957,28 @@ void Playlist::SkipTracks(const QModelIndexList &source_indexes) {
}
void Playlist::UpdateScrobblePoint(qint64 seek_point_nanosec) {
const qint64 length = current_item_metadata().length_nanosec();
if (seek_point_nanosec <= 0) {
if (length == 0) {
scrobble_point_ = kMaxScrobblePointNsecs;
}
else {
scrobble_point_ = qBound(kMinScrobblePointNsecs, length / 2, kMaxScrobblePointNsecs);
}
}
else {
if (length <= 0) {
scrobble_point_ = seek_point_nanosec + kMaxScrobblePointNsecs;
}
else {
scrobble_point_ = qBound(seek_point_nanosec + kMinScrobblePointNsecs, seek_point_nanosec + (length / 2), seek_point_nanosec + kMaxScrobblePointNsecs);
}
}
scrobbled_ = false;
}

View File

@@ -160,6 +160,9 @@ class Playlist : public QAbstractListModel {
static const int kUndoStackSize;
static const int kUndoItemLimit;
static const qint64 kMinScrobblePointNsecs;
static const qint64 kMaxScrobblePointNsecs;
static bool CompareItems(int column, Qt::SortOrder order, PlaylistItemPtr a, PlaylistItemPtr b);
static QString column_name(Column column);
@@ -213,6 +216,13 @@ class Playlist : public QAbstractListModel {
QUndoStack *undo_stack() const { return undo_stack_; }
bool scrobbled() const { return scrobbled_; }
bool nowplaying() const { return nowplaying_; }
void set_scrobbled(bool state) { scrobbled_ = state; }
void set_nowplaying(bool state) { nowplaying_ = state; }
qint64 scrobble_point_nanosec() const { return scrobble_point_; }
void UpdateScrobblePoint(qint64 seek_point_nanosec = 0);
// Changing the playlist
void InsertItems (const PlaylistItemList &items, int pos = -1, bool play_now = false, bool enqueue = false, bool enqueue_next = false);
void InsertCollectionItems (const SongList &items, int pos = -1, bool play_now = false, bool enqueue = false, bool enqueue_next = false);
@@ -373,6 +383,11 @@ private:
// Cancel async restore if songs are already replaced
bool cancel_restore_;
bool scrobbled_;
bool nowplaying_;
qint64 scrobble_point_;
};
// QDataStream& operator <<(QDataStream&, const Playlist*);