Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 35 additions & 11 deletions src/library/dao/playlistdao.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -246,6 +246,23 @@ bool PlaylistDAO::isPlaylistLocked(const int playlistId) const {
return false;
}

bool PlaylistDAO::removeTracksFromPlaylist(const int playlistId, const int startIndex) {
// Retain the first track if it is loaded in a deck
ScopedTransaction transaction(m_database);
QSqlQuery query(m_database);
query.prepare("DELETE FROM PlaylistTracks "
"WHERE playlist_id=:id AND position>=:pos");
query.bindValue(":id", playlistId);
query.bindValue(":pos", startIndex);
if (!query.exec()) {
LOG_FAILED_QUERY(query);
return false;
}
transaction.commit();
emit(changed(playlistId));
return true;
}

bool PlaylistDAO::appendTracksToPlaylist(const QList<TrackId>& trackIds, const int playlistId) {
// qDebug() << "PlaylistDAO::appendTracksToPlaylist"
// << QThread::currentThread() << m_database.connectionName();
Expand Down Expand Up @@ -1011,21 +1028,28 @@ void PlaylistDAO::setAutoDJProcessor(AutoDJProcessor* pAutoDJProcessor) {
m_pAutoDJProcessor = pAutoDJProcessor;
}

void PlaylistDAO::sendToAutoDJ(const QList<TrackId>& trackIds, bool bTop) {
void PlaylistDAO::sendToAutoDJ(const QList<TrackId>& trackIds, AutoDJSendLoc loc) {
int iAutoDJPlaylistId = getPlaylistIdFromName(AUTODJ_TABLE);
if (iAutoDJPlaylistId == -1) {
return;
}

if (bTop) {
int position = 1;
if (m_pAutoDJProcessor && m_pAutoDJProcessor->nextTrackLoaded()) {
// Load track to position two because position one is
// already loaded to the player
position = 2;
}
insertTracksIntoPlaylist(trackIds, iAutoDJPlaylistId, position);
} else {
appendTracksToPlaylist(trackIds, iAutoDJPlaylistId);
// If the first track is already loaded to the player,
// alter the playlist only below the first track
int position =
(m_pAutoDJProcessor && m_pAutoDJProcessor->nextTrackLoaded()) ? 2 : 1;

switch (loc) {
case AutoDJSendLoc::TOP:
insertTracksIntoPlaylist(trackIds, iAutoDJPlaylistId, position);
break;
case AutoDJSendLoc::BOTTOM:
appendTracksToPlaylist(trackIds, iAutoDJPlaylistId);
break;
case AutoDJSendLoc::REPLACE:
if (removeTracksFromPlaylist(iAutoDJPlaylistId, position)) {
appendTracksToPlaylist(trackIds, iAutoDJPlaylistId);
}
break;
}
}
9 changes: 8 additions & 1 deletion src/library/dao/playlistdao.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@ class PlaylistDAO : public QObject, public virtual DAO {
PLHT_UNKNOWN = -1
};

enum class AutoDJSendLoc {
TOP,
BOTTOM,
REPLACE,
};

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this enum defined in the right place? Should it be scoped? It leads to e.g. PlaylistDAO::AutoDJSendLoc::BOTTOM, which seems a little ugly.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's fine with me -- regardless it'll be easy to move later.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hm, maybe it should eject the loaded, stopped track, remove it from the top of the queue, and load the new first track in the queue.

Copy link
Copy Markdown
Contributor Author

@potocpav potocpav Jan 31, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like a more useful variant to me

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would not touch the track, loaded on the deck. This could be an action out of sight.
Removing the top track from Auto DJ will remove the loaded track anyway if the user enables AutoDJ.

PlaylistDAO(QSqlDatabase& database);
virtual ~PlaylistDAO();

Expand Down Expand Up @@ -108,7 +114,7 @@ class PlaylistDAO : public QObject, public virtual DAO {
void getPlaylistsTrackIsIn(TrackId trackId, QSet<int>* playlistSet) const;

void setAutoDJProcessor(AutoDJProcessor* pAutoDJProcessor);
void sendToAutoDJ(const QList<TrackId>& trackIds, bool bTop);
void sendToAutoDJ(const QList<TrackId>& trackIds, AutoDJSendLoc loc);

signals:
void added(int playlistId);
Expand All @@ -120,6 +126,7 @@ class PlaylistDAO : public QObject, public virtual DAO {
void lockChanged(int playlistId);

private:
bool removeTracksFromPlaylist(const int playlistId, const int startIndex);
void removeTracksFromPlaylistsInner(const QStringList& idList);
void searchForDuplicateTrack(const int fromPosition,
const int toPosition,
Expand Down
8 changes: 6 additions & 2 deletions src/library/dlganalysis.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -88,15 +88,19 @@ void DlgAnalysis::loadSelectedTrackToGroup(QString group, bool play) {
m_pAnalysisLibraryTableView->loadSelectedTrackToGroup(group, play);
}

void DlgAnalysis::slotSendToAutoDJ() {
void DlgAnalysis::slotSendToAutoDJBottom() {
// append to auto DJ
m_pAnalysisLibraryTableView->slotSendToAutoDJ();
m_pAnalysisLibraryTableView->slotSendToAutoDJBottom();
}

void DlgAnalysis::slotSendToAutoDJTop() {
m_pAnalysisLibraryTableView->slotSendToAutoDJTop();
}

void DlgAnalysis::slotSendToAutoDJReplace() {
m_pAnalysisLibraryTableView->slotSendToAutoDJReplace();
}

void DlgAnalysis::moveSelection(int delta) {
m_pAnalysisLibraryTableView->moveSelection(delta);
}
Expand Down
3 changes: 2 additions & 1 deletion src/library/dlganalysis.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,9 @@ class DlgAnalysis : public QWidget, public Ui::DlgAnalysis, public virtual Libra
bool hasFocus() const override;
void loadSelectedTrack() override;
void loadSelectedTrackToGroup(QString group, bool play) override;
void slotSendToAutoDJ() override;
void slotSendToAutoDJBottom() override;
void slotSendToAutoDJTop() override;
void slotSendToAutoDJReplace() override;
void moveSelection(int delta) override;
inline const QString currentSearch() {
return m_pAnalysisLibraryTableModel->currentSearch();
Expand Down
2 changes: 1 addition & 1 deletion src/library/librarycontrol.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -285,7 +285,7 @@ void LibraryControl::slotAutoDjAddBottom(double v) {
if (!activeView) {
return;
}
activeView->slotSendToAutoDJ();
activeView->slotSendToAutoDJBottom();
}
}

Expand Down
3 changes: 2 additions & 1 deletion src/library/libraryview.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,9 @@ class LibraryView {
// track. Does nothing otherwise.
virtual void loadSelectedTrack() {};

virtual void slotSendToAutoDJ() {};
virtual void slotSendToAutoDJBottom() {};
virtual void slotSendToAutoDJTop() {};
virtual void slotSendToAutoDJReplace() {};

// If applicable, requests that the LibraryView load the selected track to
// the specified group. Does nothing otherwise.
Expand Down
8 changes: 6 additions & 2 deletions src/library/recording/dlgrecording.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -89,14 +89,18 @@ void DlgRecording::loadSelectedTrack() {
m_pTrackTableView->loadSelectedTrack();
}

void DlgRecording::slotSendToAutoDJ() {
m_pTrackTableView->slotSendToAutoDJ();
void DlgRecording::slotSendToAutoDJBottom() {
m_pTrackTableView->slotSendToAutoDJBottom();
}

void DlgRecording::slotSendToAutoDJTop() {
m_pTrackTableView->slotSendToAutoDJTop();
}

void DlgRecording::slotSendToAutoDJReplace() {
m_pTrackTableView->slotSendToAutoDJReplace();
}

void DlgRecording::loadSelectedTrackToGroup(QString group, bool play) {
m_pTrackTableView->loadSelectedTrackToGroup(group, play);
}
Expand Down
3 changes: 2 additions & 1 deletion src/library/recording/dlgrecording.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,9 @@ class DlgRecording : public QWidget, public Ui::DlgRecording, public virtual Lib
void onShow() override;
bool hasFocus() const override;
void loadSelectedTrack() override;
void slotSendToAutoDJ() override;
void slotSendToAutoDJBottom() override;
void slotSendToAutoDJTop() override;
void slotSendToAutoDJReplace() override;
void loadSelectedTrackToGroup(QString group, bool play) override;
void moveSelection(int delta) override;
inline const QString currentSearch() { return m_proxyModel.currentSearch(); }
Expand Down
34 changes: 22 additions & 12 deletions src/widget/wtracktableview.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@
#include "library/coverartcache.h"
#include "library/dlgtrackinfo.h"
#include "library/librarytablemodel.h"
#include "library/trackcollection.h"
#include "control/controlobject.h"
#include "control/controlproxy.h"
#include "track/track.h"
Expand Down Expand Up @@ -117,8 +116,9 @@ WTrackTableView::~WTrackTableView() {
delete m_pReloadMetadataAct;
delete m_pReloadMetadataFromMusicBrainzAct;
delete m_pAddToPreviewDeck;
delete m_pAutoDJAct;
delete m_pAutoDJBottomAct;
delete m_pAutoDJTopAct;
delete m_pAutoDJReplaceAct;
delete m_pRemoveAct;
delete m_pHideAct;
delete m_pUnhideAct;
Expand Down Expand Up @@ -383,13 +383,18 @@ void WTrackTableView::createActions() {
connect(m_pFileBrowserAct, SIGNAL(triggered()),
this, SLOT(slotOpenInFileBrowser()));

m_pAutoDJAct = new QAction(tr("Add to Auto DJ Queue (bottom)"), this);
connect(m_pAutoDJAct, SIGNAL(triggered()), this, SLOT(slotSendToAutoDJ()));
m_pAutoDJBottomAct = new QAction(tr("Add to Auto-DJ Queue (bottom)"), this);
connect(m_pAutoDJBottomAct, SIGNAL(triggered()),
this, SLOT(slotSendToAutoDJBottom()));

m_pAutoDJTopAct = new QAction(tr("Add to Auto DJ Queue (top)"), this);
connect(m_pAutoDJTopAct, SIGNAL(triggered()),
this, SLOT(slotSendToAutoDJTop()));

m_pAutoDJReplaceAct = new QAction(tr("Add to Auto-DJ Queue (replace)"), this);
connect(m_pAutoDJReplaceAct, SIGNAL(triggered()),
this, SLOT(slotSendToAutoDJReplace()));

m_pReloadMetadataAct = new QAction(tr("Reload Metadata from File"), this);
connect(m_pReloadMetadataAct, SIGNAL(triggered()),
this, SLOT(slotReloadTrackMetadata()));
Expand Down Expand Up @@ -465,10 +470,10 @@ void WTrackTableView::slotMouseDoubleClicked(const QModelIndex &index) {
}
switch (action) {
case DlgPrefLibrary::ADD_TRACK_BOTTOM:
sendToAutoDJ(false); // add track to Auto-DJ Queue (bottom)
sendToAutoDJ(PlaylistDAO::AutoDJSendLoc::BOTTOM); // add track to Auto-DJ Queue (bottom)
break;
case DlgPrefLibrary::ADD_TRACK_TOP:
sendToAutoDJ(true); // add track to Auto-DJ Queue (top)
sendToAutoDJ(PlaylistDAO::AutoDJSendLoc::TOP); // add track to Auto-DJ Queue (top)
break;
default: // load track to next available deck
TrackModel* trackModel = getTrackModel();
Expand Down Expand Up @@ -726,8 +731,9 @@ void WTrackTableView::contextMenuEvent(QContextMenuEvent* event) {
m_pMenu->clear();

if (modelHasCapabilities(TrackModel::TRACKMODELCAPS_ADDTOAUTODJ)) {
m_pMenu->addAction(m_pAutoDJAct);
m_pMenu->addAction(m_pAutoDJBottomAct);
m_pMenu->addAction(m_pAutoDJTopAct);
m_pMenu->addAction(m_pAutoDJReplaceAct);
m_pMenu->addSeparator();
}

Expand Down Expand Up @@ -1305,16 +1311,20 @@ void WTrackTableView::loadSelectedTrackToGroup(QString group, bool play) {
loadSelectionToGroup(group, play);
}

void WTrackTableView::slotSendToAutoDJ() {
void WTrackTableView::slotSendToAutoDJBottom() {
// append to auto DJ
sendToAutoDJ(false); // bTop = false
sendToAutoDJ(PlaylistDAO::AutoDJSendLoc::BOTTOM);
}

void WTrackTableView::slotSendToAutoDJTop() {
sendToAutoDJ(true); // bTop = true
sendToAutoDJ(PlaylistDAO::AutoDJSendLoc::TOP);
}

void WTrackTableView::slotSendToAutoDJReplace() {
sendToAutoDJ(PlaylistDAO::AutoDJSendLoc::REPLACE);
}

void WTrackTableView::sendToAutoDJ(bool bTop) {
void WTrackTableView::sendToAutoDJ(PlaylistDAO::AutoDJSendLoc loc) {
if (!modelHasCapabilities(TrackModel::TRACKMODELCAPS_ADDTOAUTODJ)) {
return;
}
Expand Down Expand Up @@ -1343,7 +1353,7 @@ void WTrackTableView::sendToAutoDJ(bool bTop) {
m_pTrackCollection->getTrackDAO().unhideTracks(trackIds);

// TODO(XXX): Care whether the append succeeded.
playlistDao.sendToAutoDJ(trackIds, bTop);
playlistDao.sendToAutoDJ(trackIds, loc);
}

void WTrackTableView::slotReloadTrackMetadata() {
Expand Down
10 changes: 7 additions & 3 deletions src/widget/wtracktableview.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
#include "library/coverart.h"
#include "library/dlgtagfetcher.h"
#include "library/libraryview.h"
#include "library/trackcollection.h"
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is to pull in PlaylistDAO::AutoDJSendLoc

#include "library/trackmodel.h" // Can't forward declare enums
#include "track/track.h"
#include "util/duration.h"
Expand Down Expand Up @@ -44,8 +45,9 @@ class WTrackTableView : public WLibraryTableView {
void slotPurge();
void onSearchStarting();
void onSearchCleared();
void slotSendToAutoDJ() override;
void slotSendToAutoDJBottom() override;
void slotSendToAutoDJTop() override;
void slotSendToAutoDJReplace() override;

private slots:
void slotRemove();
Expand Down Expand Up @@ -79,7 +81,8 @@ class WTrackTableView : public WLibraryTableView {
void slotTagFetcherClosed();

private:
void sendToAutoDJ(bool bTop);

void sendToAutoDJ(PlaylistDAO::AutoDJSendLoc loc);
void showTrackInfo(QModelIndex index);
void showDlgTagFetcher(QModelIndex index);
void createActions();
Expand Down Expand Up @@ -128,8 +131,9 @@ class WTrackTableView : public WLibraryTableView {
QAction* m_pAddToPreviewDeck;

// Send to Auto-DJ Action
QAction *m_pAutoDJAct;
QAction *m_pAutoDJBottomAct;
QAction *m_pAutoDJTopAct;
QAction *m_pAutoDJReplaceAct;

// Remove from table
QAction *m_pRemoveAct;
Expand Down