diff --git a/autotests/alltracksproxymodeltest.cpp b/autotests/alltracksproxymodeltest.cpp index 9a90d42a..83d5d8b3 100644 --- a/autotests/alltracksproxymodeltest.cpp +++ b/autotests/alltracksproxymodeltest.cpp @@ -1,524 +1,524 @@ /* * Copyright 2015-2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "databasetestdata.h" #include "musicaudiotrack.h" #include "databaseinterface.h" #include "models/datamodel.h" #include "models/alltracksproxymodel.h" #include "qabstractitemmodeltester.h" #include #include #include #include #include #include #include #include #include #include #include #include class AllTracksProxyModelTests: public QObject, public DatabaseTestData { Q_OBJECT private Q_SLOTS: void initTestCase() { qRegisterMetaType>("QHash"); qRegisterMetaType>("QHash"); qRegisterMetaType>>("QHash>"); qRegisterMetaType>("QVector"); qRegisterMetaType>("QHash"); } void removeOneTrack() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); AllTracksProxyModel proxyTracksModel; QAbstractItemModelTester proxyTestModel(&proxyTracksModel); proxyTracksModel.setSourceModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&proxyTracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&proxyTracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 23); auto trackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist1"), QStringLiteral("album1"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(trackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 1); QCOMPARE(endRemoveRowsSpy.count(), 1); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 22); } void removeOneAlbum() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); AllTracksProxyModel proxyTracksModel; QAbstractItemModelTester proxyTestModel(&proxyTracksModel); proxyTracksModel.setSourceModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&proxyTracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&proxyTracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 23); auto firstTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist2"), QStringLiteral("album3"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(firstTrackId); auto secondTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track2"), QStringLiteral("artist2"), QStringLiteral("album3"), 2, 1); auto secondTrack = musicDb.trackDataFromDatabaseId(secondTrackId); auto thirdTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track3"), QStringLiteral("artist2"), QStringLiteral("album3"), 3, 1); auto thirdTrack = musicDb.trackDataFromDatabaseId(thirdTrackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl() , secondTrack[DatabaseInterface::ResourceRole].toUrl(), thirdTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 3); QCOMPARE(endRemoveRowsSpy.count(), 3); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 20); } void addOneTrack() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); AllTracksProxyModel proxyTracksModel; QAbstractItemModelTester proxyTestModel(&proxyTracksModel); proxyTracksModel.setSourceModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&proxyTracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&proxyTracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist2"), QStringLiteral("album4"), QStringLiteral("artist2"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 5); QCOMPARE(proxyTracksModel.rowCount(), 24); } void addOneAlbum() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); AllTracksProxyModel proxyTracksModel; QAbstractItemModelTester proxyTestModel(&proxyTracksModel); proxyTracksModel.setSourceModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&proxyTracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&proxyTracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist2"), QStringLiteral("album4"), QStringLiteral("artist2"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); auto newCover = QUrl::fromLocalFile(QStringLiteral("album5")); auto newCovers = QHash(); newCovers[QStringLiteral("album5")] = newCover; auto newFiles2 = QList(); for (const auto &oneTrack : newTracks) { newFiles2.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(newTracks, newCovers); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 5); QCOMPARE(proxyTracksModel.rowCount(), 24); } void modifyOneTrack() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); AllTracksProxyModel proxyTracksModel; QAbstractItemModelTester proxyTestModel(&proxyTracksModel); proxyTracksModel.setSourceModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&proxyTracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&proxyTracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$1"), QStringLiteral("0"), QStringLiteral("track1"), QStringLiteral("artist1"), QStringLiteral("album1"), QStringLiteral("Various Artists"), 1, 1, QTime::fromMSecsSinceStartOfDay(1), {QUrl::fromLocalFile(QStringLiteral("/$1"))}, QDateTime::fromMSecsSinceEpoch(1), {QUrl::fromLocalFile(QStringLiteral("file://image$1"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 1); QCOMPARE(proxyTracksModel.rowCount(), 23); const auto &dataChangedSignal = dataChangedSpy.constFirst(); QCOMPARE(dataChangedSignal.size(), 3); auto changedIndex = dataChangedSignal.constFirst().toModelIndex(); QCOMPARE(proxyTracksModel.data(changedIndex, DatabaseInterface::ColumnsRoles::RatingRole).isValid(), true); QCOMPARE(proxyTracksModel.data(changedIndex, DatabaseInterface::ColumnsRoles::RatingRole).toInt(), 5); } void addEmptyTracksList() { DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); AllTracksProxyModel proxyTracksModel; QAbstractItemModelTester proxyTestModel(&proxyTracksModel); proxyTracksModel.setSourceModel(&tracksModel); auto newTracks = DataModel::ListTrackDataType{}; QSignalSpy beginInsertRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&proxyTracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&proxyTracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); tracksModel.tracksAdded(newTracks); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 0); } void addTracksListTwice() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); AllTracksProxyModel proxyTracksModel; QAbstractItemModelTester proxyTestModel(&proxyTracksModel); proxyTracksModel.setSourceModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&proxyTracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&proxyTracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&proxyTracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(proxyTracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist2"), QStringLiteral("album4"), QStringLiteral("artist2"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 5); QCOMPARE(proxyTracksModel.rowCount(), 24); } }; QTEST_GUILESS_MAIN(AllTracksProxyModelTests) #include "alltracksproxymodeltest.moc" diff --git a/autotests/datamodeltest.cpp b/autotests/datamodeltest.cpp index 98872abb..b9fb6b06 100644 --- a/autotests/datamodeltest.cpp +++ b/autotests/datamodeltest.cpp @@ -1,1584 +1,1585 @@ /* * Copyright 2015-2017 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "databasetestdata.h" #include "musicaudiotrack.h" #include "databaseinterface.h" #include "models/datamodel.h" #include "qabstractitemmodeltester.h" #include #include #include #include #include #include #include #include #include #include #include #include class DataModelTests: public QObject, public DatabaseTestData { Q_OBJECT private Q_SLOTS: void initTestCase() { qRegisterMetaType>("QHash"); qRegisterMetaType>("QHash"); qRegisterMetaType>("QList"); qRegisterMetaType>("QVector"); qRegisterMetaType>("QHash"); } void removeOneTrack() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &albumsModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackRemoved, &albumsModel, &DataModel::trackRemoved); connect(&musicDb, &DatabaseInterface::trackModified, &albumsModel, &DataModel::trackModified); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initializeById(nullptr, nullptr, ElisaUtils::Track, - musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::FilterById, {}, {}, + musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); albumsModel.tracksAdded(musicDb.albumData(musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists")))); QCOMPARE(albumsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto trackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist1"), QStringLiteral("album1"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(trackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(albumsModel.rowCount(), 3); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 1); QCOMPARE(endRemoveRowsSpy.count(), 1); QCOMPARE(dataChangedSpy.count(), 0); } void removeOneAlbum() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &albumsModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackRemoved, &albumsModel, &DataModel::trackRemoved); connect(&musicDb, &DatabaseInterface::trackModified, &albumsModel, &DataModel::trackModified); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initializeById(nullptr, nullptr, ElisaUtils::Track, - musicDb.albumIdFromTitleAndArtist(QStringLiteral("album3"), QStringLiteral("artist2"))); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::FilterById, {}, {}, + musicDb.albumIdFromTitleAndArtist(QStringLiteral("album3"), QStringLiteral("artist2"))); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); albumsModel.tracksAdded(musicDb.albumData(musicDb.albumIdFromTitleAndArtist(QStringLiteral("album3"), QStringLiteral("artist2")))); QCOMPARE(albumsModel.rowCount(), 3); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto firstTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist2"), QStringLiteral("album3"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(firstTrackId); auto secondTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track2"), QStringLiteral("artist2"), QStringLiteral("album3"), 2, 1); auto secondTrack = musicDb.trackDataFromDatabaseId(secondTrackId); auto thirdTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track3"), QStringLiteral("artist2"), QStringLiteral("album3"), 3, 1); auto thirdTrack = musicDb.trackDataFromDatabaseId(thirdTrackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl(), secondTrack[DatabaseInterface::ResourceRole].toUrl(), thirdTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(albumsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 3); QCOMPARE(endRemoveRowsSpy.count(), 3); QCOMPARE(dataChangedSpy.count(), 0); } void addOneTrack() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &albumsModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackRemoved, &albumsModel, &DataModel::trackRemoved); connect(&musicDb, &DatabaseInterface::trackModified, &albumsModel, &DataModel::trackModified); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initializeById(nullptr, nullptr, ElisaUtils::Track, - musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::FilterById, {}, {}, + musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); albumsModel.tracksAdded(musicDb.albumData(musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists")))); QCOMPARE(albumsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track6"), QStringLiteral("artist2"), QStringLiteral("album1"), QStringLiteral("Various Artists"), 6, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), QUrl::fromLocalFile(QStringLiteral("album1")), 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); auto newFiles2 = QList(); for (const auto &oneTrack : newTracks) { newFiles2.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(albumsModel.rowCount(), 5); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 4); QCOMPARE(beginInsertRowsSpy.at(1).at(1).toInt(), 4); QCOMPARE(beginInsertRowsSpy.at(1).at(2).toInt(), 4); QCOMPARE(albumsModel.data(albumsModel.index(4, 0), DatabaseInterface::ColumnsRoles::TitleRole).toString(), QStringLiteral("track6")); auto secondNewTrack = MusicAudioTrack{true, QStringLiteral("$24"), QStringLiteral("0"), QStringLiteral("track5"), QStringLiteral("artist2"), QStringLiteral("album1"), QStringLiteral("Various Artists"), 5, 1, QTime::fromMSecsSinceStartOfDay(24), {QUrl::fromLocalFile(QStringLiteral("/$24"))}, QDateTime::fromMSecsSinceEpoch(24), QUrl::fromLocalFile(QStringLiteral("album1")), 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto secondNewTracks = QList(); secondNewTracks.push_back(secondNewTrack); auto newFiles3 = QList(); for (const auto &oneTrack : secondNewTracks) { newFiles3.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(secondNewTracks, mNewCovers); QCOMPARE(albumsModel.rowCount(), 6); QCOMPARE(beginInsertRowsSpy.count(), 3); QCOMPARE(endInsertRowsSpy.count(), 3); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 9); QCOMPARE(beginInsertRowsSpy.at(2).at(1).toInt(), 4); QCOMPARE(beginInsertRowsSpy.at(2).at(2).toInt(), 4); QCOMPARE(albumsModel.data(albumsModel.index(4, 0), DatabaseInterface::ColumnsRoles::TitleRole).toString(), QStringLiteral("track5")); } void modifyOneTrack() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &albumsModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackRemoved, &albumsModel, &DataModel::trackRemoved); connect(&musicDb, &DatabaseInterface::trackModified, &albumsModel, &DataModel::trackModified); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initializeById(nullptr, nullptr, ElisaUtils::Track, - musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::FilterById, {}, {}, + musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); albumsModel.tracksAdded(musicDb.albumData(musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists")))); QCOMPARE(albumsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto modifiedTrack = MusicAudioTrack{ true, QStringLiteral("$3"), QStringLiteral("0"), QStringLiteral("track3"), QStringLiteral("artist3"), QStringLiteral("album1"), QStringLiteral("Various Artists"), 5, 3, QTime::fromMSecsSinceStartOfDay(3), {QUrl::fromLocalFile(QStringLiteral("/$3"))}, QDateTime::fromMSecsSinceEpoch(23), - QUrl::fromLocalFile(QStringLiteral("album1")), 5, true, + QUrl::fromLocalFile(QStringLiteral("album1")), 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; musicDb.insertTracksList({modifiedTrack}, mNewCovers); QCOMPARE(albumsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 1); QCOMPARE(dataChangedSpy.at(0).at(0).toModelIndex(), albumsModel.index(2, 0)); QCOMPARE(dataChangedSpy.at(0).at(1).toModelIndex(), albumsModel.index(2, 0)); QCOMPARE(albumsModel.data(albumsModel.index(2, 0), DatabaseInterface::ColumnsRoles::TrackNumberRole).toInt(), 5); } void removeOneTrackAllTracks() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&tracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&tracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&tracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&tracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&tracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 23); auto trackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist1"), QStringLiteral("album1"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(trackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 1); QCOMPARE(endRemoveRowsSpy.count(), 1); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 22); } void removeOneAlbumAllTracks() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&tracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&tracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&tracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&tracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&tracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 23); auto firstTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist2"), QStringLiteral("album3"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(firstTrackId); auto secondTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track2"), QStringLiteral("artist2"), QStringLiteral("album3"), 2, 1); auto secondTrack = musicDb.trackDataFromDatabaseId(secondTrackId); auto thirdTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track3"), QStringLiteral("artist2"), QStringLiteral("album3"), 3, 1); auto thirdTrack = musicDb.trackDataFromDatabaseId(thirdTrackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl(), secondTrack[DatabaseInterface::ResourceRole].toUrl(), thirdTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 3); QCOMPARE(endRemoveRowsSpy.count(), 3); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 20); } void addOneTrackAllTracks() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&tracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&tracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&tracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&tracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&tracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist2"), QStringLiteral("album4"), QStringLiteral("artist2"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 5); QCOMPARE(tracksModel.rowCount(), 24); } void addOneAlbumAllTracks() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&tracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&tracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&tracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&tracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&tracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist2"), QStringLiteral("album4"), QStringLiteral("artist2"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); auto newCover = QUrl::fromLocalFile(QStringLiteral("album5")); auto newCovers = QHash(); newCovers[QStringLiteral("album5")] = newCover; auto newFiles2 = QList(); for (const auto &oneTrack : newTracks) { newFiles2.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(newTracks, newCovers); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 5); QCOMPARE(tracksModel.rowCount(), 24); } void modifyOneTrackAllTracks() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&tracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&tracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&tracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&tracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&tracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$1"), QStringLiteral("0"), QStringLiteral("track1"), QStringLiteral("artist1"), QStringLiteral("album1"), QStringLiteral("Various Artists"), 1, 1, QTime::fromMSecsSinceStartOfDay(1), {QUrl::fromLocalFile(QStringLiteral("/$1"))}, QDateTime::fromMSecsSinceEpoch(1), {QUrl::fromLocalFile(QStringLiteral("file://image$1"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 1); QCOMPARE(tracksModel.rowCount(), 23); const auto &dataChangedSignal = dataChangedSpy.constFirst(); QCOMPARE(dataChangedSignal.size(), 3); auto changedIndex = dataChangedSignal.constFirst().toModelIndex(); QCOMPARE(tracksModel.data(changedIndex, DatabaseInterface::ColumnsRoles::RatingRole).isValid(), true); QCOMPARE(tracksModel.data(changedIndex, DatabaseInterface::ColumnsRoles::RatingRole).toInt(), 5); } void addEmptyTracksListAllTracks() { DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); auto newTracks = DataModel::ListTrackDataType{}; QSignalSpy beginInsertRowsSpy(&tracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&tracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&tracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&tracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&tracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); tracksModel.tracksAdded(newTracks); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 0); } void addTracksListTwiceAllTracks() { DatabaseInterface musicDb; DataModel tracksModel; QAbstractItemModelTester testModel(&tracksModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &tracksModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackModified, &tracksModel, &DataModel::trackModified); connect(&musicDb, &DatabaseInterface::trackRemoved, &tracksModel, &DataModel::trackRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&tracksModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&tracksModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&tracksModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&tracksModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&tracksModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track); + tracksModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); QCOMPARE(tracksModel.rowCount(), 23); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist2"), QStringLiteral("album4"), QStringLiteral("artist2"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 5); QCOMPARE(tracksModel.rowCount(), 24); } void removeOneTrackAllAlbums() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::albumsAdded, &albumsModel, &DataModel::albumsAdded); connect(&musicDb, &DatabaseInterface::albumModified, &albumsModel, &DataModel::albumModified); connect(&musicDb, &DatabaseInterface::albumRemoved, &albumsModel, &DataModel::albumRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(albumsModel.rowCount(), 5); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto trackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist1"), QStringLiteral("album1"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(trackId); QVERIFY(!firstTrack.isEmpty()); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(albumsModel.rowCount(), 5); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 1); } void removeOneAlbumAllAlbums() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::albumsAdded, &albumsModel, &DataModel::albumsAdded); connect(&musicDb, &DatabaseInterface::albumModified, &albumsModel, &DataModel::albumModified); connect(&musicDb, &DatabaseInterface::albumRemoved, &albumsModel, &DataModel::albumRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(albumsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(albumsModel.rowCount(), 5); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto firstTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track1"), QStringLiteral("artist2"), QStringLiteral("album3"), 1, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(firstTrackId); auto secondTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track2"), QStringLiteral("artist2"), QStringLiteral("album3"), 2, 1); auto secondTrack = musicDb.trackDataFromDatabaseId(secondTrackId); auto thirdTrackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track3"), QStringLiteral("artist2"), QStringLiteral("album3"), 3, 1); auto thirdTrack = musicDb.trackDataFromDatabaseId(thirdTrackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl(), secondTrack[DatabaseInterface::ResourceRole].toUrl(), thirdTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(albumsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 1); QCOMPARE(endRemoveRowsSpy.count(), 1); QCOMPARE(dataChangedSpy.count(), 0); } void addOneTrackAllAlbums() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::albumsAdded, &albumsModel, &DataModel::albumsAdded); connect(&musicDb, &DatabaseInterface::albumModified, &albumsModel, &DataModel::albumModified); connect(&musicDb, &DatabaseInterface::albumRemoved, &albumsModel, &DataModel::albumRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist2"), QStringLiteral("album4"), QStringLiteral("artist2"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 1); } void addOneAlbumAllAlbums() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::albumsAdded, &albumsModel, &DataModel::albumsAdded); connect(&musicDb, &DatabaseInterface::albumModified, &albumsModel, &DataModel::albumModified); connect(&musicDb, &DatabaseInterface::albumRemoved, &albumsModel, &DataModel::albumRemoved); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Album, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track1"), QStringLiteral("artist2"), QStringLiteral("album5"), QStringLiteral("artist2"), 1, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); auto newCover = QUrl::fromLocalFile(QStringLiteral("album5")); auto newCovers = QHash(); newCovers[QStringLiteral("album5")] = newCover; musicDb.insertTracksList(newTracks, newCovers); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); } void removeOneArtistAllArtists() { DatabaseInterface musicDb; DataModel artistsModel; QAbstractItemModelTester testModel(&artistsModel); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&artistsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&artistsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&artistsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&artistsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&artistsModel, &DataModel::dataChanged); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Artist); + artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Artist, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(artistsModel.rowCount(), 7); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto trackId = musicDb.trackIdFromTitleAlbumTrackDiscNumber(QStringLiteral("track6"), QStringLiteral("artist1 and artist2"), QStringLiteral("album2"), 6, 1); auto firstTrack = musicDb.trackDataFromDatabaseId(trackId); musicDb.removeTracksList({firstTrack[DatabaseInterface::ResourceRole].toUrl()}); QCOMPARE(artistsModel.rowCount(), 6); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 1); QCOMPARE(endRemoveRowsSpy.count(), 1); QCOMPARE(dataChangedSpy.count(), 0); } void addOneArtistAllArtists() { DatabaseInterface musicDb; DataModel artistsModel; QAbstractItemModelTester testModel(&artistsModel); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&artistsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&artistsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&artistsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&artistsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&artistsModel, &DataModel::dataChanged); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Artist); + artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Artist, ElisaUtils::NoFilter, {}, {}, 0); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(artistsModel.rowCount(), 7); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track23"), QStringLiteral("artist6"), QStringLiteral("album4"), QStringLiteral("Various Artists"), 23, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), {QUrl::fromLocalFile(QStringLiteral("file://image$23"))}, 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); auto newFiles2 = QList(); for (const auto &oneTrack : newTracks) { newFiles2.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(artistsModel.rowCount(), 8); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); } void displayAlbumsFromOneArtist() { QTemporaryFile databaseFile; databaseFile.open(); qDebug() << "displayAlbumsFromOneArtist" << databaseFile.fileName(); DatabaseInterface musicDb; DataModel artistsModel; QAbstractItemModelTester testModel(&artistsModel); musicDb.init(QStringLiteral("testDb"), databaseFile.fileName()); QSignalSpy beginInsertRowsSpy(&artistsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&artistsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&artistsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&artistsModel, &DataModel::rowsRemoved); QSignalSpy modelAboutToBeResetSpy(&artistsModel, &DataModel::modelAboutToBeReset); QSignalSpy modelResetSpy(&artistsModel, &DataModel::modelReset); QSignalSpy dataChangedSpy(&artistsModel, &DataModel::dataChanged); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - artistsModel.initializeByArtist(nullptr, &musicDb, ElisaUtils::Album, QStringLiteral("artist1")); + artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Album, ElisaUtils::FilterByArtist, {}, QStringLiteral("artist1"), 0); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(artistsModel.rowCount(), 1); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); } void displayArtistsFromOneGenre() { QTemporaryFile databaseFile; databaseFile.open(); qDebug() << "displayArtistsFromOneGenre" << databaseFile.fileName(); DatabaseInterface musicDb; DataModel artistsModel; QAbstractItemModelTester testModel(&artistsModel); musicDb.init(QStringLiteral("testDb"), databaseFile.fileName()); QSignalSpy beginInsertRowsSpy(&artistsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&artistsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&artistsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&artistsModel, &DataModel::rowsRemoved); QSignalSpy modelAboutToBeResetSpy(&artistsModel, &DataModel::modelAboutToBeReset); QSignalSpy modelResetSpy(&artistsModel, &DataModel::modelReset); QSignalSpy dataChangedSpy(&artistsModel, &DataModel::dataChanged); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - artistsModel.initializeByGenre(nullptr, &musicDb, ElisaUtils::Artist, QStringLiteral("genre1")); + artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Artist, ElisaUtils::FilterByGenre, QStringLiteral("genre1"), {}, 0); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(artistsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); } void displayAlbumsFromOneArtistAndGenre() { QTemporaryFile databaseFile; databaseFile.open(); qDebug() << "displayAlbumsFromOneArtistAndGenre" << databaseFile.fileName(); DatabaseInterface musicDb; DataModel artistsModel; QAbstractItemModelTester testModel(&artistsModel); musicDb.init(QStringLiteral("testDb"), databaseFile.fileName()); QSignalSpy beginInsertRowsSpy(&artistsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&artistsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&artistsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&artistsModel, &DataModel::rowsRemoved); QSignalSpy modelAboutToBeResetSpy(&artistsModel, &DataModel::modelAboutToBeReset); QSignalSpy modelResetSpy(&artistsModel, &DataModel::modelReset); QSignalSpy dataChangedSpy(&artistsModel, &DataModel::dataChanged); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - artistsModel.initializeByGenreAndArtist(nullptr, &musicDb, ElisaUtils::Album, QStringLiteral("genre3"), QStringLiteral("artist2")); + artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Album, ElisaUtils::FilterByGenreAndArtist, + QStringLiteral("genre3"), QStringLiteral("artist2"), 0); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(artistsModel.rowCount(), 2); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); } void displayTracksFromOneAlbum() { QTemporaryFile databaseFile; databaseFile.open(); qDebug() << "displayTracksFromOneAlbum" << databaseFile.fileName(); DatabaseInterface musicDb; DataModel artistsModel; QAbstractItemModelTester testModel(&artistsModel); musicDb.init(QStringLiteral("testDb"), databaseFile.fileName()); QSignalSpy beginInsertRowsSpy(&artistsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&artistsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&artistsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&artistsModel, &DataModel::rowsRemoved); QSignalSpy modelAboutToBeResetSpy(&artistsModel, &DataModel::modelAboutToBeReset); QSignalSpy modelResetSpy(&artistsModel, &DataModel::modelReset); QSignalSpy dataChangedSpy(&artistsModel, &DataModel::dataChanged); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(artistsModel.rowCount(), 0); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto albumId = musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists")); QVERIFY(albumId != 0); - artistsModel.initializeById(nullptr, &musicDb, ElisaUtils::Track, albumId); + artistsModel.initialize(nullptr, &musicDb, ElisaUtils::Track, ElisaUtils::FilterById, {}, {}, albumId); QCOMPARE(artistsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newTracks = QList(); newTracks = {{true, QStringLiteral("$31"), QStringLiteral("0"), QStringLiteral("track12"), QStringLiteral("artist1"), QStringLiteral("album1"), QStringLiteral("Various Artists"), 12, 1, QTime::fromMSecsSinceStartOfDay(31), {QUrl::fromLocalFile(QStringLiteral("/$31"))}, QDateTime::fromMSecsSinceEpoch(31), {QUrl::fromLocalFile(QStringLiteral("album1"))}, 5, true, QStringLiteral("genre4"), QStringLiteral("composer4"), QStringLiteral("lyricist4"), true}, {true, QStringLiteral("$32"), QStringLiteral("0"), QStringLiteral("track13"), QStringLiteral("artist3"), QStringLiteral("album3"), QStringLiteral("artist3"), 13, 1, QTime::fromMSecsSinceStartOfDay(32), {QUrl::fromLocalFile(QStringLiteral("/$32"))}, QDateTime::fromMSecsSinceEpoch(32), {QUrl::fromLocalFile(QStringLiteral("album3"))}, 4, true, QStringLiteral("genre3"), QStringLiteral("composer3"), QStringLiteral("lyricist3"), false}}; auto newCovers = mNewCovers; newCovers[QStringLiteral("file:///$31")] = QUrl::fromLocalFile(QStringLiteral("album1")); newCovers[QStringLiteral("file:///$32")] = QUrl::fromLocalFile(QStringLiteral("album3")); musicDb.insertTracksList(newTracks, newCovers); QCOMPARE(artistsModel.rowCount(), 5); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(modelAboutToBeResetSpy.count(), 0); QCOMPARE(modelResetSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 4); } void addOneTrackWrongOrder() { DatabaseInterface musicDb; DataModel albumsModel; QAbstractItemModelTester testModel(&albumsModel); connect(&musicDb, &DatabaseInterface::tracksAdded, &albumsModel, &DataModel::tracksAdded); connect(&musicDb, &DatabaseInterface::trackRemoved, &albumsModel, &DataModel::trackRemoved); connect(&musicDb, &DatabaseInterface::trackModified, &albumsModel, &DataModel::trackModified); musicDb.init(QStringLiteral("testDb")); QSignalSpy beginInsertRowsSpy(&albumsModel, &DataModel::rowsAboutToBeInserted); QSignalSpy endInsertRowsSpy(&albumsModel, &DataModel::rowsInserted); QSignalSpy beginRemoveRowsSpy(&albumsModel, &DataModel::rowsAboutToBeRemoved); QSignalSpy endRemoveRowsSpy(&albumsModel, &DataModel::rowsRemoved); QSignalSpy dataChangedSpy(&albumsModel, &DataModel::dataChanged); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newFiles = QList(); const auto &constNewTracks = mNewTracks; for (const auto &oneTrack : constNewTracks) { newFiles.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(mNewTracks, mNewCovers); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); - albumsModel.initializeById(nullptr, nullptr, ElisaUtils::Track, - musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); + albumsModel.initialize(nullptr, nullptr, ElisaUtils::Track, ElisaUtils::FilterById, {}, {}, + musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists"))); QCOMPARE(beginInsertRowsSpy.count(), 0); QCOMPARE(endInsertRowsSpy.count(), 0); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); albumsModel.tracksAdded(musicDb.albumData(musicDb.albumIdFromTitleAndArtist(QStringLiteral("album1"), QStringLiteral("Various Artists")))); QCOMPARE(albumsModel.rowCount(), 4); QCOMPARE(beginInsertRowsSpy.count(), 1); QCOMPARE(endInsertRowsSpy.count(), 1); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 0); auto newTrack = MusicAudioTrack{true, QStringLiteral("$23"), QStringLiteral("0"), QStringLiteral("track6"), QStringLiteral("artist2"), QStringLiteral("album1"), QStringLiteral("Various Artists"), 2, 1, QTime::fromMSecsSinceStartOfDay(23), {QUrl::fromLocalFile(QStringLiteral("/$23"))}, QDateTime::fromMSecsSinceEpoch(23), QUrl::fromLocalFile(QStringLiteral("album1")), 5, true, {}, QStringLiteral("composer1"), QStringLiteral("lyricist1"), false}; auto newTracks = QList(); newTracks.push_back(newTrack); auto newFiles2 = QList(); for (const auto &oneTrack : newTracks) { newFiles2.push_back(oneTrack.resourceURI()); } musicDb.insertTracksList(newTracks, mNewCovers); QCOMPARE(albumsModel.rowCount(), 5); QCOMPARE(beginInsertRowsSpy.count(), 2); QCOMPARE(endInsertRowsSpy.count(), 2); QCOMPARE(beginRemoveRowsSpy.count(), 0); QCOMPARE(endRemoveRowsSpy.count(), 0); QCOMPARE(dataChangedSpy.count(), 4); QCOMPARE(beginInsertRowsSpy.at(1).at(1).toInt(), 2); QCOMPARE(beginInsertRowsSpy.at(1).at(2).toInt(), 2); } }; QTEST_GUILESS_MAIN(DataModelTests) #include "datamodeltest.moc" diff --git a/autotests/viewmanagertest.cpp b/autotests/viewmanagertest.cpp index 08543dd4..c4c212eb 100644 --- a/autotests/viewmanagertest.cpp +++ b/autotests/viewmanagertest.cpp @@ -1,354 +1,287 @@ /* * Copyright 2015-2017 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "viewmanager.h" #include #include class ViewManagerTests: public QObject { Q_OBJECT private: private Q_SLOTS: void initTestCase() { qRegisterMetaType("ViewManager::ViewsType"); + qRegisterMetaType("ViewManager::SortOrder"); qRegisterMetaType("ElisaUtils::PlayListEntryType"); + qRegisterMetaType("ElisaUtils::FilterType"); } void closeAllViewsTest() { ViewManager viewManager; QSignalSpy openGridViewSpy(&viewManager, &ViewManager::openGridView); - QSignalSpy switchRecentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchRecentlyPlayedTracksView); - QSignalSpy switchFrequentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchFrequentlyPlayedTracksView); - QSignalSpy switchOneAlbumViewSpy(&viewManager, &ViewManager::switchOneAlbumView); - QSignalSpy switchAllTracksViewSpy(&viewManager, &ViewManager::switchAllTracksView); + QSignalSpy openListViewSpy(&viewManager, &ViewManager::openListView); QSignalSpy switchFilesBrowserViewSpy(&viewManager, &ViewManager::switchFilesBrowserView); QSignalSpy switchOffAllViewsSpy(&viewManager, &ViewManager::switchOffAllViews); QSignalSpy popOneViewSpy(&viewManager, &ViewManager::popOneView); viewManager.closeAllViews(); QCOMPARE(openGridViewSpy.count(), 0); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 1); QCOMPARE(popOneViewSpy.count(), 0); } void openAlbumViewTest() { ViewManager viewManager; QSignalSpy openGridViewSpy(&viewManager, &ViewManager::openGridView); - QSignalSpy switchRecentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchRecentlyPlayedTracksView); - QSignalSpy switchFrequentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchFrequentlyPlayedTracksView); - QSignalSpy switchOneAlbumViewSpy(&viewManager, &ViewManager::switchOneAlbumView); - QSignalSpy switchAllTracksViewSpy(&viewManager, &ViewManager::switchAllTracksView); + QSignalSpy openListViewSpy(&viewManager, &ViewManager::openListView); QSignalSpy switchFilesBrowserViewSpy(&viewManager, &ViewManager::switchFilesBrowserView); QSignalSpy switchOffAllViewsSpy(&viewManager, &ViewManager::switchOffAllViews); QSignalSpy popOneViewSpy(&viewManager, &ViewManager::popOneView); viewManager.openChildView(QStringLiteral("album1"), QStringLiteral("artist1"), {}, 12, ElisaUtils::Album); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(0).count(), 11); + QCOMPARE(openGridViewSpy.at(0).count(), 12); QCOMPARE(openGridViewSpy.at(0).at(0).value(), ViewManager::AllAlbums); viewManager.viewIsLoaded(ViewManager::AllAlbums); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 1); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 1); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.at(0).count(), 6); - QCOMPARE(switchOneAlbumViewSpy.at(0).at(2), QStringLiteral("album1")); - QCOMPARE(switchOneAlbumViewSpy.at(0).at(4), QStringLiteral("artist1")); + QCOMPARE(openListViewSpy.at(0).count(), 11); + QCOMPARE(openListViewSpy.at(0).at(3), QStringLiteral("album1")); + QCOMPARE(openListViewSpy.at(0).at(4), QStringLiteral("artist1")); } void openArtistViewTest() { ViewManager viewManager; QSignalSpy openGridViewSpy(&viewManager, &ViewManager::openGridView); - QSignalSpy switchRecentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchRecentlyPlayedTracksView); - QSignalSpy switchFrequentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchFrequentlyPlayedTracksView); - QSignalSpy switchOneAlbumViewSpy(&viewManager, &ViewManager::switchOneAlbumView); - QSignalSpy switchAllTracksViewSpy(&viewManager, &ViewManager::switchAllTracksView); + QSignalSpy openListViewSpy(&viewManager, &ViewManager::openListView); QSignalSpy switchFilesBrowserViewSpy(&viewManager, &ViewManager::switchFilesBrowserView); QSignalSpy switchOffAllViewsSpy(&viewManager, &ViewManager::switchOffAllViews); QSignalSpy popOneViewSpy(&viewManager, &ViewManager::popOneView); viewManager.openChildView(QStringLiteral("artist1"), {}, {}, 0, ElisaUtils::Artist); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(0).count(), 11); + QCOMPARE(openGridViewSpy.at(0).count(), 12); QCOMPARE(openGridViewSpy.at(0).at(0).value(), ViewManager::AllArtists); viewManager.viewIsLoaded(ViewManager::AllArtists); QCOMPARE(openGridViewSpy.count(), 2); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(1).count(), 11); + QCOMPARE(openGridViewSpy.at(1).count(), 12); QCOMPARE(openGridViewSpy.at(1).at(0).value(), ViewManager::OneArtist); } void openGenreViewTest() { ViewManager viewManager; QSignalSpy openGridViewSpy(&viewManager, &ViewManager::openGridView); - QSignalSpy switchRecentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchRecentlyPlayedTracksView); - QSignalSpy switchFrequentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchFrequentlyPlayedTracksView); - QSignalSpy switchOneAlbumViewSpy(&viewManager, &ViewManager::switchOneAlbumView); - QSignalSpy switchAllTracksViewSpy(&viewManager, &ViewManager::switchAllTracksView); + QSignalSpy openListViewSpy(&viewManager, &ViewManager::openListView); QSignalSpy switchFilesBrowserViewSpy(&viewManager, &ViewManager::switchFilesBrowserView); QSignalSpy switchOffAllViewsSpy(&viewManager, &ViewManager::switchOffAllViews); QSignalSpy popOneViewSpy(&viewManager, &ViewManager::popOneView); viewManager.openChildView(QStringLiteral("genre1"), {}, {}, 0, ElisaUtils::Genre); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(0).count(), 11); + QCOMPARE(openGridViewSpy.at(0).count(), 12); QCOMPARE(openGridViewSpy.at(0).at(0).value(), ViewManager::AllGenres); viewManager.viewIsLoaded(ViewManager::AllArtists); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); } void openArtistFromGenreViewTest() { ViewManager viewManager; QSignalSpy openGridViewSpy(&viewManager, &ViewManager::openGridView); - QSignalSpy switchRecentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchRecentlyPlayedTracksView); - QSignalSpy switchFrequentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchFrequentlyPlayedTracksView); - QSignalSpy switchOneAlbumViewSpy(&viewManager, &ViewManager::switchOneAlbumView); - QSignalSpy switchAllTracksViewSpy(&viewManager, &ViewManager::switchAllTracksView); + QSignalSpy openListViewSpy(&viewManager, &ViewManager::openListView); QSignalSpy switchFilesBrowserViewSpy(&viewManager, &ViewManager::switchFilesBrowserView); QSignalSpy switchOffAllViewsSpy(&viewManager, &ViewManager::switchOffAllViews); QSignalSpy popOneViewSpy(&viewManager, &ViewManager::popOneView); viewManager.openChildView(QStringLiteral("genre1"), {}, {}, 0, ElisaUtils::Genre); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(0).count(), 11); + QCOMPARE(openGridViewSpy.at(0).count(), 12); QCOMPARE(openGridViewSpy.at(0).at(0).value(), ViewManager::AllGenres); viewManager.viewIsLoaded(ViewManager::AllGenres); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); viewManager.openChildView(QStringLiteral("genre1"), {}, {}, 0, ElisaUtils::Genre); QCOMPARE(openGridViewSpy.count(), 2); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(1).count(), 11); + QCOMPARE(openGridViewSpy.at(1).count(), 12); QCOMPARE(openGridViewSpy.at(1).at(0).value(), ViewManager::AllArtistsFromGenre); viewManager.viewIsLoaded(ViewManager::AllArtistsFromGenre); viewManager.openChildView(QStringLiteral("artist1"), {}, {}, 0, ElisaUtils::Artist); QCOMPARE(openGridViewSpy.count(), 3); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(2).count(), 11); + QCOMPARE(openGridViewSpy.at(2).count(), 12); QCOMPARE(openGridViewSpy.at(2).at(0).value(), ViewManager::OneArtistFromGenre); viewManager.viewIsLoaded(ViewManager::OneArtistFromGenre); } void openArtistViewAndAlbumFromAnotherArtistTest() { ViewManager viewManager; QSignalSpy openGridViewSpy(&viewManager, &ViewManager::openGridView); - QSignalSpy switchRecentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchRecentlyPlayedTracksView); - QSignalSpy switchFrequentlyPlayedTracksViewSpy(&viewManager, &ViewManager::switchFrequentlyPlayedTracksView); - QSignalSpy switchOneAlbumViewSpy(&viewManager, &ViewManager::switchOneAlbumView); - QSignalSpy switchAllTracksViewSpy(&viewManager, &ViewManager::switchAllTracksView); + QSignalSpy openListViewSpy(&viewManager, &ViewManager::openListView); QSignalSpy switchFilesBrowserViewSpy(&viewManager, &ViewManager::switchFilesBrowserView); QSignalSpy switchOffAllViewsSpy(&viewManager, &ViewManager::switchOffAllViews); QSignalSpy popOneViewSpy(&viewManager, &ViewManager::popOneView); viewManager.openChildView(QStringLiteral("artist1"), {}, {}, 0, ElisaUtils::Artist); QCOMPARE(openGridViewSpy.count(), 1); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(0).count(), 11); + QCOMPARE(openGridViewSpy.at(0).count(), 12); QCOMPARE(openGridViewSpy.at(0).at(0).value(), ViewManager::AllArtists); viewManager.viewIsLoaded(ViewManager::AllArtists); QCOMPARE(openGridViewSpy.count(), 2); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); - QCOMPARE(openGridViewSpy.at(1).count(), 11); + QCOMPARE(openGridViewSpy.at(1).count(), 12); QCOMPARE(openGridViewSpy.at(1).at(0).value(), ViewManager::OneArtist); viewManager.viewIsLoaded(ViewManager::OneArtist); QCOMPARE(openGridViewSpy.count(), 2); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 0); viewManager.openChildView(QStringLiteral("album1"), QStringLiteral("artist2"), {}, 0, ElisaUtils::Album); QCOMPARE(openGridViewSpy.count(), 2); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 1); viewManager.viewIsLoaded(ViewManager::AllArtists); QCOMPARE(openGridViewSpy.count(), 3); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 0); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 0); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 1); - QCOMPARE(openGridViewSpy.at(2).count(), 11); + QCOMPARE(openGridViewSpy.at(2).count(), 12); QCOMPARE(openGridViewSpy.at(2).at(0).value(), ViewManager::OneArtist); viewManager.viewIsLoaded(ViewManager::OneArtist); QCOMPARE(openGridViewSpy.count(), 3); - QCOMPARE(switchRecentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchFrequentlyPlayedTracksViewSpy.count(), 0); - QCOMPARE(switchOneAlbumViewSpy.count(), 1); - QCOMPARE(switchAllTracksViewSpy.count(), 0); + QCOMPARE(openListViewSpy.count(), 1); QCOMPARE(switchFilesBrowserViewSpy.count(), 0); QCOMPARE(switchOffAllViewsSpy.count(), 0); QCOMPARE(popOneViewSpy.count(), 1); - QCOMPARE(switchOneAlbumViewSpy.at(0).count(), 6); - QCOMPARE(switchOneAlbumViewSpy.at(0).at(0).value(), ViewManager::OneAlbumFromArtist); + QCOMPARE(openListViewSpy.at(0).count(), 11); + QCOMPARE(openListViewSpy.at(0).at(0).value(), ViewManager::OneAlbumFromArtist); } }; QTEST_GUILESS_MAIN(ViewManagerTests) #include "viewmanagertest.moc" diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index e76d1c13..03858964 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,494 +1,491 @@ include_directories(${elisa_BINARY_DIR}) set(elisaLib_SOURCES mediaplaylist.cpp musicaudiotrack.cpp progressindicator.cpp databaseinterface.cpp musiclistenersmanager.cpp managemediaplayercontrol.cpp manageheaderbar.cpp manageaudioplayer.cpp trackslistener.cpp elisaapplication.cpp modeldataloader.cpp notificationitem.cpp topnotificationmanager.cpp elisautils.cpp datatype.cpp abstractfile/abstractfilelistener.cpp abstractfile/abstractfilelisting.cpp filescanner.cpp viewmanager.cpp powermanagementinterface.cpp file/filelistener.cpp file/localfilelisting.cpp models/datamodel.cpp models/abstractmediaproxymodel.cpp models/gridviewproxymodel.cpp models/alltracksproxymodel.cpp models/singlealbumproxymodel.cpp models/trackmetadatamodel.cpp models/trackcontextmetadatamodel.cpp models/viewsmodel.cpp ) ecm_qt_declare_logging_category(elisaLib_SOURCES HEADER "indexersManager.h" IDENTIFIER "orgKdeElisaIndexersManager" CATEGORY_NAME "org.kde.elisa.indexers.manager" DEFAULT_SEVERITY Info ) ecm_qt_declare_logging_category(elisaLib_SOURCES HEADER "databaseLogging.h" IDENTIFIER "orgKdeElisaDatabase" CATEGORY_NAME "org.kde.elisa.database" DEFAULT_SEVERITY Info ) ecm_qt_declare_logging_category(elisaLib_SOURCES HEADER "abstractfile/indexercommon.h" IDENTIFIER "orgKdeElisaIndexer" CATEGORY_NAME "org.kde.elisa.indexer" DEFAULT_SEVERITY Info ) if (LIBVLC_FOUND) ecm_qt_declare_logging_category(elisaLib_SOURCES HEADER "vlcLogging.h" IDENTIFIER "orgKdeElisaPlayerVlc" CATEGORY_NAME "org.kde.elisa.player.vlc" DEFAULT_SEVERITY Info ) set(elisaLib_SOURCES ${elisaLib_SOURCES} audiowrapper_libvlc.cpp ) else() ecm_qt_declare_logging_category(elisaLib_SOURCES HEADER "qtMultimediaLogging.h" IDENTIFIER "orgKdeElisaPlayerQtMultimedia" CATEGORY_NAME "org.kde.elisa.player.qtMultimedia" DEFAULT_SEVERITY Info ) set(elisaLib_SOURCES ${elisaLib_SOURCES} audiowrapper_qtmultimedia.cpp ) endif() if (ANDROID) set(elisaLib_SOURCES ${elisaLib_SOURCES} android/androidmusiclistener.cpp ) endif() if (KF5KIO_FOUND) set(elisaLib_SOURCES ${elisaLib_SOURCES} models/filebrowsermodel.cpp models/filebrowserproxymodel.cpp ) endif() if (KF5Baloo_FOUND) if (Qt5DBus_FOUND) ecm_qt_declare_logging_category(elisaLib_SOURCES HEADER "baloo/baloocommon.h" IDENTIFIER "orgKdeElisaBaloo" CATEGORY_NAME "org.kde.elisa.baloo" DEFAULT_SEVERITY Info ) set(elisaLib_SOURCES ${elisaLib_SOURCES} baloo/localbaloofilelisting.cpp baloo/baloolistener.cpp baloo/baloodetector.cpp ) qt5_add_dbus_interface(elisaLib_SOURCES ${BALOO_DBUS_INTERFACES_DIR}/org.kde.baloo.main.xml baloo/main) qt5_add_dbus_interface(elisaLib_SOURCES ${BALOO_DBUS_INTERFACES_DIR}/org.kde.baloo.fileindexer.xml baloo/fileindexer) qt5_add_dbus_interface(elisaLib_SOURCES ${BALOO_DBUS_INTERFACES_DIR}/org.kde.baloo.scheduler.xml baloo/scheduler) qt5_add_dbus_adaptor(elisaLib_SOURCES ${BALOO_DBUS_INTERFACES_DIR}/org.kde.BalooWatcherApplication.xml baloo/localbaloofilelisting.h LocalBalooFileListing) endif() endif() if (Qt5DBus_FOUND) set(elisaLib_SOURCES ${elisaLib_SOURCES} mpris2/mpris2.cpp mpris2/mediaplayer2.cpp mpris2/mediaplayer2player.cpp ) endif() if (UPNPQT_FOUND) set(elisaLib_SOURCES ${elisaLib_SOURCES} upnp/upnpcontrolcontentdirectory.cpp upnp/upnpcontentdirectorymodel.cpp upnp/upnpcontrolconnectionmanager.cpp upnp/upnpcontrolmediaserver.cpp upnp/didlparser.cpp upnp/upnplistener.cpp upnp/upnpdiscoverallmusic.cpp ) endif() if (KF5Baloo_FOUND) if (Qt5DBus_FOUND) qt5_add_dbus_interface(elisaLib_SOURCES ${BALOO_DBUS_INTERFACES_DIR}/org.kde.baloo.fileindexer.xml baloo/fileindexer) qt5_add_dbus_interface(elisaLib_SOURCES ${BALOO_DBUS_INTERFACES_DIR}/org.kde.baloo.scheduler.xml baloo/scheduler) set(elisaLib_SOURCES ${elisaLib_SOURCES} ../src/baloo/baloolistener.cpp ../src/baloo/localbaloofilelisting.cpp ) endif() endif() kconfig_add_kcfg_files(elisaLib_SOURCES ../src/elisa_settings.kcfgc ) set(elisaLib_SOURCES ${elisaLib_SOURCES} ../src/elisa_core.kcfg ) add_library(elisaLib ${elisaLib_SOURCES}) target_link_libraries(elisaLib LINK_PUBLIC Qt5::Multimedia LINK_PRIVATE Qt5::Core Qt5::Sql Qt5::Widgets Qt5::Concurrent Qt5::Qml KF5::I18n KF5::CoreAddons KF5::ConfigCore KF5::ConfigGui) if (KF5FileMetaData_FOUND) target_link_libraries(elisaLib LINK_PRIVATE KF5::FileMetaData ) endif() if (KF5KIO_FOUND) target_link_libraries(elisaLib LINK_PUBLIC KF5::KIOCore KF5::KIOFileWidgets KF5::KIOWidgets ) endif() if (KF5XmlGui_FOUND) target_link_libraries(elisaLib LINK_PUBLIC KF5::XmlGui ) endif() if (KF5ConfigWidgets_FOUND) target_link_libraries(elisaLib LINK_PUBLIC KF5::ConfigWidgets ) endif() if (KF5KCMUtils_FOUND) target_link_libraries(elisaLib LINK_PUBLIC KF5::KCMUtils ) endif() if (KF5Baloo_FOUND) if (Qt5DBus_FOUND) target_link_libraries(elisaLib LINK_PUBLIC KF5::Baloo ) endif() endif() if (Qt5DBus_FOUND) target_link_libraries(elisaLib LINK_PUBLIC Qt5::DBus ) if (KF5DBusAddons_FOUND) target_link_libraries(elisaLib LINK_PUBLIC KF5::DBusAddons ) endif() endif() if (LIBVLC_FOUND) target_include_directories(elisaLib PRIVATE ${LIBVLC_INCLUDE_DIR} ) target_link_libraries(elisaLib LINK_PRIVATE ${LIBVLC_LIBRARY} ) endif() if (ANDROID) target_link_libraries(elisaLib LINK_PUBLIC Qt5::AndroidExtras ) endif() generate_export_header(elisaLib BASE_NAME ElisaLib EXPORT_FILE_NAME elisaLib_export.h) set_target_properties(elisaLib PROPERTIES VERSION 0.1 SOVERSION 0 EXPORT_NAME ElisaLib ) if (NOT APPLE AND NOT WIN32) install(TARGETS elisaLib LIBRARY DESTINATION ${KDE_INSTALL_FULL_LIBDIR}/elisa NAMELINK_SKIP RUNTIME DESTINATION ${KDE_INSTALL_FULL_LIBDIR}/elisa BUNDLE DESTINATION ${KDE_INSTALL_FULL_LIBDIR}/elisa ) else() install(TARGETS elisaLib ${INSTALL_TARGETS_DEFAULT_ARGS}) endif() set(elisaqmlplugin_SOURCES elisaqmlplugin.cpp datatype.cpp elisautils.cpp ) if (KF5FileMetaData_FOUND) set(elisaqmlplugin_SOURCES ${elisaqmlplugin_SOURCES} embeddedcoverageimageprovider.cpp ) endif() add_library(elisaqmlplugin SHARED ${elisaqmlplugin_SOURCES}) target_link_libraries(elisaqmlplugin LINK_PRIVATE Qt5::Quick Qt5::Widgets KF5::ConfigCore KF5::ConfigGui elisaLib ) if (KF5FileMetaData_FOUND) target_link_libraries(elisaqmlplugin LINK_PRIVATE KF5::FileMetaData ) endif() set_target_properties(elisaqmlplugin PROPERTIES LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin/org/kde/elisa ) if (NOT APPLE AND NOT WIN32) set_target_properties(elisaqmlplugin PROPERTIES INSTALL_RPATH "${KDE_INSTALL_FULL_LIBDIR}/elisa;${CMAKE_INSTALL_RPATH}" ) endif() install(TARGETS elisaqmlplugin DESTINATION ${QML_INSTALL_DIR}/org/kde/elisa/) install(FILES qmldir DESTINATION ${QML_INSTALL_DIR}/org/kde/elisa) add_custom_target(copy) add_custom_target(copy2) file(MAKE_DIRECTORY ${CMAKE_BINARY_DIR}/bin/org/kde/elisa) add_custom_command(TARGET copy PRE_BUILD COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/qmldir ${CMAKE_BINARY_DIR}/bin/org/kde/elisa/) add_custom_command(TARGET copy2 PRE_BUILD COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/plugins.qmltypes ${CMAKE_BINARY_DIR}/bin/org/kde/elisa/) add_dependencies(elisaqmlplugin copy copy2) if (Qt5Quick_FOUND AND Qt5Widgets_FOUND) set(elisa_SOURCES main.cpp windows/WindowsTheme.qml windows/PlatformIntegration.qml android/ElisaMainWindow.qml android/AndroidTheme.qml android/PlatformIntegration.qml android/AlbumsView.qml android/ArtistsView.qml android/TracksView.qml android/GenresView.qml qml/ElisaMainWindow.qml qml/ApplicationMenu.qml qml/BaseTheme.qml qml/Theme.qml qml/PlatformIntegration.qml qml/LabelWithToolTip.qml qml/RatingStar.qml qml/DraggableItem.qml qml/PassiveNotification.qml qml/TopNotification.qml qml/TopNotificationItem.qml qml/TrackImportNotification.qml qml/HeaderBar.qml qml/NavigationActionBar.qml qml/MediaPlayerControl.qml qml/ContextView.qml qml/ContextViewLyrics.qml qml/ContentView.qml qml/ViewSelector.qml qml/ViewSelectorDelegate.qml qml/DataGridView.qml - qml/TracksView.qml - qml/AlbumView.qml - qml/RecentlyPlayedTracks.qml - qml/FrequentlyPlayedTracks.qml + qml/DataListView.qml qml/MediaPlayListView.qml qml/PlayListBasicView.qml qml/PlayListEntry.qml qml/SimplePlayListView.qml qml/SimplePlayListEntry.qml qml/PlayListAlbumHeader.qml qml/BasicPlayListAlbumHeader.qml qml/MetaDataDelegate.qml qml/MediaTrackDelegate.qml qml/MediaAlbumTrackDelegate.qml qml/MediaTrackMetadataView.qml qml/GridBrowserView.qml qml/GridBrowserDelegate.qml qml/ListBrowserView.qml qml/FileBrowserDelegate.qml qml/FileBrowserView.qml qml/ScrollHelper.qml qml/FlatButtonWithToolTip.qml qml/HeaderFooterToolbar.qml ) qt5_add_resources(elisa_SOURCES resources.qrc) set_property(SOURCE qrc_resources.cpp PROPERTY SKIP_AUTOMOC ON) set(elisa_ICONS_PNG ../icons/128-apps-elisa.png ../icons/64-apps-elisa.png ../icons/48-apps-elisa.png ../icons/32-apps-elisa.png ../icons/22-apps-elisa.png ../icons/16-apps-elisa.png ) # add icons to application sources, to have them bundled ecm_add_app_icon(elisa_SOURCES ICONS ${elisa_ICONS_PNG}) add_executable(elisa ${elisa_SOURCES}) target_include_directories(elisa PRIVATE ${KDSoap_INCLUDE_DIRS}) target_link_libraries(elisa LINK_PRIVATE elisaLib Qt5::Widgets Qt5::QuickControls2 KF5::I18n KF5::CoreAddons KF5::ConfigCore KF5::ConfigGui ) if (ANDROID) target_link_libraries(elisa LINK_PRIVATE Qt5::AndroidExtras Qt5::Svg Qt5::Sql Qt5::Concurrent KF5::Kirigami2 ) endif() if (KF5Crash_FOUND) target_link_libraries(elisa LINK_PRIVATE KF5::Crash ) endif() if (KF5Declarative_FOUND) target_link_libraries(elisa LINK_PRIVATE KF5::Declarative ) endif() if (NOT APPLE AND NOT WIN32) set_target_properties(elisa PROPERTIES INSTALL_RPATH "${KDE_INSTALL_FULL_LIBDIR}/elisa;${CMAKE_INSTALL_RPATH}" ) endif() install(TARGETS elisa ${INSTALL_TARGETS_DEFAULT_ARGS}) endif() if (KF5ConfigWidgets_FOUND AND KF5Declarative_FOUND) add_subdirectory(localFileConfiguration) endif() set(elisaImport_SOURCES elisaimport.cpp elisaimportapplication.cpp ) kconfig_add_kcfg_files(elisaImport_SOURCES ../src/elisa_settings.kcfgc ) set(elisaImport_SOURCES ${elisaImport_SOURCES} ../src/elisa_core.kcfg ) add_executable(elisaImport ${elisaImport_SOURCES}) target_link_libraries(elisaImport LINK_PRIVATE KF5::ConfigCore KF5::ConfigGui elisaLib ) if (KF5FileMetaData_FOUND) target_link_libraries(elisaImport LINK_PRIVATE KF5::FileMetaData ) endif() set(QML_IMPORT_PATH ${CMAKE_BINARY_DIR}/bin CACHE INTERNAL "qml import path" FORCE) if (ANDROID) kirigami_package_breeze_icons(ICONS elisa) endif() diff --git a/src/elisaqmlplugin.cpp b/src/elisaqmlplugin.cpp index 42554f01..fe0a6755 100644 --- a/src/elisaqmlplugin.cpp +++ b/src/elisaqmlplugin.cpp @@ -1,186 +1,188 @@ /* * Copyright 2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "elisaqmlplugin.h" #if defined UPNPQT_FOUND && UPNPQT_FOUND #include "upnp/upnpcontrolconnectionmanager.h" #include "upnp/upnpcontrolmediaserver.h" #include "upnp/upnpcontrolcontentdirectory.h" #include "upnp/upnpcontentdirectorymodel.h" #include "upnpdevicedescription.h" #include "upnp/didlparser.h" #include "upnp/upnpdiscoverallmusic.h" #include "upnpssdpengine.h" #include "upnpabstractservice.h" #include "upnpcontrolabstractdevice.h" #include "upnpcontrolabstractservice.h" #include "upnpbasictypes.h" #endif #include "elisautils.h" #include "elisaapplication.h" #include "progressindicator.h" #include "mediaplaylist.h" #include "managemediaplayercontrol.h" #include "manageheaderbar.h" #include "manageaudioplayer.h" #include "musicaudiotrack.h" #include "musiclistenersmanager.h" #include "trackslistener.h" #include "viewmanager.h" #include "databaseinterface.h" #include "models/datamodel.h" #include "models/trackmetadatamodel.h" #include "models/trackcontextmetadatamodel.h" #include "models/viewsmodel.h" #include "models/gridviewproxymodel.h" #include "models/alltracksproxymodel.h" #include "models/singlealbumproxymodel.h" #if defined KF5FileMetaData_FOUND && KF5FileMetaData_FOUND #include "embeddedcoverageimageprovider.h" #endif #if defined KF5KIO_FOUND && KF5KIO_FOUND #include "models/filebrowsermodel.h" #include "models/filebrowserproxymodel.h" #endif #include "audiowrapper.h" #include "notificationitem.h" #include "topnotificationmanager.h" #include "elisautils.h" #include "datatype.h" #if defined Qt5DBus_FOUND && Qt5DBus_FOUND #include "mpris2/mpris2.h" #include "mpris2/mediaplayer2player.h" #endif #include #include #include #include #include #include void ElisaQmlTestPlugin::initializeEngine(QQmlEngine *engine, const char *uri) { QQmlExtensionPlugin::initializeEngine(engine, uri); #if defined KF5FileMetaData_FOUND && KF5FileMetaData_FOUND engine->addImageProvider(QStringLiteral("cover"), new EmbeddedCoverageImageProvider); #endif } void ElisaQmlTestPlugin::registerTypes(const char *uri) { #if defined UPNPQT_FOUND && UPNPQT_FOUND qmlRegisterType(uri, 1, 0, "UpnpSsdpEngine"); qmlRegisterType(uri, 1, 0, "UpnpDiscoverAllMusic"); qmlRegisterType(uri, 1, 0, "UpnpAbstractDevice"); qmlRegisterType(uri, 1, 0, "UpnpAbstractService"); qmlRegisterType(uri, 1, 0, "UpnpControlAbstractDevice"); qmlRegisterType(uri, 1, 0, "UpnpControlAbstractService"); qmlRegisterType(uri, 1, 0, "UpnpControlConnectionManager"); qmlRegisterType(uri, 1, 0, "UpnpControlMediaServer"); qmlRegisterType(uri, 1, 0, "UpnpContentDirectoryModel"); qmlRegisterType(uri, 1, 0, "DidlParser"); qmlRegisterType(uri, 1, 0, "UpnpControlContentDirectory"); qmlRegisterType(uri, 1, 0, "UpnpDeviceDescription"); qRegisterMetaType(); qRegisterMetaType >(); qRegisterMetaType(); qRegisterMetaType(); qRegisterMetaType(); #endif qRegisterMetaType("DataUtils::DataType"); qmlRegisterType(uri, 1, 0, "MediaPlayList"); qmlRegisterType(uri, 1, 0, "ManageMediaPlayerControl"); qmlRegisterType(uri, 1, 0, "ManageHeaderBar"); qmlRegisterType(uri, 1, 0, "ManageAudioPlayer"); qmlRegisterType(uri, 1, 0, "ProgressIndicator"); qmlRegisterType(uri, 1, 0, "MusicListenersManager"); qmlRegisterType(uri, 1, 0, "ViewManager"); qmlRegisterType(uri, 1, 0, "DataModel"); qmlRegisterType(uri, 1, 0, "TrackMetadataModel"); qmlRegisterType(uri, 1, 0, "TrackContextMetaDataModel"); qmlRegisterType(uri, 1, 0, "ViewsModel"); qmlRegisterType(uri, 1, 0, "GridViewProxyModel"); qmlRegisterType(uri, 1, 0, "AllTracksProxyModel"); qmlRegisterType(uri, 1, 0, "SingleAlbumProxyModel"); #if defined KF5KIO_FOUND && KF5KIO_FOUND qmlRegisterType(uri, 1, 0, "FileBrowserModel"); qmlRegisterType(uri, 1, 0, "FileBrowserProxyModel"); #endif qmlRegisterType(uri, 1, 0, "AudioWrapper"); qmlRegisterType(uri, 1, 0, "TopNotificationManager"); qmlRegisterUncreatableMetaObject(DataUtils::staticMetaObject, uri, 1, 0, "DataUtils", QStringLiteral("Only enums")); qmlRegisterUncreatableType(uri, 1, 0, "DatabaseInterface", QStringLiteral("Only created in c++")); #if defined Qt5DBus_FOUND && Qt5DBus_FOUND qmlRegisterType(uri, 1, 0, "Mpris2"); qRegisterMetaType(); #endif qRegisterMetaType(); qRegisterMetaType>("QHash"); qRegisterMetaType>("QHash"); qRegisterMetaType>("QList"); qRegisterMetaType>("QVector"); qRegisterMetaType>("QVector"); qRegisterMetaType>("QHash"); qRegisterMetaType("DatabaseInterface::ListTrackDataType"); qRegisterMetaType("DatabaseInterface::ListAlbumDataType"); qRegisterMetaType("DatabaseInterface::ListArtistDataType"); qRegisterMetaType("DatabaseInterface::ListGenreDataType"); qRegisterMetaType("ModelDataLoader::ListTrackDataType"); qRegisterMetaType("ModelDataLoader::ListAlbumDataType"); qRegisterMetaType("ModelDataLoader::ListArtistDataType"); qRegisterMetaType("ModelDataLoader::ListGenreDataType"); qRegisterMetaType("ModelDataLoader::AlbumDataType"); qRegisterMetaType("TracksListener::ListTrackDataType"); qRegisterMetaType>(); qRegisterMetaType(); qRegisterMetaType("NotificationItem"); qRegisterMetaType>("QMap"); - qRegisterMetaType("PlayListEnqueueMode"); - qRegisterMetaType("PlayListEnqueueTriggerPlay"); - qRegisterMetaType("PlayListEntryType"); - qRegisterMetaType("EntryData"); - qRegisterMetaType("EntryDataList"); + qRegisterMetaType("ElisaUtils::PlayListEnqueueMode"); + qRegisterMetaType("ElisaUtils::PlayListEnqueueTriggerPlay"); + qRegisterMetaType("ElisaUtils::PlayListEntryType"); + qRegisterMetaType("ElisaUtils::EntryData"); + qRegisterMetaType("ElisaUtils::EntryDataList"); + qRegisterMetaType("ElisaUtils::FilterType"); qRegisterMetaType("DatabaseInterface::TrackDataType"); qRegisterMetaType("DatabaseInterface::AlbumDataType"); qRegisterMetaType("DatabaseInterface::ArtistDataType"); qRegisterMetaType("DatabaseInterface::GenreDataType"); qRegisterMetaType("ModelDataLoader::TrackDataType"); qRegisterMetaType("TracksListener::TrackDataType"); qRegisterMetaType("ViewManager::ViewsType"); + qRegisterMetaType("ViewManager::SortOrder"); qRegisterMetaTypeStreamOperators("PlayListControler::PlayerState"); qmlRegisterUncreatableType(uri, 1, 0, "ElisaApplication", QStringLiteral("only one and done in c++")); qmlRegisterUncreatableMetaObject(ElisaUtils::staticMetaObject, uri, 1, 0, "ElisaUtils", QStringLiteral("Namespace ElisaUtils")); } diff --git a/src/elisautils.h b/src/elisautils.h index e7b915e5..6a04c91b 100644 --- a/src/elisautils.h +++ b/src/elisautils.h @@ -1,67 +1,80 @@ /* * Copyright 2017 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #ifndef ELISAUTILS_H #define ELISAUTILS_H #include "elisaLib_export.h" #include #include #include #include namespace ElisaUtils { Q_NAMESPACE enum PlayListEnqueueMode { AppendPlayList, ReplacePlayList, }; Q_ENUM_NS(PlayListEnqueueMode) enum PlayListEnqueueTriggerPlay { DoNotTriggerPlay, TriggerPlay, }; Q_ENUM_NS(PlayListEnqueueTriggerPlay) using EntryData = std::tuple; using EntryDataList = QList; enum PlayListEntryType { Album, Artist, Genre, Lyricist, Composer, Track, FileName, Unknown, }; Q_ENUM_NS(PlayListEntryType) +enum FilterType { + UnknownFilter, + NoFilter, + FilterById, + FilterByGenre, + FilterByArtist, + FilterByGenreAndArtist, + FilterByRecentlyPlayed, + FilterByFrequentlyPlayed, +}; + +Q_ENUM_NS(FilterType) + } Q_DECLARE_METATYPE(ElisaUtils::EntryData) Q_DECLARE_METATYPE(ElisaUtils::EntryDataList) #endif // ELISAUTILS_H diff --git a/src/modeldataloader.cpp b/src/modeldataloader.cpp index 2d11a3a6..92e60e59 100644 --- a/src/modeldataloader.cpp +++ b/src/modeldataloader.cpp @@ -1,443 +1,443 @@ /* * Copyright 2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "modeldataloader.h" #include "filescanner.h" #include class ModelDataLoaderPrivate { public: DatabaseInterface *mDatabase = nullptr; QMimeDatabase mMimeDatabase; FileScanner mFileScanner; ElisaUtils::PlayListEntryType mModelType = ElisaUtils::Unknown; - ModelDataLoader::FilterType mFilterType = ModelDataLoader::FilterType::Unknown; + ModelDataLoader::FilterType mFilterType = ModelDataLoader::FilterType::UnknownFilter; QString mArtist; QString mAlbumTitle; QString mAlbumArtist; QString mGenre; qulonglong mDatabaseId = 0; }; ModelDataLoader::ModelDataLoader(QObject *parent) : QObject(parent), d(std::make_unique()) { } ModelDataLoader::~ModelDataLoader() = default; void ModelDataLoader::setDatabase(DatabaseInterface *database) { d->mDatabase = database; connect(database, &DatabaseInterface::genresAdded, this, &ModelDataLoader::databaseGenresAdded); connect(database, &DatabaseInterface::albumsAdded, this, &ModelDataLoader::databaseAlbumsAdded); connect(database, &DatabaseInterface::albumModified, this, &ModelDataLoader::databaseAlbumModified); connect(database, &DatabaseInterface::albumRemoved, this, &ModelDataLoader::databaseAlbumRemoved); connect(database, &DatabaseInterface::tracksAdded, this, &ModelDataLoader::databaseTracksAdded); connect(database, &DatabaseInterface::trackModified, this, &ModelDataLoader::databaseTrackModified); connect(database, &DatabaseInterface::trackRemoved, this, &ModelDataLoader::databaseTrackRemoved); connect(database, &DatabaseInterface::artistsAdded, this, &ModelDataLoader::databaseArtistsAdded); connect(database, &DatabaseInterface::artistRemoved, this, &ModelDataLoader::databaseArtistRemoved); } void ModelDataLoader::loadData(ElisaUtils::PlayListEntryType dataType) { if (!d->mDatabase) { return; } d->mFilterType = ModelDataLoader::FilterType::NoFilter; switch (dataType) { case ElisaUtils::Album: Q_EMIT allAlbumsData(d->mDatabase->allAlbumsData()); break; case ElisaUtils::Artist: Q_EMIT allArtistsData(d->mDatabase->allArtistsData()); break; case ElisaUtils::Composer: break; case ElisaUtils::Genre: Q_EMIT allGenresData(d->mDatabase->allGenresData()); break; case ElisaUtils::Lyricist: break; case ElisaUtils::Track: Q_EMIT allTracksData(d->mDatabase->allTracksData()); break; case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadDataByAlbumId(ElisaUtils::PlayListEntryType dataType, qulonglong databaseId) { if (!d->mDatabase) { return; } d->mFilterType = ModelDataLoader::FilterType::FilterById; d->mDatabaseId = databaseId; switch (dataType) { case ElisaUtils::Album: break; case ElisaUtils::Artist: break; case ElisaUtils::Composer: break; case ElisaUtils::Genre: break; case ElisaUtils::Lyricist: break; case ElisaUtils::Track: Q_EMIT allTracksData(d->mDatabase->albumData(databaseId)); break; case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadDataByGenre(ElisaUtils::PlayListEntryType dataType, const QString &genre) { if (!d->mDatabase) { return; } d->mFilterType = ModelDataLoader::FilterType::FilterByGenre; d->mGenre = genre; switch (dataType) { case ElisaUtils::Artist: Q_EMIT allArtistsData(d->mDatabase->allArtistsDataByGenre(genre)); break; case ElisaUtils::Album: case ElisaUtils::Composer: case ElisaUtils::Track: case ElisaUtils::Genre: case ElisaUtils::Lyricist: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadDataByArtist(ElisaUtils::PlayListEntryType dataType, const QString &artist) { if (!d->mDatabase) { return; } d->mFilterType = ModelDataLoader::FilterType::FilterByArtist; d->mArtist = artist; switch (dataType) { case ElisaUtils::Album: Q_EMIT allAlbumsData(d->mDatabase->allAlbumsDataByArtist(artist)); break; case ElisaUtils::Artist: case ElisaUtils::Composer: case ElisaUtils::Track: case ElisaUtils::Genre: case ElisaUtils::Lyricist: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadDataByGenreAndArtist(ElisaUtils::PlayListEntryType dataType, const QString &genre, const QString &artist) { if (!d->mDatabase) { return; } d->mFilterType = ModelDataLoader::FilterType::FilterByGenreAndArtist; d->mArtist = artist; d->mGenre = genre; switch (dataType) { case ElisaUtils::Album: Q_EMIT allAlbumsData(d->mDatabase->allAlbumsDataByGenreAndArtist(genre, artist)); break; case ElisaUtils::Artist: case ElisaUtils::Composer: case ElisaUtils::Genre: case ElisaUtils::Lyricist: case ElisaUtils::Track: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadDataByDatabaseId(ElisaUtils::PlayListEntryType dataType, qulonglong databaseId) { if (!d->mDatabase) { return; } d->mFilterType = ModelDataLoader::FilterType::FilterById; d->mDatabaseId = databaseId; switch (dataType) { case ElisaUtils::Track: Q_EMIT allTrackData(d->mDatabase->trackDataFromDatabaseId(databaseId)); break; case ElisaUtils::Album: case ElisaUtils::Artist: case ElisaUtils::Composer: case ElisaUtils::Genre: case ElisaUtils::Lyricist: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadDataByFileName(ElisaUtils::PlayListEntryType dataType, const QUrl &fileName) { if (!d->mDatabase) { return; } - d->mFilterType = ModelDataLoader::FilterType::Unknown; + d->mFilterType = ModelDataLoader::FilterType::UnknownFilter; switch (dataType) { case ElisaUtils::FileName: { auto result = d->mFileScanner.scanOneFile(fileName, d->mMimeDatabase); Q_EMIT allTrackData(result.toTrackData()); break; } case ElisaUtils::Track: case ElisaUtils::Album: case ElisaUtils::Artist: case ElisaUtils::Composer: case ElisaUtils::Genre: case ElisaUtils::Lyricist: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadRecentlyPlayedData(ElisaUtils::PlayListEntryType dataType) { if (!d->mDatabase) { return; } - d->mFilterType = ModelDataLoader::FilterType::RecentlyPlayed; + d->mFilterType = ModelDataLoader::FilterType::FilterByRecentlyPlayed; switch (dataType) { case ElisaUtils::Track: Q_EMIT allTracksData(d->mDatabase->recentlyPlayedTracksData(50)); break; case ElisaUtils::Album: case ElisaUtils::Artist: case ElisaUtils::Composer: case ElisaUtils::Genre: case ElisaUtils::Lyricist: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::loadFrequentlyPlayedData(ElisaUtils::PlayListEntryType dataType) { if (!d->mDatabase) { return; } - d->mFilterType = ModelDataLoader::FilterType::FrequentlyPlayed; + d->mFilterType = ModelDataLoader::FilterType::FilterByFrequentlyPlayed; switch (dataType) { case ElisaUtils::Track: Q_EMIT allTracksData(d->mDatabase->frequentlyPlayedTracksData(50)); break; case ElisaUtils::Album: case ElisaUtils::Artist: case ElisaUtils::Composer: case ElisaUtils::Genre: case ElisaUtils::Lyricist: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } void ModelDataLoader::databaseTracksAdded(const ListTrackDataType &newData) { switch(d->mFilterType) { case ModelDataLoader::FilterType::NoFilter: Q_EMIT tracksAdded(newData); break; case ModelDataLoader::FilterType::FilterById: { auto filteredData = newData; auto new_end = std::remove_if(filteredData.begin(), filteredData.end(), [&](const auto &oneTrack) { return oneTrack.albumId() != d->mDatabaseId; }); filteredData.erase(new_end, filteredData.end()); Q_EMIT tracksAdded(filteredData); break; } case ModelDataLoader::FilterType::FilterByGenre: case ModelDataLoader::FilterType::FilterByGenreAndArtist: case ModelDataLoader::FilterType::FilterByArtist: - case ModelDataLoader::FilterType::RecentlyPlayed: - case ModelDataLoader::FilterType::FrequentlyPlayed: - case ModelDataLoader::FilterType::Unknown: + case ModelDataLoader::FilterType::FilterByRecentlyPlayed: + case ModelDataLoader::FilterType::FilterByFrequentlyPlayed: + case ModelDataLoader::FilterType::UnknownFilter: break; } } void ModelDataLoader::databaseTrackModified(const TrackDataType &modifiedTrack) { Q_EMIT trackModified(modifiedTrack); } void ModelDataLoader::databaseTrackRemoved(qulonglong removedTrackId) { Q_EMIT trackRemoved(removedTrackId); } void ModelDataLoader::databaseGenresAdded(const ListGenreDataType &newData) { Q_EMIT genresAdded(newData); } void ModelDataLoader::databaseArtistsAdded(const ListArtistDataType &newData) { switch(d->mFilterType) { case ModelDataLoader::FilterType::FilterByGenre: { auto filteredData = newData; auto new_end = std::remove_if(filteredData.begin(), filteredData.end(), [&](const auto &oneArtist){return !d->mDatabase->internalArtistMatchGenre(oneArtist.databaseId(), d->mGenre);}); filteredData.erase(new_end, filteredData.end()); Q_EMIT artistsAdded(filteredData); break; } case ModelDataLoader::FilterType::NoFilter: Q_EMIT artistsAdded(newData); break; case ModelDataLoader::FilterType::FilterByGenreAndArtist: case ModelDataLoader::FilterType::FilterByArtist: case ModelDataLoader::FilterType::FilterById: - case ModelDataLoader::FilterType::RecentlyPlayed: - case ModelDataLoader::FilterType::FrequentlyPlayed: - case ModelDataLoader::FilterType::Unknown: + case ModelDataLoader::FilterType::FilterByRecentlyPlayed: + case ModelDataLoader::FilterType::FilterByFrequentlyPlayed: + case ModelDataLoader::FilterType::UnknownFilter: break; } } void ModelDataLoader::databaseArtistRemoved(qulonglong removedDatabaseId) { Q_EMIT artistRemoved(removedDatabaseId); } void ModelDataLoader::databaseAlbumsAdded(const ListAlbumDataType &newData) { switch(d->mFilterType) { case ModelDataLoader::FilterType::FilterByArtist: { auto filteredData = newData; auto new_end = std::remove_if(filteredData.begin(), filteredData.end(), [&](const auto &oneAlbum){return oneAlbum.artist() != d->mArtist;}); filteredData.erase(new_end, filteredData.end()); Q_EMIT albumsAdded(filteredData); break; } case ModelDataLoader::FilterType::NoFilter: Q_EMIT albumsAdded(newData); break; case ModelDataLoader::FilterType::FilterByGenreAndArtist: { auto filteredData = newData; auto new_end = std::remove_if(filteredData.begin(), filteredData.end(), [&](const auto &oneAlbum){ const auto &allGenres = oneAlbum.genres(); return oneAlbum.artist() != d->mArtist || !allGenres.contains(d->mGenre); }); filteredData.erase(new_end, filteredData.end()); Q_EMIT albumsAdded(filteredData); break; } case ModelDataLoader::FilterType::FilterByGenre: case ModelDataLoader::FilterType::FilterById: - case ModelDataLoader::FilterType::RecentlyPlayed: - case ModelDataLoader::FilterType::FrequentlyPlayed: - case ModelDataLoader::FilterType::Unknown: + case ModelDataLoader::FilterType::FilterByRecentlyPlayed: + case ModelDataLoader::FilterType::FilterByFrequentlyPlayed: + case ModelDataLoader::FilterType::UnknownFilter: break; } } void ModelDataLoader::databaseAlbumRemoved(qulonglong removedDatabaseId) { Q_EMIT albumRemoved(removedDatabaseId); } void ModelDataLoader::databaseAlbumModified(const AlbumDataType &modifiedAlbum) { Q_EMIT albumModified(modifiedAlbum); } #include "moc_modeldataloader.cpp" diff --git a/src/modeldataloader.h b/src/modeldataloader.h index f277a37e..7de66d14 100644 --- a/src/modeldataloader.h +++ b/src/modeldataloader.h @@ -1,136 +1,136 @@ /* * Copyright 2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #ifndef MODELDATALOADER_H #define MODELDATALOADER_H #include "elisaLib_export.h" #include "elisautils.h" #include "databaseinterface.h" #include "models/datamodel.h" #include #include class ModelDataLoaderPrivate; class ELISALIB_EXPORT ModelDataLoader : public QObject { Q_OBJECT public: using ListAlbumDataType = DatabaseInterface::ListAlbumDataType; using ListArtistDataType = DatabaseInterface::ListArtistDataType; using ListGenreDataType = DatabaseInterface::ListGenreDataType; using ListTrackDataType = DatabaseInterface::ListTrackDataType; using TrackDataType = DatabaseInterface::TrackDataType; using AlbumDataType = DatabaseInterface::AlbumDataType; - using FilterType = DataModel::FilterType; + using FilterType = ElisaUtils::FilterType; explicit ModelDataLoader(QObject *parent = nullptr); ~ModelDataLoader() override; void setDatabase(DatabaseInterface *database); Q_SIGNALS: void allAlbumsData(const ModelDataLoader::ListAlbumDataType &allData); void allArtistsData(const ModelDataLoader::ListArtistDataType &allData); void allGenresData(const ModelDataLoader::ListGenreDataType &allData); void allTracksData(const ModelDataLoader::ListTrackDataType &allData); void allTrackData(const ModelDataLoader::TrackDataType &allData); void tracksAdded(ModelDataLoader::ListTrackDataType newData); void trackModified(const ModelDataLoader::TrackDataType &modifiedTrack); void trackRemoved(qulonglong removedTrackId); void genresAdded(ModelDataLoader::ListGenreDataType newData); void artistsAdded(ModelDataLoader::ListArtistDataType newData); void artistRemoved(qulonglong removedDatabaseId); void albumsAdded(ModelDataLoader::ListAlbumDataType newData); void albumRemoved(qulonglong removedDatabaseId); void albumModified(const ModelDataLoader::AlbumDataType &modifiedAlbum); public Q_SLOTS: void loadData(ElisaUtils::PlayListEntryType dataType); void loadDataByAlbumId(ElisaUtils::PlayListEntryType dataType, qulonglong databaseId); void loadDataByGenre(ElisaUtils::PlayListEntryType dataType, const QString &genre); void loadDataByArtist(ElisaUtils::PlayListEntryType dataType, const QString &artist); void loadDataByGenreAndArtist(ElisaUtils::PlayListEntryType dataType, const QString &genre, const QString &artist); void loadDataByDatabaseId(ElisaUtils::PlayListEntryType dataType, qulonglong databaseId); void loadDataByFileName(ElisaUtils::PlayListEntryType dataType, const QUrl &fileName); void loadRecentlyPlayedData(ElisaUtils::PlayListEntryType dataType); void loadFrequentlyPlayedData(ElisaUtils::PlayListEntryType dataType); private: void databaseTracksAdded(const ListTrackDataType &newData); void databaseTrackModified(const TrackDataType &modifiedTrack); void databaseTrackRemoved(qulonglong removedTrackId); void databaseGenresAdded(const ListGenreDataType &newData); void databaseArtistsAdded(const ListArtistDataType &newData); void databaseArtistRemoved(qulonglong removedDatabaseId); void databaseAlbumsAdded(const ListAlbumDataType &newData); void databaseAlbumRemoved(qulonglong removedDatabaseId); void databaseAlbumModified(const AlbumDataType &modifiedAlbum); private: std::unique_ptr d; }; #endif // MODELDATALOADER_H diff --git a/src/models/alltracksproxymodel.cpp b/src/models/alltracksproxymodel.cpp index c46f211d..f23216fe 100644 --- a/src/models/alltracksproxymodel.cpp +++ b/src/models/alltracksproxymodel.cpp @@ -1,98 +1,85 @@ /* * Copyright 2017 Alexander Stippich * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "alltracksproxymodel.h" #include "databaseinterface.h" #include #include AllTracksProxyModel::AllTracksProxyModel(QObject *parent) : AbstractMediaProxyModel(parent) { setSortCaseSensitivity(Qt::CaseInsensitive); sortModel(Qt::AscendingOrder); } AllTracksProxyModel::~AllTracksProxyModel() = default; bool AllTracksProxyModel::filterAcceptsRow(int source_row, const QModelIndex &source_parent) const { bool result = false; - for (int column = 0, columnCount = sourceModel()->columnCount(source_parent); column < columnCount; ++column) { - auto currentIndex = sourceModel()->index(source_row, column, source_parent); + auto currentIndex = sourceModel()->index(source_row, 0, source_parent); - const auto &titleValue = sourceModel()->data(currentIndex, Qt::DisplayRole).toString(); - const auto &artistValue = sourceModel()->data(currentIndex, DatabaseInterface::ColumnsRoles::ArtistRole).toString(); - const auto maximumRatingValue = sourceModel()->data(currentIndex, DatabaseInterface::ColumnsRoles::RatingRole).toInt(); + const auto &titleValue = sourceModel()->data(currentIndex, Qt::DisplayRole).toString(); + const auto &artistValue = sourceModel()->data(currentIndex, DatabaseInterface::ColumnsRoles::ArtistRole).toString(); + const auto maximumRatingValue = sourceModel()->data(currentIndex, DatabaseInterface::ColumnsRoles::RatingRole).toInt(); - if (maximumRatingValue < mFilterRating) { - result = false; - continue; - } - - if (mFilterExpression.match(titleValue).hasMatch()) { - result = true; - continue; - } - - if (mFilterExpression.match(artistValue).hasMatch()) { - result = true; - continue; - } + if (maximumRatingValue < mFilterRating) { + return result; + } - if (result) { - continue; - } + if (mFilterExpression.match(titleValue).hasMatch()) { + result = true; + } - if (!result) { - break; - } + if (mFilterExpression.match(artistValue).hasMatch()) { + result = true; } return result; } void AllTracksProxyModel::genericEnqueueToPlayList(ElisaUtils::PlayListEnqueueMode enqueueMode, ElisaUtils::PlayListEnqueueTriggerPlay triggerPlay) { QtConcurrent::run(&mThreadPool, [=] () { QReadLocker locker(&mDataLock); - auto allTracks = ElisaUtils::EntryDataList(); + auto allTracks = ElisaUtils::EntryDataList{}; allTracks.reserve(rowCount()); for (int rowIndex = 0, maxRowCount = rowCount(); rowIndex < maxRowCount; ++rowIndex) { auto currentIndex = index(rowIndex, 0); allTracks.push_back(ElisaUtils::EntryData{data(currentIndex, DatabaseInterface::ColumnsRoles::DatabaseIdRole).toULongLong(), data(currentIndex, DatabaseInterface::ColumnsRoles::TitleRole).toString()}); } Q_EMIT entriesToEnqueue(allTracks, ElisaUtils::Track, enqueueMode, triggerPlay); }); } void AllTracksProxyModel::enqueueToPlayList() { genericEnqueueToPlayList(ElisaUtils::AppendPlayList, ElisaUtils::DoNotTriggerPlay); } void AllTracksProxyModel::replaceAndPlayOfPlayList() { genericEnqueueToPlayList(ElisaUtils::ReplacePlayList, ElisaUtils::TriggerPlay); } #include "moc_alltracksproxymodel.cpp" diff --git a/src/models/datamodel.cpp b/src/models/datamodel.cpp index 357847e1..039d59c2 100644 --- a/src/models/datamodel.cpp +++ b/src/models/datamodel.cpp @@ -1,707 +1,666 @@ /* * Copyright 2015-2017 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "datamodel.h" #include "modeldataloader.h" #include "musiclistenersmanager.h" #include #include #include #include #include #include class DataModelPrivate { public: DataModel::ListTrackDataType mAllTrackData; DataModel::ListAlbumDataType mAllAlbumData; DataModel::ListArtistDataType mAllArtistData; DataModel::ListGenreDataType mAllGenreData; ModelDataLoader mDataLoader; ElisaUtils::PlayListEntryType mModelType = ElisaUtils::Unknown; - DataModel::FilterType mFilterType = DataModel::Unknown; + ElisaUtils::FilterType mFilterType = ElisaUtils::UnknownFilter; QString mArtist; QString mAlbumTitle; QString mAlbumArtist; QString mGenre; qulonglong mDatabaseId = 0; bool mIsBusy = false; }; DataModel::DataModel(QObject *parent) : QAbstractListModel(parent), d(std::make_unique()) { } DataModel::~DataModel() = default; int DataModel::rowCount(const QModelIndex &parent) const { auto dataCount = 0; if (parent.isValid()) { return dataCount; } dataCount = d->mAllTrackData.size() + d->mAllAlbumData.size() + d->mAllArtistData.size() + d->mAllGenreData.size(); return dataCount; } QHash DataModel::roleNames() const { auto roles = QAbstractListModel::roleNames(); roles[static_cast(DatabaseInterface::ColumnsRoles::TitleRole)] = "title"; roles[static_cast(DatabaseInterface::ColumnsRoles::SecondaryTextRole)] = "secondaryText"; roles[static_cast(DatabaseInterface::ColumnsRoles::ImageUrlRole)] = "imageUrl"; roles[static_cast(DatabaseInterface::ColumnsRoles::DatabaseIdRole)] = "databaseId"; roles[static_cast(DatabaseInterface::ColumnsRoles::ElementTypeRole)] = "dataType"; roles[static_cast(DatabaseInterface::ColumnsRoles::ArtistRole)] = "artist"; roles[static_cast(DatabaseInterface::ColumnsRoles::AllArtistsRole)] = "allArtists"; roles[static_cast(DatabaseInterface::ColumnsRoles::HighestTrackRating)] = "highestTrackRating"; roles[static_cast(DatabaseInterface::ColumnsRoles::GenreRole)] = "genre"; roles[static_cast(DatabaseInterface::ColumnsRoles::AlbumRole)] = "album"; roles[static_cast(DatabaseInterface::ColumnsRoles::AlbumArtistRole)] = "albumArtist"; roles[static_cast(DatabaseInterface::ColumnsRoles::DurationRole)] = "duration"; roles[static_cast(DatabaseInterface::ColumnsRoles::TrackNumberRole)] = "trackNumber"; roles[static_cast(DatabaseInterface::ColumnsRoles::DiscNumberRole)] = "discNumber"; roles[static_cast(DatabaseInterface::ColumnsRoles::RatingRole)] = "rating"; roles[static_cast(DatabaseInterface::ColumnsRoles::IsSingleDiscAlbumRole)] = "isSingleDiscAlbum"; return roles; } Qt::ItemFlags DataModel::flags(const QModelIndex &index) const { if (!index.isValid()) { return Qt::NoItemFlags; } return Qt::ItemIsSelectable | Qt::ItemIsEnabled; } QVariant DataModel::data(const QModelIndex &index, int role) const { auto result = QVariant(); const auto dataCount = d->mAllTrackData.size() + d->mAllAlbumData.size() + d->mAllArtistData.size() + d->mAllGenreData.size(); Q_ASSERT(index.isValid()); Q_ASSERT(index.column() == 0); Q_ASSERT(index.row() >= 0 && index.row() < dataCount); Q_ASSERT(!index.parent().isValid()); Q_ASSERT(index.model() == this); Q_ASSERT(index.internalId() == 0); switch(role) { case Qt::DisplayRole: switch(d->mModelType) { case ElisaUtils::Track: result = d->mAllTrackData[index.row()][TrackDataType::key_type::TitleRole]; break; case ElisaUtils::Album: result = d->mAllAlbumData[index.row()][AlbumDataType::key_type::TitleRole]; break; case ElisaUtils::Artist: result = d->mAllArtistData[index.row()][ArtistDataType::key_type::TitleRole]; break; case ElisaUtils::Genre: result = d->mAllGenreData[index.row()][GenreDataType::key_type::TitleRole]; break; case ElisaUtils::Lyricist: case ElisaUtils::Composer: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } break; case DatabaseInterface::ColumnsRoles::DurationRole: { if (d->mModelType == ElisaUtils::Track) { auto trackDuration = d->mAllTrackData[index.row()][TrackDataType::key_type::DurationRole].toTime(); if (trackDuration.hour() == 0) { result = trackDuration.toString(QStringLiteral("mm:ss")); } else { result = trackDuration.toString(); } } break; } default: switch(d->mModelType) { case ElisaUtils::Track: result = d->mAllTrackData[index.row()][static_cast(role)]; break; case ElisaUtils::Album: result = d->mAllAlbumData[index.row()][static_cast(role)]; break; case ElisaUtils::Artist: result = d->mAllArtistData[index.row()][static_cast(role)]; break; case ElisaUtils::Genre: result = d->mAllGenreData[index.row()][static_cast(role)]; break; case ElisaUtils::Lyricist: case ElisaUtils::Composer: case ElisaUtils::FileName: case ElisaUtils::Unknown: break; } } return result; } QModelIndex DataModel::index(int row, int column, const QModelIndex &parent) const { auto result = QModelIndex(); if (column != 0) { return result; } if (parent.isValid()) { return result; } result = createIndex(row, column); return result; } QModelIndex DataModel::parent(const QModelIndex &child) const { Q_UNUSED(child) auto result = QModelIndex(); return result; } QString DataModel::title() const { return d->mAlbumTitle; } QString DataModel::author() const { return d->mAlbumArtist; } bool DataModel::isBusy() const { return d->mIsBusy; } void DataModel::initialize(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType) -{ - initializeModel(manager, database, modelType, FilterType::NoFilter); -} - -void DataModel::initializeById(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, qulonglong databaseId) + ElisaUtils::PlayListEntryType modelType, ElisaUtils::FilterType filter, + const QString &genre, const QString &artist, qulonglong databaseId) { d->mDatabaseId = databaseId; - - initializeModel(manager, database, modelType, FilterType::FilterById); -} - -void DataModel::initializeByGenre(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, const QString &genre) -{ d->mGenre = genre; - - initializeModel(manager, database, modelType, FilterType::FilterByGenre); -} - -void DataModel::initializeByArtist(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, const QString &artist) -{ d->mArtist = artist; - initializeModel(manager, database, modelType, FilterType::FilterByArtist); -} - -void DataModel::initializeByGenreAndArtist(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, const QString &genre, - const QString &artist) -{ - d->mGenre = genre; - d->mArtist = artist; - - initializeModel(manager, database, modelType, FilterType::FilterByGenreAndArtist); -} - -void DataModel::initializeRecentlyPlayed(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType) -{ - initializeModel(manager, database, modelType, FilterType::RecentlyPlayed); -} - -void DataModel::initializeFrequentlyPlayed(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType) -{ - initializeModel(manager, database, modelType, FilterType::FrequentlyPlayed); + initializeModel(manager, database, modelType, filter); } void DataModel::setBusy(bool value) { if (d->mIsBusy == value) { return; } d->mIsBusy = value; Q_EMIT isBusyChanged(); } void DataModel::initializeModel(MusicListenersManager *manager, DatabaseInterface *database, ElisaUtils::PlayListEntryType modelType, DataModel::FilterType type) { d->mModelType = modelType; d->mFilterType = type; if (manager) { manager->connectModel(&d->mDataLoader); } if (manager) { connectModel(manager->viewDatabase()); } else if (database) { connectModel(database); } else { return; } switch(d->mFilterType) { - case NoFilter: + case ElisaUtils::NoFilter: connect(this, &DataModel::needData, &d->mDataLoader, &ModelDataLoader::loadData); break; - case FilterById: + case ElisaUtils::FilterById: connect(this, &DataModel::needDataById, &d->mDataLoader, &ModelDataLoader::loadDataByAlbumId); break; - case FilterByGenre: + case ElisaUtils::FilterByGenre: connect(this, &DataModel::needDataByGenre, &d->mDataLoader, &ModelDataLoader::loadDataByGenre); break; - case FilterByArtist: + case ElisaUtils::FilterByArtist: connect(this, &DataModel::needDataByArtist, &d->mDataLoader, &ModelDataLoader::loadDataByArtist); break; - case FilterByGenreAndArtist: + case ElisaUtils::FilterByGenreAndArtist: connect(this, &DataModel::needDataByGenreAndArtist, &d->mDataLoader, &ModelDataLoader::loadDataByGenreAndArtist); break; - case RecentlyPlayed: + case ElisaUtils::FilterByRecentlyPlayed: connect(this, &DataModel::needRecentlyPlayedData, &d->mDataLoader, &ModelDataLoader::loadRecentlyPlayedData); break; - case FrequentlyPlayed: + case ElisaUtils::FilterByFrequentlyPlayed: connect(this, &DataModel::needFrequentlyPlayedData, &d->mDataLoader, &ModelDataLoader::loadFrequentlyPlayedData); break; - case Unknown: + case ElisaUtils::UnknownFilter: break; } setBusy(true); askModelData(); } void DataModel::askModelData() { switch(d->mFilterType) { - case NoFilter: + case ElisaUtils::NoFilter: Q_EMIT needData(d->mModelType); break; - case FilterById: + case ElisaUtils::FilterById: Q_EMIT needDataById(d->mModelType, d->mDatabaseId); break; - case FilterByGenre: + case ElisaUtils::FilterByGenre: Q_EMIT needDataByGenre(d->mModelType, d->mGenre); break; - case FilterByArtist: + case ElisaUtils::FilterByArtist: Q_EMIT needDataByArtist(d->mModelType, d->mArtist); break; - case FilterByGenreAndArtist: + case ElisaUtils::FilterByGenreAndArtist: Q_EMIT needDataByGenreAndArtist(d->mModelType, d->mGenre, d->mArtist); break; - case RecentlyPlayed: + case ElisaUtils::FilterByRecentlyPlayed: Q_EMIT needRecentlyPlayedData(d->mModelType); break; - case FrequentlyPlayed: + case ElisaUtils::FilterByFrequentlyPlayed: Q_EMIT needFrequentlyPlayedData(d->mModelType); break; - case Unknown: + case ElisaUtils::UnknownFilter: break; } } int DataModel::trackIndexFromId(qulonglong id) const { int result; for (result = 0; result < d->mAllTrackData.size(); ++result) { if (d->mAllTrackData[result].databaseId() == id) { return result; } } result = -1; return result; } void DataModel::connectModel(DatabaseInterface *database) { d->mDataLoader.setDatabase(database); connect(&d->mDataLoader, &ModelDataLoader::allTracksData, this, &DataModel::tracksAdded); connect(&d->mDataLoader, &ModelDataLoader::allAlbumsData, this, &DataModel::albumsAdded); connect(&d->mDataLoader, &ModelDataLoader::allArtistsData, this, &DataModel::artistsAdded); connect(&d->mDataLoader, &ModelDataLoader::allGenresData, this, &DataModel::genresAdded); connect(&d->mDataLoader, &ModelDataLoader::genresAdded, this, &DataModel::genresAdded); connect(&d->mDataLoader, &ModelDataLoader::albumsAdded, this, &DataModel::albumsAdded); connect(&d->mDataLoader, &ModelDataLoader::albumModified, this, &DataModel::albumModified); connect(&d->mDataLoader, &ModelDataLoader::albumRemoved, this, &DataModel::albumRemoved); connect(&d->mDataLoader, &ModelDataLoader::tracksAdded, this, &DataModel::tracksAdded); connect(&d->mDataLoader, &ModelDataLoader::trackModified, this, &DataModel::trackModified); connect(&d->mDataLoader, &ModelDataLoader::trackRemoved, this, &DataModel::trackRemoved); connect(&d->mDataLoader, &ModelDataLoader::artistsAdded, this, &DataModel::artistsAdded); connect(&d->mDataLoader, &ModelDataLoader::artistRemoved, this, &DataModel::artistRemoved); } void DataModel::tracksAdded(ListTrackDataType newData) { if (newData.isEmpty() && d->mModelType == ElisaUtils::Track) { setBusy(false); } if (newData.isEmpty() || d->mModelType != ElisaUtils::Track) { return; } - if (d->mFilterType == FilterById && !d->mAllTrackData.isEmpty()) { + if (d->mFilterType == ElisaUtils::FilterById && !d->mAllTrackData.isEmpty()) { for (const auto &newTrack : newData) { auto trackIndex = trackIndexFromId(newTrack.databaseId()); if (trackIndex != -1) { continue; } bool trackInserted = false; for (int trackIndex = 0; trackIndex < d->mAllTrackData.count(); ++trackIndex) { const auto &oneTrack = d->mAllTrackData[trackIndex]; if (oneTrack.discNumber() >= newTrack.discNumber() && oneTrack.trackNumber() > newTrack.trackNumber()) { beginInsertRows({}, trackIndex, trackIndex); d->mAllTrackData.insert(trackIndex, newTrack); endInsertRows(); if (d->mAllTrackData.size() == 1) { setBusy(false); } trackInserted = true; break; } } if (!trackInserted) { beginInsertRows({}, d->mAllTrackData.count(), d->mAllTrackData.count()); d->mAllTrackData.insert(d->mAllTrackData.count(), newTrack); endInsertRows(); if (d->mAllTrackData.size() == 1) { setBusy(false); } } } } else { if (d->mAllTrackData.isEmpty()) { beginInsertRows({}, 0, newData.size() - 1); d->mAllTrackData.swap(newData); endInsertRows(); setBusy(false); } else { beginInsertRows({}, d->mAllTrackData.size(), d->mAllTrackData.size() + newData.size() - 1); d->mAllTrackData.append(newData); endInsertRows(); } } } void DataModel::trackModified(const TrackDataType &modifiedTrack) { if (d->mModelType != ElisaUtils::Track) { return; } if (!d->mAlbumTitle.isEmpty() && !d->mAlbumArtist.isEmpty()) { if (modifiedTrack.album() != d->mAlbumTitle) { return; } auto trackIndex = trackIndexFromId(modifiedTrack.databaseId()); if (trackIndex == -1) { return; } d->mAllTrackData[trackIndex] = modifiedTrack; Q_EMIT dataChanged(index(trackIndex, 0), index(trackIndex, 0)); } else { auto itTrack = std::find_if(d->mAllTrackData.begin(), d->mAllTrackData.end(), [modifiedTrack](auto track) { return track.databaseId() == modifiedTrack.databaseId(); }); if (itTrack == d->mAllTrackData.end()) { return; } auto position = itTrack - d->mAllTrackData.begin(); d->mAllTrackData[position] = modifiedTrack; Q_EMIT dataChanged(index(position, 0), index(position, 0)); } } void DataModel::trackRemoved(qulonglong removedTrackId) { if (d->mModelType != ElisaUtils::Track) { return; } if (!d->mAlbumTitle.isEmpty() && !d->mAlbumArtist.isEmpty()) { auto trackIndex = trackIndexFromId(removedTrackId); if (trackIndex == -1) { return; } beginRemoveRows({}, trackIndex, trackIndex); d->mAllTrackData.removeAt(trackIndex); endRemoveRows(); } else { auto itTrack = std::find_if(d->mAllTrackData.begin(), d->mAllTrackData.end(), [removedTrackId](auto track) {return track.databaseId() == removedTrackId;}); if (itTrack == d->mAllTrackData.end()) { return; } auto position = itTrack - d->mAllTrackData.begin(); beginRemoveRows({}, position, position); d->mAllTrackData.erase(itTrack); endRemoveRows(); } } void DataModel::genresAdded(DataModel::ListGenreDataType newData) { if (newData.isEmpty() && d->mModelType == ElisaUtils::Genre) { setBusy(false); } if (newData.isEmpty() || d->mModelType != ElisaUtils::Genre) { return; } if (d->mAllGenreData.isEmpty()) { beginInsertRows({}, d->mAllGenreData.size(), newData.size() - 1); d->mAllGenreData.swap(newData); endInsertRows(); setBusy(false); } else { beginInsertRows({}, d->mAllGenreData.size(), d->mAllGenreData.size() + newData.size() - 1); d->mAllGenreData.append(newData); endInsertRows(); } } void DataModel::artistsAdded(DataModel::ListArtistDataType newData) { if (newData.isEmpty() && d->mModelType == ElisaUtils::Artist) { setBusy(false); } if (newData.isEmpty() || d->mModelType != ElisaUtils::Artist) { return; } if (d->mAllArtistData.isEmpty()) { beginInsertRows({}, d->mAllArtistData.size(), newData.size() - 1); d->mAllArtistData.swap(newData); endInsertRows(); setBusy(false); } else { beginInsertRows({}, d->mAllArtistData.size(), d->mAllArtistData.size() + newData.size() - 1); d->mAllArtistData.append(newData); endInsertRows(); } } void DataModel::artistRemoved(qulonglong removedDatabaseId) { if (d->mModelType != ElisaUtils::Artist) { return; } auto removedDataIterator = d->mAllArtistData.end(); removedDataIterator = std::find_if(d->mAllArtistData.begin(), d->mAllArtistData.end(), [removedDatabaseId](auto album) {return album.databaseId() == removedDatabaseId;}); if (removedDataIterator == d->mAllArtistData.end()) { return; } int dataIndex = removedDataIterator - d->mAllArtistData.begin(); beginRemoveRows({}, dataIndex, dataIndex); d->mAllArtistData.erase(removedDataIterator); endRemoveRows(); } void DataModel::albumsAdded(DataModel::ListAlbumDataType newData) { if (newData.isEmpty() && d->mModelType == ElisaUtils::Album) { setBusy(false); } if (newData.isEmpty() || d->mModelType != ElisaUtils::Album) { return; } if (d->mAllAlbumData.isEmpty()) { beginInsertRows({}, d->mAllAlbumData.size(), newData.size() - 1); d->mAllAlbumData.swap(newData); endInsertRows(); setBusy(false); } else { beginInsertRows({}, d->mAllAlbumData.size(), d->mAllAlbumData.size() + newData.size() - 1); d->mAllAlbumData.append(newData); endInsertRows(); } } void DataModel::albumRemoved(qulonglong removedDatabaseId) { if (d->mModelType != ElisaUtils::Album) { return; } auto removedDataIterator = d->mAllAlbumData.end(); removedDataIterator = std::find_if(d->mAllAlbumData.begin(), d->mAllAlbumData.end(), [removedDatabaseId](auto album) {return album.databaseId() == removedDatabaseId;}); if (removedDataIterator == d->mAllAlbumData.end()) { return; } int dataIndex = removedDataIterator - d->mAllAlbumData.begin(); beginRemoveRows({}, dataIndex, dataIndex); d->mAllAlbumData.erase(removedDataIterator); endRemoveRows(); } void DataModel::albumModified(const DataModel::AlbumDataType &modifiedAlbum) { if (d->mModelType != ElisaUtils::Album) { return; } auto modifiedAlbumIterator = std::find_if(d->mAllAlbumData.begin(), d->mAllAlbumData.end(), [modifiedAlbum](auto album) { return album.databaseId() == modifiedAlbum.databaseId(); }); if (modifiedAlbumIterator == d->mAllAlbumData.end()) { return; } auto albumIndex = modifiedAlbumIterator - d->mAllAlbumData.begin(); Q_EMIT dataChanged(index(albumIndex, 0), index(albumIndex, 0)); } void DataModel::cleanedDatabase() { beginResetModel(); d->mAllAlbumData.clear(); d->mAllGenreData.clear(); d->mAllTrackData.clear(); d->mAllArtistData.clear(); endResetModel(); } #include "moc_datamodel.cpp" diff --git a/src/models/datamodel.h b/src/models/datamodel.h index a39b6147..ef5640bb 100644 --- a/src/models/datamodel.h +++ b/src/models/datamodel.h @@ -1,190 +1,161 @@ /* * Copyright 2015-2017 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #ifndef DATAMODEL_H #define DATAMODEL_H #include "elisaLib_export.h" #include "elisautils.h" #include "databaseinterface.h" #include #include #include #include #include class DataModelPrivate; class MusicListenersManager; class DatabaseInterface; class ELISALIB_EXPORT DataModel : public QAbstractListModel { Q_OBJECT Q_PROPERTY(QString title READ title NOTIFY titleChanged) Q_PROPERTY(QString author READ author NOTIFY authorChanged) Q_PROPERTY(bool isBusy READ isBusy NOTIFY isBusyChanged) public: - enum FilterType { - Unknown, - NoFilter, - FilterById, - FilterByGenre, - FilterByArtist, - FilterByGenreAndArtist, - RecentlyPlayed, - FrequentlyPlayed, - }; - - Q_ENUM(FilterType) - using ListTrackDataType = DatabaseInterface::ListTrackDataType; using TrackDataType = DatabaseInterface::TrackDataType; using ListAlbumDataType = DatabaseInterface::ListAlbumDataType; using AlbumDataType = DatabaseInterface::AlbumDataType; using ListArtistDataType = DatabaseInterface::ListArtistDataType; using ArtistDataType = DatabaseInterface::ArtistDataType; using ListGenreDataType = DatabaseInterface::ListGenreDataType; using GenreDataType = DatabaseInterface::GenreDataType; + using FilterType = ElisaUtils::FilterType; + explicit DataModel(QObject *parent = nullptr); ~DataModel() override; int rowCount(const QModelIndex &parent = QModelIndex()) const override; QHash roleNames() const override; Qt::ItemFlags flags(const QModelIndex &index) const override; QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override; QModelIndex index(int row, int column, const QModelIndex &parent = QModelIndex()) const override; QModelIndex parent(const QModelIndex &child) const override; QString title() const; QString author() const; bool isBusy() const; Q_SIGNALS: void titleChanged(); void authorChanged(); void needData(ElisaUtils::PlayListEntryType dataType); void needDataById(ElisaUtils::PlayListEntryType dataType, qulonglong databaseId); void needDataByGenre(ElisaUtils::PlayListEntryType dataType, const QString &genre); void needDataByArtist(ElisaUtils::PlayListEntryType dataType, const QString &artist); void needDataByGenreAndArtist(ElisaUtils::PlayListEntryType dataType, const QString &genre, const QString &artist); void needRecentlyPlayedData(ElisaUtils::PlayListEntryType dataType); void needFrequentlyPlayedData(ElisaUtils::PlayListEntryType dataType); void isBusyChanged(); public Q_SLOTS: void tracksAdded(DataModel::ListTrackDataType newData); void trackModified(const DataModel::TrackDataType &modifiedTrack); void trackRemoved(qulonglong removedTrackId); void genresAdded(DataModel::ListGenreDataType newData); void artistsAdded(DataModel::ListArtistDataType newData); void artistRemoved(qulonglong removedDatabaseId); void albumsAdded(DataModel::ListAlbumDataType newData); void albumRemoved(qulonglong removedDatabaseId); void albumModified(const DataModel::AlbumDataType &modifiedAlbum); void initialize(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType); - - void initializeById(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, qulonglong databaseId); - - void initializeByGenre(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, const QString &genre); - - void initializeByArtist(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, const QString &artist); - - void initializeByGenreAndArtist(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, const QString &genre, - const QString &artist); - - void initializeRecentlyPlayed(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType); - - void initializeFrequentlyPlayed(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType); + ElisaUtils::PlayListEntryType modelType, ElisaUtils::FilterType filter, + const QString &genre, const QString &artist, qulonglong databaseId); private Q_SLOTS: void cleanedDatabase(); private: int trackIndexFromId(qulonglong id) const; void connectModel(DatabaseInterface *database); void setBusy(bool value); void initializeModel(MusicListenersManager *manager, DatabaseInterface *database, - ElisaUtils::PlayListEntryType modelType, FilterType type); + ElisaUtils::PlayListEntryType modelType, ElisaUtils::FilterType type); void askModelData(); std::unique_ptr d; }; #endif // DATAMODEL_H diff --git a/src/qml/AlbumView.qml b/src/qml/AlbumView.qml deleted file mode 100644 index a9fdb7bc..00000000 --- a/src/qml/AlbumView.qml +++ /dev/null @@ -1,133 +0,0 @@ -/* - * Copyright 2018 Matthieu Gallien - * - * This program is free software: you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 3 of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this program. If not, see . - */ - -import QtQuick 2.10 -import QtQuick.Controls 2.3 -import org.kde.kirigami 2.5 as Kirigami -import org.kde.elisa 1.0 - -FocusScope { - id: viewHeader - - property var viewType - property alias mainTitle: albumGridView.mainTitle - property alias secondaryTitle: albumGridView.secondaryTitle - property alias image: albumGridView.image - property alias databaseId: albumGridView.databaseId - - DataModel { - id: realModel - } - - SingleAlbumProxyModel { - id: proxyModel - - sourceModel: realModel - - onEntriesToEnqueue: elisa.mediaPlayList.enqueue(newEntries, databaseIdType, enqueueMode, triggerPlay) - } - - ListBrowserView { - id: albumGridView - - focus: true - - anchors.fill: parent - - contentModel: proxyModel - - isSubPage: true - - enableSorting: false - - delegate: MediaAlbumTrackDelegate { - id: entry - - width: albumGridView.delegateWidth - height: ((true && !true) ? elisaTheme.delegateHeight*2 : elisaTheme.delegateHeight) - - focus: true - - databaseId: model.databaseId - title: model.title - artist: model.artist - album: (model.album !== undefined && model.album !== '' ? model.album : '') - albumArtist: model.albumArtist - duration: model.duration - imageUrl: (model.imageUrl !== undefined && model.imageUrl !== '' ? model.imageUrl : '') - trackNumber: model.trackNumber - discNumber: model.discNumber - rating: model.rating - isFirstTrackOfDisc: true - isSingleDiscAlbum: true - isSelected: albumGridView.currentIndex === index - isAlternateColor: (index % 2) === 1 - - mediaTrack.onEnqueue: elisa.mediaPlayList.enqueue(databaseId, name, ElisaUtils.Track, - ElisaUtils.AppendPlayList, - ElisaUtils.DoNotTriggerPlay) - - mediaTrack.onReplaceAndPlay: elisa.mediaPlayList.enqueue(databaseId, name, ElisaUtils.Track, - ElisaUtils.ReplacePlayList, - ElisaUtils.TriggerPlay) - - - mediaTrack.onClicked: albumGridView.currentIndex = index - - onActiveFocusChanged: { - if (activeFocus && albumGridView.currentIndex !== index) { - albumGridView.currentIndex = index - } - } - } - - allowArtistNavigation: true - - onShowArtist: { - viewManager.openChildView(secondaryTitle, '', elisaTheme.artistIcon, 0, ElisaUtils.Artist) - } - - onGoBack: viewManager.goBack() - - Loader { - anchors.centerIn: parent - height: Kirigami.Units.gridUnit * 5 - width: height - - visible: realModel.isBusy - active: realModel.isBusy - - sourceComponent: BusyIndicator { - anchors.centerIn: parent - } - } - } - - Connections { - target: elisa - - onMusicManagerChanged: realModel.initializeById(elisa.musicManager, elisa.musicManager.viewDatabase, - ElisaUtils.Track, databaseId) - } - - Component.onCompleted: { - if (elisa.musicManager) { - realModel.initializeById(elisa.musicManager, elisa.musicManager.viewDatabase, - ElisaUtils.Track, databaseId) - } - } -} diff --git a/src/qml/ContentView.qml b/src/qml/ContentView.qml index 9d4976da..43d3e01a 100644 --- a/src/qml/ContentView.qml +++ b/src/qml/ContentView.qml @@ -1,512 +1,446 @@ /* * Copyright 2016-2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ import QtQuick 2.7 import QtQuick.Controls 2.2 import QtQuick.Layouts 1.2 import QtQuick.Window 2.2 import org.kde.elisa 1.0 RowLayout { id: contentViewContainer spacing: 0 property bool showPlaylist property alias currentViewIndex: listViews.currentIndex signal toggleSearch() function goBack() { viewManager.goBack() } function openArtist(name) { viewManager.openChildView(name, '', elisaTheme.artistIcon, 0, ElisaUtils.Artist) } function openAlbum(album, artist, image, albumID) { image = !image ? elisaTheme.defaultAlbumImage : image; viewManager.openChildView(album, artist, image, albumID, ElisaUtils.Album); } function openNowPlaying() { viewManager.closeAllViews(); } ViewManager { id: viewManager onSwitchOffAllViews: { listViews.setCurrentIndex(pageModel.indexFromViewType(viewType)) while(browseStackView.depth > 1) { browseStackView.pop() } } - onSwitchRecentlyPlayedTracksView: { - listViews.setCurrentIndex(pageModel.indexFromViewType(viewType)) - - while(browseStackView.depth > expectedDepth) { - browseStackView.pop() - } - - browseStackView.push(allRecentlyPlayedTracksView, { - viewType: viewType, - mainTitle: mainTitle, - image: imageUrl, - modelType: dataType, - stackView: browseStackView, - opacity: 0, - }) - } - - onSwitchFrequentlyPlayedTracksView: { - listViews.setCurrentIndex(pageModel.indexFromViewType(viewType)) - - while(browseStackView.depth > expectedDepth) { - browseStackView.pop() - } - - browseStackView.push(allFrequentlyPlayedTracksView, { - viewType: viewType, - mainTitle: mainTitle, - image: imageUrl, - modelType: dataType, - stackView: browseStackView, - opacity: 0, - }) - } - onOpenGridView: { if (expectedDepth === 1) { listViews.setCurrentIndex(pageModel.indexFromViewType(viewType)) } while(browseStackView.depth > expectedDepth) { browseStackView.pop() } browseStackView.push(dataGridView, { viewType: viewType, + filterType: filterType, mainTitle: pageModel.viewMainTitle(viewType, mainTitle), secondaryTitle: secondaryTitle, image: pageModel.viewImageUrl(viewType, imageUrl), modelType: dataType, defaultIcon: viewDefaultIcon, showRating: viewShowRating, delegateDisplaySecondaryText: viewDelegateDisplaySecondaryText, genreFilterText: genreNameFilter, artistFilter: artistNameFilter, isSubPage: (browseStackView.depth >= 2), stackView: browseStackView, opacity: 0, }) } - onSwitchOneAlbumView: { - while(browseStackView.depth > expectedDepth) { - browseStackView.pop() - } - - browseStackView.push(albumView, { - viewType: viewType, - mainTitle: mainTitle, - secondaryTitle: secondaryTitle, - image: imageUrl, - databaseId: databaseId, - stackView: browseStackView, - opacity: 0, - }) - } - - onSwitchAllTracksView: { + onOpenListView: { listViews.setCurrentIndex(pageModel.indexFromViewType(viewType)) while(browseStackView.depth > expectedDepth) { browseStackView.pop() } - browseStackView.push(allTracksView, { + browseStackView.push(dataListView, { viewType: viewType, + filterType: filterType, + isSubPage: expectedDepth > 1, mainTitle: mainTitle, + secondaryTitle: secondaryTitle, + databaseId: databaseId, image: imageUrl, modelType: dataType, + sortRole: sortRole, + sortAscending: sortOrder, stackView: browseStackView, + displaySingleAlbum: displaySingleAlbum, opacity: 0, }) } onSwitchFilesBrowserView: { listViews.setCurrentIndex(pageModel.indexFromViewType(viewType)) while(browseStackView.depth > expectedDepth) { browseStackView.pop() } browseStackView.push(filesBrowserView, { viewType: viewType, mainTitle: mainTitle, image: imageUrl, opacity: 0, }) } onPopOneView: { if (browseStackView.depth > 2) { browseStackView.pop() } } } ViewsModel { id: pageModel } ViewSelector { id: listViews model: pageModel Layout.fillHeight: true Behavior on Layout.maximumWidth { NumberAnimation { duration: 150 } } onSwitchView: viewManager.openParentView(viewType, pageModel.viewMainTitle(viewType, ""), pageModel.viewImageUrl(viewType, "")) } Rectangle { id: viewSelectorSeparatorItem Layout.fillHeight: true width: 1 color: myPalette.mid } ColumnLayout { Layout.fillHeight: true Layout.fillWidth: true spacing: 0 TopNotification { id: invalidBalooConfiguration Layout.fillWidth: true musicManager: elisa.musicManager focus: true } Item { Layout.fillHeight: true Layout.fillWidth: true RowLayout { anchors.fill: parent spacing: 0 id: contentZone FocusScope { id: mainContentView focus: true Layout.fillHeight: true Layout.minimumWidth: 0 Layout.maximumWidth: 0 Layout.preferredWidth: 0 visible: Layout.minimumWidth != 0 MouseArea { anchors.fill: parent acceptedButtons: Qt.BackButton onClicked: goBack() } Rectangle { radius: 3 color: myPalette.base anchors.fill: parent StackView { id: browseStackView anchors.fill: parent clip: true initialItem: Item { } popEnter: Transition { OpacityAnimator { from: 0.0 to: 1.0 duration: 300 } } popExit: Transition { OpacityAnimator { from: 1.0 to: 0.0 duration: 300 } } pushEnter: Transition { OpacityAnimator { from: 0.0 to: 1.0 duration: 300 } } pushExit: Transition { OpacityAnimator { from: 1.0 to: 0.0 duration: 300 } } replaceEnter: Transition { OpacityAnimator { from: 0.0 to: 1.0 duration: 300 } } replaceExit: Transition { OpacityAnimator { from: 1.0 to: 0.0 duration: 300 } } } Behavior on border.color { ColorAnimation { duration: 300 } } } } Rectangle { id: firstViewSeparatorItem Layout.fillHeight: true width: 1 color: myPalette.mid } MediaPlayListView { id: playList Layout.fillHeight: true Layout.fillWidth: true onStartPlayback: elisa.audioControl.ensurePlay() onPausePlayback: elisa.audioControl.playPause() onDisplayError: messageNotification.showNotification(errorText) } Rectangle { id: viewSeparatorItem Layout.fillHeight: true width: 1 color: myPalette.mid } Loader { id: albumContext active: Layout.minimumWidth != 0 sourceComponent: ContextView { anchors.fill: parent databaseId: elisa.manageHeaderBar.databaseId title: elisa.manageHeaderBar.title artistName: elisa.manageHeaderBar.artist albumName: elisa.manageHeaderBar.album albumArtUrl: elisa.manageHeaderBar.image fileUrl: elisa.manageHeaderBar.fileName } Layout.fillHeight: true Layout.minimumWidth: 0 Layout.maximumWidth: 0 Layout.preferredWidth: 0 visible: Layout.minimumWidth != 0 } } } states: [ State { name: 'playList' when: listViews.currentIndex === 0 PropertyChanges { target: mainContentView Layout.minimumWidth: 0 Layout.maximumWidth: 0 Layout.preferredWidth: 0 } PropertyChanges { target: firstViewSeparatorItem Layout.minimumWidth: 0 Layout.maximumWidth: 0 Layout.preferredWidth: 0 } PropertyChanges { target: viewSeparatorItem visible: true } PropertyChanges { target: albumContext Layout.minimumWidth: contentZone.width * 3 / 5 - 2 - 3.5 * elisaTheme.layoutHorizontalMargin Layout.maximumWidth: contentZone.width * 3 / 5 - 2 - 3.5 * elisaTheme.layoutHorizontalMargin Layout.preferredWidth: contentZone.width * 3 / 5 - 2 - 3.5 * elisaTheme.layoutHorizontalMargin } }, State { name: "browsingViewsNoPlaylist" when: listViews.currentIndex !== 0 && contentViewContainer.showPlaylist !== true extend: "browsingViews" PropertyChanges { target: mainContentView Layout.minimumWidth: contentZone.width Layout.maximumWidth: contentZone.width Layout.preferredWidth: contentZone.width } PropertyChanges { target: playList Layout.minimumWidth: 0 Layout.maximumWidth: 0 Layout.preferredWidth: 0 } }, State { name: 'browsingViews' when: listViews.currentIndex !== 0 PropertyChanges { target: mainContentView Layout.minimumWidth: contentZone.width * 0.66 Layout.maximumWidth: contentZone.width * 0.68 Layout.preferredWidth: contentZone.width * 0.68 } PropertyChanges { target: firstViewSeparatorItem Layout.minimumWidth: 1 Layout.maximumWidth: 1 Layout.preferredWidth: 1 } PropertyChanges { target: viewSeparatorItem visible: false } PropertyChanges { target: albumContext Layout.minimumWidth: 0 Layout.maximumWidth: 0 Layout.preferredWidth: 0 } } ] transitions: Transition { NumberAnimation { properties: "Layout.minimumWidth, Layout.maximumWidth, Layout.preferredWidth, opacity" easing.type: Easing.InOutQuad duration: 300 } } } - Component { - id: allFrequentlyPlayedTracksView - - FrequentlyPlayedTracks { - StackView.onActivated: viewManager.viewIsLoaded(viewType) - } - } - - Component { - id: allRecentlyPlayedTracksView - - RecentlyPlayedTracks { - StackView.onActivated: viewManager.viewIsLoaded(viewType) - } - } - Component { id: dataGridView DataGridView { StackView.onActivated: viewManager.viewIsLoaded(viewType) } } Component { - id: allTracksView - - TracksView { - StackView.onActivated: viewManager.viewIsLoaded(viewType) - } - } - - Component { - id: albumView + id: dataListView - AlbumView { + DataListView { StackView.onActivated: viewManager.viewIsLoaded(viewType) } } Component { id: filesBrowserView FileBrowserView { StackView.onActivated: viewManager.viewIsLoaded(viewType) } } } diff --git a/src/qml/DataGridView.qml b/src/qml/DataGridView.qml index f8cc7f8b..2b9714af 100644 --- a/src/qml/DataGridView.qml +++ b/src/qml/DataGridView.qml @@ -1,134 +1,109 @@ /* * Copyright 2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ import QtQuick 2.10 import QtQuick.Controls 2.3 import org.kde.kirigami 2.5 as Kirigami import org.kde.elisa 1.0 FocusScope { id: viewHeader property var viewType + property var filterType property alias mainTitle: gridView.mainTitle property alias secondaryTitle: gridView.secondaryTitle property alias image: gridView.image property var modelType property alias defaultIcon: gridView.defaultIcon property alias showRating: gridView.showRating property alias delegateDisplaySecondaryText: gridView.delegateDisplaySecondaryText property alias isSubPage: gridView.isSubPage property string genreFilterText property string artistFilter focus: true Accessible.role: Accessible.Pane Accessible.name: mainTitle + function initializeModel() + { + realModel.initialize(elisa.musicManager, elisa.musicManager.viewDatabase, + modelType, filterType, genreFilterText, artistFilter, 0) + } + DataModel { id: realModel } GridViewProxyModel { id: proxyModel sourceModel: realModel dataType: modelType onEntriesToEnqueue: elisa.mediaPlayList.enqueue(newEntries, databaseIdType, enqueueMode, triggerPlay) } GridBrowserView { id: gridView focus: true anchors.fill: parent contentModel: proxyModel onEnqueue: elisa.mediaPlayList.enqueue(databaseId, name, modelType, ElisaUtils.AppendPlayList, ElisaUtils.DoNotTriggerPlay) onReplaceAndPlay: elisa.mediaPlayList.enqueue(databaseId, name, modelType, ElisaUtils.ReplacePlayList, ElisaUtils.TriggerPlay) onOpen: viewManager.openChildView(innerMainTitle, innerSecondaryTitle, innerImage, databaseId, dataType) onGoBack: viewManager.goBack() Loader { anchors.centerIn: parent height: Kirigami.Units.gridUnit * 5 width: height visible: realModel.isBusy active: realModel.isBusy sourceComponent: BusyIndicator { anchors.centerIn: parent } } } Connections { target: elisa - onMusicManagerChanged: { - if (genreFilterText && artistFilter) { - realModel.initializeByGenreAndArtist(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType, genreFilterText, artistFilter) - } else if (genreFilterText) { - realModel.initializeByGenre(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType, genreFilterText) - } else if (artistFilter) { - realModel.initializeByArtist(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType, artistFilter) - } else { - realModel.initialize(elisa.musicManager, elisa.musicManager.viewDatabase, - modelType) - } - } + onMusicManagerChanged: initializeModel() } Component.onCompleted: { if (elisa.musicManager) { - if (genreFilterText && artistFilter) { - realModel.initializeByGenreAndArtist(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType, genreFilterText, artistFilter) - } else if (genreFilterText) { - realModel.initializeByGenre(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType, genreFilterText) - } else if (artistFilter) { - realModel.initializeByArtist(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType, artistFilter) - } else { - realModel.initialize(elisa.musicManager, elisa.musicManager.viewDatabase, - modelType) - } + initializeModel() } } } diff --git a/src/qml/TracksView.qml b/src/qml/DataListView.qml similarity index 57% rename from src/qml/TracksView.qml rename to src/qml/DataListView.qml index 9ee0077d..0ae35750 100644 --- a/src/qml/TracksView.qml +++ b/src/qml/DataListView.qml @@ -1,120 +1,188 @@ /* * Copyright 2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ import QtQuick 2.10 import QtQuick.Controls 2.3 import org.kde.kirigami 2.5 as Kirigami import org.kde.elisa 1.0 FocusScope { id: viewHeader property var viewType + property var filterType + property alias isSubPage: listView.isSubPage property alias mainTitle: listView.mainTitle + property alias secondaryTitle: listView.secondaryTitle + property int databaseId property alias image: listView.image property var modelType - - focus: true + property alias sortRole: proxyModel.sortRole + property bool sortAscending: true + property bool displaySingleAlbum: false DataModel { id: realModel } AllTracksProxyModel { id: proxyModel - sortRole: Qt.DisplayRole sourceModel: realModel onEntriesToEnqueue: elisa.mediaPlayList.enqueue(newEntries, databaseIdType, enqueueMode, triggerPlay) } - ListBrowserView { - id: listView + Component { + id: singleAlbumDelegate - focus: true + MediaAlbumTrackDelegate { + id: entry - anchors.fill: parent + width: listView.delegateWidth + height: ((true && !true) ? elisaTheme.delegateHeight*2 : elisaTheme.delegateHeight) + + focus: true + + databaseId: model.databaseId + title: model.title + artist: model.artist + album: (model.album !== undefined && model.album !== '' ? model.album : '') + albumArtist: model.albumArtist + duration: model.duration + imageUrl: (model.imageUrl !== undefined && model.imageUrl !== '' ? model.imageUrl : '') + trackNumber: model.trackNumber + discNumber: model.discNumber + rating: model.rating + isFirstTrackOfDisc: true + isSingleDiscAlbum: true + isSelected: listView.currentIndex === index + isAlternateColor: (index % 2) === 1 + + mediaTrack.onEnqueue: elisa.mediaPlayList.enqueue(databaseId, name, ElisaUtils.Track, + ElisaUtils.AppendPlayList, + ElisaUtils.DoNotTriggerPlay) + + mediaTrack.onReplaceAndPlay: elisa.mediaPlayList.enqueue(databaseId, name, ElisaUtils.Track, + ElisaUtils.ReplacePlayList, + ElisaUtils.TriggerPlay) - contentModel: proxyModel - delegate: MediaTrackDelegate { + mediaTrack.onClicked: listView.currentIndex = index + + onActiveFocusChanged: { + if (activeFocus && listView.currentIndex !== index) { + listView.currentIndex = index + } + } + } + } + + Component { + id: multipleDiscDelegate + + MediaTrackDelegate { id: entry width: listView.delegateWidth height: elisaTheme.trackDelegateHeight focus: true databaseId: model.databaseId title: model.title artist: model.artist album: (model.album !== undefined && model.album !== '' ? model.album : '') albumArtist: (model.albumArtist !== undefined && model.albumArtist !== '' ? model.albumArtist : '') duration: model.duration imageUrl: (model.imageUrl !== undefined && model.imageUrl !== '' ? model.imageUrl : '') trackNumber: model.trackNumber discNumber: model.discNumber rating: model.rating isFirstTrackOfDisc: false isSingleDiscAlbum: model.isSingleDiscAlbum isSelected: listView.currentIndex === index isAlternateColor: (index % 2) === 1 onEnqueue: elisa.mediaPlayList.enqueue(databaseId, name, modelType, ElisaUtils.AppendPlayList, ElisaUtils.DoNotTriggerPlay) onReplaceAndPlay: elisa.mediaPlayList.enqueue(databaseId, name, modelType, ElisaUtils.ReplacePlayList, ElisaUtils.TriggerPlay) onClicked: { listView.currentIndex = index entry.forceActiveFocus() } } + } + + ListBrowserView { + id: listView + + focus: true + + anchors.fill: parent + + contentModel: proxyModel + + delegate: (displaySingleAlbum ? singleAlbumDelegate : multipleDiscDelegate) + + allowArtistNavigation: isSubPage + + onShowArtist: { + viewManager.openChildView(secondaryTitle, '', elisaTheme.artistIcon, 0, ElisaUtils.Artist) + } + + onGoBack: viewManager.goBack() Loader { anchors.centerIn: parent height: Kirigami.Units.gridUnit * 5 width: height visible: realModel.isBusy active: realModel.isBusy sourceComponent: BusyIndicator { anchors.centerIn: parent } } } Connections { target: elisa onMusicManagerChanged: realModel.initialize(elisa.musicManager, elisa.musicManager.viewDatabase, modelType) } Component.onCompleted: { if (elisa.musicManager) { - realModel.initialize(elisa.musicManager, elisa.musicManager.viewDatabase, - modelType) + realModel.initialize(elisa.musicManager, elisa.musicManager.viewDatabase, modelType, filterType, mainTitle, secondaryTitle, databaseId) + } + + if (sortAscending) { + proxyModel.sortModel(Qt.AscendingOrder) + } else { + proxyModel.sortModel(Qt.DescendingOrder) } } } diff --git a/src/qml/FrequentlyPlayedTracks.qml b/src/qml/FrequentlyPlayedTracks.qml deleted file mode 100644 index bfc99ebb..00000000 --- a/src/qml/FrequentlyPlayedTracks.qml +++ /dev/null @@ -1,123 +0,0 @@ -/* - * Copyright 2018 Matthieu Gallien - * - * This program is free software: you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 3 of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this program. If not, see . - */ - -import QtQuick 2.10 -import QtQuick.Controls 2.3 -import org.kde.kirigami 2.5 as Kirigami -import org.kde.elisa 1.0 - -FocusScope { - id: viewHeader - - property var viewType - property alias mainTitle: listView.mainTitle - property alias image: listView.image - property var modelType - - focus: true - - DataModel { - id: realModel - } - - AllTracksProxyModel { - id: proxyModel - - sortRole: DatabaseInterface.PlayFrequency - sourceModel: realModel - - onEntriesToEnqueue: elisa.mediaPlayList.enqueue(newEntries, databaseIdType, enqueueMode, triggerPlay) - } - - ListBrowserView { - id: listView - - focus: true - - anchors.fill: parent - - contentModel: proxyModel - - delegate: MediaTrackDelegate { - id: entry - - width: listView.delegateWidth - height: elisaTheme.trackDelegateHeight - - focus: true - - databaseId: model.databaseId - title: model.title - artist: model.artist - album: (model.album !== undefined && model.album !== '' ? model.album : '') - albumArtist: (model.albumArtist !== undefined && model.albumArtist !== '' ? model.albumArtist : '') - duration: model.duration - imageUrl: (model.imageUrl !== undefined && model.imageUrl !== '' ? model.imageUrl : '') - trackNumber: model.trackNumber - discNumber: model.discNumber - rating: model.rating - isFirstTrackOfDisc: false - isSingleDiscAlbum: model.isSingleDiscAlbum - isSelected: listView.currentIndex === index - isAlternateColor: (index % 2) === 1 - - onEnqueue: elisa.mediaPlayList.enqueue(databaseId, name, modelType, - ElisaUtils.AppendPlayList, - ElisaUtils.DoNotTriggerPlay) - - onReplaceAndPlay: elisa.mediaPlayList.enqueue(databaseId, name, modelType, - ElisaUtils.ReplacePlayList, - ElisaUtils.TriggerPlay) - - onClicked: { - listView.currentIndex = index - entry.forceActiveFocus() - } - } - - Loader { - anchors.centerIn: parent - height: Kirigami.Units.gridUnit * 5 - width: height - - visible: realModel.isBusy - active: realModel.isBusy - - sourceComponent: BusyIndicator { - anchors.centerIn: parent - } - } - } - - Connections { - target: elisa - - onMusicManagerChanged: realModel.initializeFrequentlyPlayed(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType) - } - - Component.onCompleted: { - if (elisa.musicManager) { - realModel.initializeFrequentlyPlayed(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType) - } - - proxyModel.sortModel(Qt.DescendingOrder) - } -} diff --git a/src/qml/RecentlyPlayedTracks.qml b/src/qml/RecentlyPlayedTracks.qml deleted file mode 100644 index c7140471..00000000 --- a/src/qml/RecentlyPlayedTracks.qml +++ /dev/null @@ -1,123 +0,0 @@ -/* - * Copyright 2018 Matthieu Gallien - * - * This program is free software: you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 3 of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this program. If not, see . - */ - -import QtQuick 2.10 -import QtQuick.Controls 2.3 -import org.kde.kirigami 2.5 as Kirigami -import org.kde.elisa 1.0 - -FocusScope { - id: viewHeader - - property var viewType - property alias mainTitle: listView.mainTitle - property alias image: listView.image - property var modelType - - focus: true - - DataModel { - id: realModel - } - - AllTracksProxyModel { - id: proxyModel - - sortRole: DatabaseInterface.LastPlayDate - sourceModel: realModel - - onEntriesToEnqueue: elisa.mediaPlayList.enqueue(newEntries, databaseIdType, enqueueMode, triggerPlay) - } - - ListBrowserView { - id: listView - - focus: true - - anchors.fill: parent - - contentModel: proxyModel - - delegate: MediaTrackDelegate { - id: entry - - width: listView.delegateWidth - height: elisaTheme.trackDelegateHeight - - focus: true - - databaseId: model.databaseId - title: model.title - artist: model.artist - album: (model.album !== undefined && model.album !== '' ? model.album : '') - albumArtist: (model.albumArtist !== undefined && model.albumArtist !== '' ? model.albumArtist : '') - duration: model.duration - imageUrl: (model.imageUrl !== undefined && model.imageUrl !== '' ? model.imageUrl : '') - trackNumber: model.trackNumber - discNumber: model.discNumber - rating: model.rating - isFirstTrackOfDisc: false - isSingleDiscAlbum: model.isSingleDiscAlbum - isSelected: listView.currentIndex === index - isAlternateColor: (index % 2) === 1 - - onEnqueue: elisa.mediaPlayList.enqueue(databaseId, name, modelType, - ElisaUtils.AppendPlayList, - ElisaUtils.DoNotTriggerPlay) - - onReplaceAndPlay: elisa.mediaPlayList.enqueue(databaseId, name, modelType, - ElisaUtils.ReplacePlayList, - ElisaUtils.TriggerPlay) - - onClicked: { - listView.currentIndex = index - entry.forceActiveFocus() - } - } - - Loader { - anchors.centerIn: parent - height: Kirigami.Units.gridUnit * 5 - width: height - - visible: realModel.isBusy - active: realModel.isBusy - - sourceComponent: BusyIndicator { - anchors.centerIn: parent - } - } - } - - Connections { - target: elisa - - onMusicManagerChanged: realModel.initializeRecentlyPlayed(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType) - } - - Component.onCompleted: { - if (elisa.musicManager) { - realModel.initializeRecentlyPlayed(elisa.musicManager, - elisa.musicManager.viewDatabase, - modelType) - } - - proxyModel.sortModel(Qt.DescendingOrder) - } -} diff --git a/src/resources.qrc b/src/resources.qrc index c38dffbc..475c408b 100644 --- a/src/resources.qrc +++ b/src/resources.qrc @@ -1,64 +1,61 @@ qml/MediaPlayerControl.qml qml/RatingStar.qml qml/MediaPlayListView.qml qml/ElisaMainWindow.qml qml/ApplicationMenu.qml qml/HeaderBar.qml qml/ContextView.qml qml/ContentView.qml qml/DraggableItem.qml qml/PassiveNotification.qml qml/NavigationActionBar.qml qml/PlayListEntry.qml qml/Theme.qml qml/PlatformIntegration.qml qml/LabelWithToolTip.qml qml/TopNotification.qml qml/TrackImportNotification.qml qml/TopNotificationItem.qml qml/MediaTrackDelegate.qml qml/MediaAlbumTrackDelegate.qml qml/MediaTrackMetadataView.qml qml/GridBrowserView.qml qml/GridBrowserDelegate.qml qml/ListBrowserView.qml qml/FileBrowserDelegate.qml qml/FileBrowserView.qml qtquickcontrols2.conf background.png qml/BaseTheme.qml qml/ScrollHelper.qml qml/FlatButtonWithToolTip.qml qml/DataGridView.qml - qml/TracksView.qml - qml/AlbumView.qml - qml/RecentlyPlayedTracks.qml - qml/FrequentlyPlayedTracks.qml + qml/DataListView.qml qml/PlayListBasicView.qml qml/SimplePlayListView.qml qml/SimplePlayListEntry.qml qml/ViewSelector.qml qml/PlayListAlbumHeader.qml qml/BasicPlayListAlbumHeader.qml qml/MetaDataDelegate.qml qml/ContextViewLyrics.qml qml/ViewSelectorDelegate.qml qml/HeaderFooterToolbar.qml windows/WindowsTheme.qml windows/PlatformIntegration.qml windows/LabelWithToolTip.qml android/ElisaMainWindow.qml android/AndroidTheme.qml android/PlatformIntegration.qml android/AlbumsView.qml android/ArtistsView.qml android/TracksView.qml android/GenresView.qml diff --git a/src/viewmanager.cpp b/src/viewmanager.cpp index 0e4ea3af..434a9fa2 100644 --- a/src/viewmanager.cpp +++ b/src/viewmanager.cpp @@ -1,383 +1,396 @@ /* * Copyright 2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #include "viewmanager.h" +#include "databaseinterface.h" + ViewManager::ViewManager(QObject *parent) : QObject(parent) { } void ViewManager::closeAllViews() { mCurrentView = ViewsType::NoViews; mTargetView = ViewsType::NoViews; Q_EMIT switchOffAllViews(mTargetView); } void ViewManager::openParentView(ViewManager::ViewsType viewType, const QString &mainTitle, const QUrl &mainImage) { switch(viewType) { case NoViews: closeAllViews(); break; case RecentlyPlayedTracks: openRecentlyPlayedTracks(mainTitle, mainImage); break; case FrequentlyPlayedTracks: openFrequentlyPlayedTracks(mainTitle, mainImage); break; case AllAlbums: openAllAlbums(mainTitle, mainImage); break; case AllArtists: openAllArtists(mainTitle, mainImage); break; case AllTracks: openAllTracks(mainTitle, mainImage); break; case AllGenres: openAllGenres(mainTitle, mainImage); break; case FilesBrowser: openFilesBrowser(mainTitle, mainImage); break; case OneAlbum: case OneArtist: case OneAlbumFromArtist: case OneArtistFromGenre: case OneAlbumFromArtistAndGenre: case AllArtistsFromGenre: break; } } void ViewManager::openChildView(const QString &innerMainTitle, const QString &innerSecondaryTitle, const QUrl &innerImage, qulonglong databaseId, ElisaUtils::PlayListEntryType dataType) { switch(dataType) { case ElisaUtils::Album: openOneAlbum(innerMainTitle, innerSecondaryTitle, innerImage, databaseId); break; case ElisaUtils::Artist: openOneArtist(innerMainTitle, innerImage, databaseId); break; case ElisaUtils::Genre: openAllArtistsFromGenre(innerMainTitle); break; case ElisaUtils::Track: case ElisaUtils::FileName: case ElisaUtils::Lyricist: case ElisaUtils::Composer: case ElisaUtils::Unknown: break; } } void ViewManager::viewIsLoaded(ViewManager::ViewsType viewType) { switch (viewType) { case ViewsType::RecentlyPlayedTracks: recentlyPlayedTracksIsLoaded(); break; case ViewsType::FrequentlyPlayedTracks: frequentlyPlayedTracksIsLoaded(); break; case ViewsType::AllAlbums: allAlbumsViewIsLoaded(); break; case ViewsType::OneAlbum: oneAlbumViewIsLoaded(); break; case ViewsType::AllArtists: allArtistsViewIsLoaded(); break; case ViewsType::OneArtist: oneArtistViewIsLoaded(); break; case ViewsType::OneAlbumFromArtist: oneAlbumViewIsLoaded(); break; case ViewsType::AllTracks: allTracksViewIsLoaded(); break; case ViewsType::AllGenres: allGenresViewIsLoaded(); break; case ViewsType::AllArtistsFromGenre: allArtistsFromGenreViewIsLoaded(); break; case ViewsType::OneArtistFromGenre: oneArtistViewIsLoaded(); break; case ViewsType::OneAlbumFromArtistAndGenre: oneAlbumViewIsLoaded(); break; case ViewsType::FilesBrowser: filesBrowserViewIsLoaded(); break; case ViewsType::NoViews: break; } } void ViewManager::openRecentlyPlayedTracks(const QString &mainTitle, const QUrl &imageUrl) { mTargetView = ViewsType::RecentlyPlayedTracks; if (mCurrentView != mTargetView) { - Q_EMIT switchRecentlyPlayedTracksView(mTargetView, 1, mainTitle, imageUrl, ElisaUtils::Track); + Q_EMIT openListView(mTargetView, ElisaUtils::FilterByRecentlyPlayed, 1, mainTitle, {}, + 0, imageUrl, ElisaUtils::Track, DatabaseInterface::LastPlayDate, + SortOrder::SortDescending, MultipleAlbum); } } void ViewManager::openFrequentlyPlayedTracks(const QString &mainTitle, const QUrl &imageUrl) { mTargetView = ViewsType::FrequentlyPlayedTracks; if (mCurrentView != mTargetView) { - Q_EMIT switchFrequentlyPlayedTracksView(mTargetView, 1, mainTitle, imageUrl, ElisaUtils::Track); + Q_EMIT openListView(mTargetView, ElisaUtils::FilterByFrequentlyPlayed, 1, mainTitle, {}, + 0, imageUrl, ElisaUtils::Track, DatabaseInterface::PlayFrequency, SortOrder::SortDescending, MultipleAlbum); } } void ViewManager::openAllAlbums(const QString &mainTitle, const QUrl &imageUrl) { mTargetView = ViewsType::AllAlbums; if (mCurrentView != mTargetView) { - Q_EMIT openGridView(mTargetView, 1, mainTitle, {}, imageUrl, ElisaUtils::Album, + Q_EMIT openGridView(mTargetView, ElisaUtils::NoFilter, 1, mainTitle, {}, imageUrl, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), {}, {}, true, true); } } void ViewManager::openOneAlbum(const QString &albumTitle, const QString &albumAuthor, const QUrl &albumCover, qulonglong albumDatabaseId) { mTargetAlbumTitle = albumTitle; mTargetAlbumAuthor = albumAuthor; mTargetDatabaseId = albumDatabaseId; mTargetImageUrl = albumCover; if (mCurrentView == ViewsType::AllAlbums) { mTargetView = ViewsType::OneAlbum; - Q_EMIT switchOneAlbumView(mTargetView, 2, - mTargetAlbumTitle, mTargetImageUrl, mTargetAlbumAuthor, mTargetDatabaseId); + Q_EMIT openListView(mTargetView, ElisaUtils::FilterById, 2, mTargetAlbumTitle, mTargetAlbumAuthor, + mTargetDatabaseId, mTargetImageUrl, ElisaUtils::Track, Qt::DisplayRole, + SortOrder::SortAscending, SingleAlbum); } else if (mCurrentView == ViewsType::OneArtist && mCurrentArtistName == mTargetAlbumAuthor) { mTargetView = ViewsType::OneAlbumFromArtist; - Q_EMIT switchOneAlbumView(mTargetView, 3, - mTargetAlbumTitle, mTargetImageUrl, mTargetAlbumAuthor, mTargetDatabaseId); + Q_EMIT openListView(mTargetView, ElisaUtils::FilterById, 3, mTargetAlbumTitle, mTargetAlbumAuthor, + mTargetDatabaseId, mTargetImageUrl, ElisaUtils::Track, Qt::DisplayRole, + SortOrder::SortAscending, SingleAlbum); } else if (mCurrentView == ViewsType::OneArtist && mCurrentArtistName != mTargetAlbumAuthor) { mTargetView = ViewsType::OneAlbumFromArtist; Q_EMIT popOneView(); } else if (mCurrentView == ViewsType::OneArtistFromGenre) { mTargetView = ViewsType::OneAlbumFromArtistAndGenre; - Q_EMIT switchOneAlbumView(mTargetView, 4, - mTargetAlbumTitle, mTargetImageUrl, mTargetAlbumAuthor, mTargetDatabaseId); + Q_EMIT openListView(mTargetView, ElisaUtils::FilterById, 4, mTargetAlbumTitle, mTargetAlbumAuthor, + mTargetDatabaseId, mTargetImageUrl, ElisaUtils::Track, Qt::DisplayRole, + SortOrder::SortAscending, SingleAlbum); } else { mTargetView = ViewsType::OneAlbum; - Q_EMIT openGridView(ViewsType::AllAlbums, 1, {}, {}, {}, ElisaUtils::Album, + Q_EMIT openGridView(ViewsType::AllAlbums, ElisaUtils::NoFilter, 1, {}, {}, {}, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), {}, {}, true, true); } } void ViewManager::openAllArtists(const QString &mainTitle, const QUrl &imageUrl) { mTargetView = ViewsType::AllArtists; if (mCurrentView != mTargetView) { - Q_EMIT openGridView(ViewsType::AllArtists, 1, mainTitle, {}, imageUrl, ElisaUtils::Artist, + Q_EMIT openGridView(ViewsType::AllArtists, ElisaUtils::NoFilter, 1, mainTitle, {}, imageUrl, ElisaUtils::Artist, QUrl(QStringLiteral("image://icon/view-media-artist")), {}, {}, false, false); } } void ViewManager::openOneArtist(const QString &artistName, const QUrl &artistImageUrl, qulonglong artistDatabaseId) { mTargetArtistName = artistName; mTargetDatabaseId = artistDatabaseId; mTargetImageUrl = artistImageUrl; if (mCurrentView == ViewsType::AllArtistsFromGenre) { mTargetView = ViewsType::OneArtistFromGenre; } else { mTargetView = ViewsType::OneArtist; } if (mCurrentView == ViewsType::AllArtists && mTargetView == ViewsType::OneArtist) { - Q_EMIT openGridView(mTargetView, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, + Q_EMIT openGridView(mTargetView, ElisaUtils::FilterByArtist, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), {}, mTargetArtistName, true, true); } else if (mCurrentView == ViewsType::OneArtist && mCurrentArtistName != mTargetArtistName && mTargetView == ViewsType::OneArtist) { - Q_EMIT openGridView(mTargetView, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, + Q_EMIT openGridView(mTargetView, ElisaUtils::FilterByArtist, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), {}, mTargetArtistName, true, true); } else if (mCurrentView == ViewsType::OneAlbumFromArtist && mCurrentArtistName != mTargetArtistName && mTargetView == ViewsType::OneArtist) { - Q_EMIT openGridView(mTargetView, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, + Q_EMIT openGridView(mTargetView, ElisaUtils::FilterByArtist, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), {}, mTargetArtistName, true, true); } else if (mCurrentView == ViewsType::AllArtistsFromGenre && mTargetView == ViewsType::OneArtistFromGenre) { - Q_EMIT openGridView(mTargetView, 3, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, + Q_EMIT openGridView(mTargetView, ElisaUtils::FilterByGenreAndArtist, 3, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), mTargetGenreName, mTargetArtistName, true, true); } else { - Q_EMIT openGridView(ViewsType::AllArtists, 1, {}, {}, {}, ElisaUtils::Artist, + Q_EMIT openGridView(ViewsType::AllArtists, ElisaUtils::NoFilter, 1, {}, {}, {}, ElisaUtils::Artist, QUrl(QStringLiteral("image://icon/view-media-artist")), {}, {}, false, false); } } void ViewManager::openAllTracks(const QString &mainTitle, const QUrl &imageUrl) { mTargetView = ViewsType::AllTracks; if (mCurrentView != mTargetView) { - Q_EMIT switchAllTracksView(mTargetView, 1, mainTitle, imageUrl, ElisaUtils::Track); + Q_EMIT openListView(mTargetView, ElisaUtils::NoFilter, 1, mainTitle, {}, + 0, imageUrl, ElisaUtils::Track, Qt::DisplayRole, + SortOrder::SortAscending, MultipleAlbum); } } void ViewManager::openAllGenres(const QString &mainTitle, const QUrl &imageUrl) { mTargetView = ViewsType::AllGenres; if (mCurrentView != mTargetView) { - Q_EMIT openGridView(mTargetView, 1, mainTitle, {}, imageUrl, ElisaUtils::Genre, + Q_EMIT openGridView(mTargetView, ElisaUtils::NoFilter, 1, mainTitle, {}, imageUrl, ElisaUtils::Genre, QUrl(QStringLiteral("image://icon/view-media-genre")), {}, {}, false, false); } } void ViewManager::openAllArtistsFromGenre(const QString &genreName) { mTargetView = ViewsType::AllArtistsFromGenre; mTargetGenreName = genreName; if (mCurrentView == ViewsType::AllGenres) { - Q_EMIT openGridView(mTargetView, 2, mTargetGenreName, {}, QUrl(QStringLiteral("image://icon/view-media-artist")), + Q_EMIT openGridView(mTargetView, ElisaUtils::FilterByGenre, 2, mTargetGenreName, {}, QUrl(QStringLiteral("image://icon/view-media-artist")), ElisaUtils::Artist, QUrl(QStringLiteral("image://icon/view-media-artist")), mTargetGenreName, {}, false, false); } else { - Q_EMIT openGridView(ViewsType::AllGenres, 1, {}, {}, {}, ElisaUtils::Genre, + Q_EMIT openGridView(ViewsType::AllGenres, ElisaUtils::NoFilter, 1, {}, {}, {}, ElisaUtils::Genre, QUrl(QStringLiteral("image://icon/view-media-genre")), {}, {}, false, false); } } void ViewManager::openFilesBrowser(const QString &mainTitle, const QUrl &imageUrl) { mTargetView = ViewsType::FilesBrowser; if (mCurrentView != mTargetView) { Q_EMIT switchFilesBrowserView(mTargetView, 1, mainTitle, imageUrl); } } void ViewManager::recentlyPlayedTracksIsLoaded() { mCurrentView = ViewsType::RecentlyPlayedTracks; } void ViewManager::frequentlyPlayedTracksIsLoaded() { mCurrentView = ViewsType::FrequentlyPlayedTracks; } void ViewManager::allAlbumsViewIsLoaded() { mCurrentView = ViewsType::AllAlbums; if (mTargetView == ViewsType::OneAlbum) { - Q_EMIT switchOneAlbumView(mTargetView, 2, mTargetAlbumTitle, mTargetImageUrl, mTargetAlbumAuthor, mTargetDatabaseId); + Q_EMIT openListView(mTargetView, ElisaUtils::FilterById, 2, mTargetAlbumTitle, mTargetAlbumAuthor, + mTargetDatabaseId, mTargetImageUrl, ElisaUtils::Track, Qt::DisplayRole, + SortOrder::SortAscending, MultipleAlbum); } } void ViewManager::oneAlbumViewIsLoaded() { mCurrentAlbumTitle = mTargetAlbumTitle; mCurrentAlbumAuthor = mTargetAlbumAuthor; if (mTargetView == ViewsType::OneAlbum) { mCurrentView = ViewsType::OneAlbum; } else if (mTargetView == ViewsType::OneAlbumFromArtist) { mCurrentView = ViewsType::OneAlbumFromArtist; } else if (mTargetView == ViewsType::OneAlbumFromArtistAndGenre) { mCurrentView = ViewsType::OneAlbumFromArtistAndGenre; } } void ViewManager::allArtistsViewIsLoaded() { mCurrentView = ViewsType::AllArtists; if (mTargetView == ViewsType::OneArtist) { - Q_EMIT openGridView(mTargetView, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, + Q_EMIT openGridView(mTargetView, ElisaUtils::FilterByArtist, 2, mTargetArtistName, {}, mTargetImageUrl, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), {}, mTargetArtistName, true, true); } else if (mTargetView == ViewsType::OneAlbumFromArtist) { - Q_EMIT openGridView(ViewsType::OneArtist, 2, mTargetAlbumAuthor, {}, mTargetImageUrl, ElisaUtils::Album, + Q_EMIT openGridView(ViewsType::OneArtist, ElisaUtils::FilterByArtist, 2, mTargetAlbumAuthor, {}, mTargetImageUrl, ElisaUtils::Album, QUrl(QStringLiteral("image://icon/media-optical-audio")), {}, mTargetAlbumAuthor, true, true); } } void ViewManager::oneArtistViewIsLoaded() { mCurrentArtistName = mTargetArtistName; if (mTargetView == ViewsType::OneArtist) { mCurrentView = ViewsType::OneArtist; } else if (mTargetView == ViewsType::OneArtistFromGenre) { mCurrentGenreName = mTargetGenreName; mCurrentView = ViewsType::OneArtistFromGenre; } else if (mTargetView == ViewsType::OneAlbumFromArtist) { mCurrentView = ViewsType::OneArtist; - Q_EMIT switchOneAlbumView(mTargetView, 3, - mTargetAlbumTitle, mTargetImageUrl, mTargetAlbumAuthor, mTargetDatabaseId); + Q_EMIT openListView(mTargetView, ElisaUtils::FilterById, 3, mTargetAlbumTitle, mTargetAlbumAuthor, + mTargetDatabaseId, mTargetImageUrl, ElisaUtils::Track, Qt::DisplayRole, + SortOrder::SortAscending, MultipleAlbum); } } void ViewManager::allTracksViewIsLoaded() { mCurrentView = ViewsType::AllTracks; } void ViewManager::allGenresViewIsLoaded() { mCurrentView = ViewsType::AllGenres; } void ViewManager::allArtistsFromGenreViewIsLoaded() { mCurrentGenreName = mTargetGenreName; mCurrentView = ViewsType::AllArtistsFromGenre; } void ViewManager::filesBrowserViewIsLoaded() { mCurrentView = ViewsType::FilesBrowser; } void ViewManager::goBack() { Q_EMIT popOneView(); if (mCurrentView == ViewsType::OneAlbum) { mCurrentView = ViewsType::AllAlbums; } else if (mCurrentView == ViewsType::OneArtist) { mCurrentView = ViewsType::AllArtists; } else if (mCurrentView == ViewsType::OneAlbumFromArtist) { mCurrentView = ViewsType::OneArtist; } else if (mCurrentView == ViewsType::AllArtistsFromGenre) { mCurrentView = ViewsType::AllGenres; } else if (mCurrentView == ViewsType::OneArtistFromGenre) { mCurrentView = ViewsType::AllArtistsFromGenre; } else if (mCurrentView == ViewsType::OneAlbumFromArtistAndGenre) { mCurrentView = ViewsType::OneArtistFromGenre; } mTargetView = mCurrentView; } #include "moc_viewmanager.cpp" diff --git a/src/viewmanager.h b/src/viewmanager.h index 67ed63c0..dfc21d24 100644 --- a/src/viewmanager.h +++ b/src/viewmanager.h @@ -1,156 +1,157 @@ /* * Copyright 2018 Matthieu Gallien * * This program is free software: you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see . */ #ifndef VIEWMANAGER_H #define VIEWMANAGER_H #include "elisaLib_export.h" #include "elisautils.h" #include #include class ELISALIB_EXPORT ViewManager : public QObject { Q_OBJECT public: enum ViewsType { NoViews, AllAlbums, OneAlbum, AllArtists, OneArtist, OneAlbumFromArtist, AllTracks, AllGenres, AllArtistsFromGenre, OneArtistFromGenre, OneAlbumFromArtistAndGenre, FrequentlyPlayedTracks, RecentlyPlayedTracks, FilesBrowser }; Q_ENUM(ViewsType) + enum SortOrder { + SortAscending = true, + SortDescending = false, + }; + + Q_ENUM(SortOrder) + + static const bool SingleAlbum = true; + static const bool MultipleAlbum = false; + explicit ViewManager(QObject *parent = nullptr); Q_SIGNALS: - void openGridView(ViewManager::ViewsType viewType, int expectedDepth, + void openGridView(ViewManager::ViewsType viewType, ElisaUtils::FilterType filterType, int expectedDepth, const QString &mainTitle, const QString &secondaryTitle, const QUrl &imageUrl, ElisaUtils::PlayListEntryType dataType, const QUrl &viewDefaultIcon, const QString &genreNameFilter, const QString &artistNameFilter, bool viewShowRating, bool viewDelegateDisplaySecondaryText); - void switchRecentlyPlayedTracksView(ViewManager::ViewsType viewType, int expectedDepth, - const QString &mainTitle, const QUrl &imageUrl, - ElisaUtils::PlayListEntryType dataType); - - void switchFrequentlyPlayedTracksView(ViewManager::ViewsType viewType, int expectedDepth, - const QString &mainTitle, const QUrl &imageUrl, - ElisaUtils::PlayListEntryType dataType); - - void switchOneAlbumView(ViewManager::ViewsType viewType, int expectedDepth, - const QString &mainTitle, const QUrl &imageUrl, const QString &secondaryTitle, qulonglong databaseId); - - void switchAllTracksView(ViewManager::ViewsType viewType, int expectedDepth, const QString &mainTitle, - const QUrl &imageUrl, ElisaUtils::PlayListEntryType dataType); + void openListView(ViewManager::ViewsType viewType, ElisaUtils::FilterType filterType, int expectedDepth, + const QString &mainTitle, const QString &secondaryTitle, qulonglong databaseId, + const QUrl &imageUrl, ElisaUtils::PlayListEntryType dataType, int sortRole, + ViewManager::SortOrder sortOrder, bool displaySingleAlbum); void switchFilesBrowserView(ViewManager::ViewsType viewType, int expectedDepth, const QString &mainTitle, const QUrl &imageUrl); void switchOffAllViews(ViewManager::ViewsType viewType); void popOneView(); public Q_SLOTS: void closeAllViews(); void openParentView(ViewManager::ViewsType viewType, const QString &mainTitle, const QUrl &mainImage); void openChildView(const QString &innerMainTitle, const QString & innerSecondaryTitle, const QUrl &innerImage, qulonglong databaseId, ElisaUtils::PlayListEntryType dataType); void viewIsLoaded(ViewManager::ViewsType viewType); void goBack(); private: void openRecentlyPlayedTracks(const QString &mainTitle, const QUrl &imageUrl); void openFrequentlyPlayedTracks(const QString &mainTitle, const QUrl &imageUrl); void openAllAlbums(const QString &mainTitle, const QUrl &imageUrl); void openAllArtists(const QString &mainTitle, const QUrl &imageUrl); void openAllTracks(const QString &mainTitle, const QUrl &imageUrl); void openAllGenres(const QString &mainTitle, const QUrl &imageUrl); void openFilesBrowser(const QString &mainTitle, const QUrl &imageUrl); void openOneAlbum(const QString &albumTitle, const QString &albumAuthor, const QUrl &albumCover, qulonglong albumDatabaseId); void openOneArtist(const QString &artistName, const QUrl &artistImageUrl, qulonglong artistDatabaseId); void openAllArtistsFromGenre(const QString &genreName); void recentlyPlayedTracksIsLoaded(); void frequentlyPlayedTracksIsLoaded(); void allAlbumsViewIsLoaded(); void oneAlbumViewIsLoaded(); void allArtistsViewIsLoaded(); void oneArtistViewIsLoaded(); void allTracksViewIsLoaded(); void allGenresViewIsLoaded(); void allArtistsFromGenreViewIsLoaded(); void filesBrowserViewIsLoaded(); ViewsType mCurrentView = ViewsType::NoViews; QString mCurrentAlbumTitle; QString mCurrentAlbumAuthor; QString mCurrentArtistName; QString mCurrentGenreName; ViewsType mTargetView = ViewsType::NoViews; QString mTargetAlbumTitle; QString mTargetAlbumAuthor; QString mTargetArtistName; QString mTargetGenreName; QUrl mTargetImageUrl; qulonglong mTargetDatabaseId = 0; }; #endif // VIEWMANAGER_H