mirror of
https://github.com/QuasarApp/SoundBand.git
synced 2025-04-27 07:44:31 +00:00
Merge pull request #62 from QuasarApp/default_qtPlayList
create song storage class
This commit is contained in:
commit
03bbae91fa
@ -10,7 +10,7 @@ Item {
|
|||||||
|
|
||||||
property int currentSongId: 0
|
property int currentSongId: 0
|
||||||
property string currentSongName: qsTr("Song is not selected")
|
property string currentSongName: qsTr("Song is not selected")
|
||||||
property bool playState: false
|
property bool playState: syncEngine.playState === 1;
|
||||||
|
|
||||||
|
|
||||||
function changeSong(id, name){
|
function changeSong(id, name){
|
||||||
@ -84,7 +84,6 @@ Item {
|
|||||||
|
|
||||||
onClicked: {
|
onClicked: {
|
||||||
syncEngine.pause(playState);
|
syncEngine.pause(playState);
|
||||||
playState = !playState;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -123,7 +122,7 @@ Item {
|
|||||||
anchors.right: parent.right;
|
anchors.right: parent.right;
|
||||||
anchors.rightMargin: Utils.dp(Screen.pixelDensity, 5)
|
anchors.rightMargin: Utils.dp(Screen.pixelDensity, 5)
|
||||||
onClicked: {
|
onClicked: {
|
||||||
state = ++state % 4;
|
state = ++state % 5;
|
||||||
syncEngine.setRepeat(state)
|
syncEngine.setRepeat(state)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -33,7 +33,8 @@ SOURCES += main.cpp \
|
|||||||
playlistmodel.cpp \
|
playlistmodel.cpp \
|
||||||
serverlistmodel.cpp \
|
serverlistmodel.cpp \
|
||||||
playlistsmodel.cpp \
|
playlistsmodel.cpp \
|
||||||
currentplaylistmodel.cpp
|
currentplaylistmodel.cpp \
|
||||||
|
../sync/playlist.cpp
|
||||||
|
|
||||||
|
|
||||||
RESOURCES += qml.qrc
|
RESOURCES += qml.qrc
|
||||||
@ -69,5 +70,6 @@ HEADERS += \
|
|||||||
playlistmodel.h \
|
playlistmodel.h \
|
||||||
serverlistmodel.h \
|
serverlistmodel.h \
|
||||||
playlistsmodel.h \
|
playlistsmodel.h \
|
||||||
currentplaylistmodel.h
|
currentplaylistmodel.h \
|
||||||
|
../sync/playlist.h
|
||||||
|
|
||||||
|
@ -17,7 +17,7 @@ class CurrentPlayListModel : public QAbstractListModel
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
SyncEngine * syncEngine;
|
SyncEngine * syncEngine;
|
||||||
const QList<syncLib::SongHeader> *playList;
|
const QList<syncLib::SongStorage> *playList;
|
||||||
int itemCount;
|
int itemCount;
|
||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
|
@ -94,7 +94,7 @@ QVariant PlayListModel::data(const QModelIndex &index, int role) const
|
|||||||
|
|
||||||
bool PlayListModel::select(int id){
|
bool PlayListModel::select(int id){
|
||||||
|
|
||||||
for(QList<syncLib::SongHeader>::Iterator i = playList.begin(); i < playList.end(); i++){
|
for(QList<syncLib::SongStorage>::Iterator i = playList.begin(); i < playList.end(); i++){
|
||||||
if(i->id == id){
|
if(i->id == id){
|
||||||
|
|
||||||
if((i->isSelected = !i->isSelected)){
|
if((i->isSelected = !i->isSelected)){
|
||||||
@ -114,7 +114,7 @@ bool PlayListModel::select(int id){
|
|||||||
QList<int> PlayListModel::getSelected(){
|
QList<int> PlayListModel::getSelected(){
|
||||||
QList<int> result;
|
QList<int> result;
|
||||||
|
|
||||||
for(QList<syncLib::SongHeader>::Iterator i = playList.begin(); i < playList.end(); i++){
|
for(QList<syncLib::SongStorage>::Iterator i = playList.begin(); i < playList.end(); i++){
|
||||||
if(i->isSelected){
|
if(i->isSelected){
|
||||||
result.push_back(i->id);
|
result.push_back(i->id);
|
||||||
}
|
}
|
||||||
@ -124,7 +124,7 @@ QList<int> PlayListModel::getSelected(){
|
|||||||
|
|
||||||
bool PlayListModel::isSelected(int id){
|
bool PlayListModel::isSelected(int id){
|
||||||
|
|
||||||
for(QList<syncLib::SongHeader>::Iterator i = playList.begin(); i < playList.end(); i++){
|
for(QList<syncLib::SongStorage>::Iterator i = playList.begin(); i < playList.end(); i++){
|
||||||
if(i->id == id){
|
if(i->id == id){
|
||||||
return i->isSelected;
|
return i->isSelected;
|
||||||
}
|
}
|
||||||
|
@ -16,7 +16,7 @@ class PlayListModel : public QAbstractListModel
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
SyncEngine * syncEngine;
|
SyncEngine * syncEngine;
|
||||||
QList<syncLib::SongHeader> playList;
|
QList<syncLib::SongStorage> playList;
|
||||||
QString playListName;
|
QString playListName;
|
||||||
int itemCount;
|
int itemCount;
|
||||||
|
|
||||||
|
@ -8,9 +8,11 @@ SyncEngine::SyncEngine()
|
|||||||
sqlApi = sync->getSqlApi();
|
sqlApi = sync->getSqlApi();
|
||||||
|
|
||||||
connect(sync, SIGNAL(networkStateChange()), this, SIGNAL(serversCountChanged()));
|
connect(sync, SIGNAL(networkStateChange()), this, SIGNAL(serversCountChanged()));
|
||||||
|
connect(sync, SIGNAL(currentPlayListChanged()), this, SIGNAL(currentPlayListNameChanged()));
|
||||||
connect(sync, SIGNAL(currentPlayListChanged()), this, SIGNAL(currentPlayListCountChanged()));
|
connect(sync, SIGNAL(currentPlayListChanged()), this, SIGNAL(currentPlayListCountChanged()));
|
||||||
connect(sync, SIGNAL(seekChanged(qint64)), this, SLOT(seekChanged(qint64)));
|
connect(sync, SIGNAL(seekChanged(qint64)), this, SLOT(seekChanged(qint64)));
|
||||||
connect(sync, SIGNAL(currentSongChanged()), this, SIGNAL(currentSongChanged()));
|
connect(sync, SIGNAL(currentSongChanged()), this, SIGNAL(currentSongChanged()));
|
||||||
|
connect(sync, SIGNAL(playStateChanged()), this, SIGNAL(playStateChanged()));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -42,7 +44,7 @@ bool SyncEngine::init(){
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
const QList<syncLib::SongHeader>* SyncEngine::currentPlayList() const{
|
const QList<syncLib::SongStorage>* SyncEngine::currentPlayList() const{
|
||||||
|
|
||||||
return sync->getPlayList();
|
return sync->getPlayList();
|
||||||
}
|
}
|
||||||
@ -140,7 +142,7 @@ int SyncEngine::repeat()const{
|
|||||||
}
|
}
|
||||||
|
|
||||||
void SyncEngine::setRepeat(int flag){
|
void SyncEngine::setRepeat(int flag){
|
||||||
sync->setRepeat((syncLib::Repeat)flag);
|
sync->setRepeat((QMediaPlaylist::PlaybackMode)flag);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool SyncEngine::setPlayList(const QString& name){
|
bool SyncEngine::setPlayList(const QString& name){
|
||||||
@ -157,7 +159,7 @@ bool SyncEngine::setPlayList(const QString& name){
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool SyncEngine::getPlayList(QList<syncLib::SongHeader> &playList, const QString &name){
|
bool SyncEngine::getPlayList(QList<SongStorage> &playList, const QString &name){
|
||||||
return sqlApi->updateAvailableSongs(playList, name, true);
|
return sqlApi->updateAvailableSongs(playList, name, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -251,6 +253,10 @@ bool SyncEngine::removeFromPlayList(int id, const QString &playList){
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int SyncEngine::playState()const{
|
||||||
|
return sync->playState();
|
||||||
|
}
|
||||||
|
|
||||||
SyncEngine::~SyncEngine(){
|
SyncEngine::~SyncEngine(){
|
||||||
disconnect(sync, SIGNAL(networkStateChange()), this, SIGNAL(serversCountChanged()));
|
disconnect(sync, SIGNAL(networkStateChange()), this, SIGNAL(serversCountChanged()));
|
||||||
delete sync;
|
delete sync;
|
||||||
|
@ -16,6 +16,7 @@ class SyncEngine : public QObject
|
|||||||
Q_PROPERTY(double pos READ pos WRITE setPos NOTIFY posChanged)
|
Q_PROPERTY(double pos READ pos WRITE setPos NOTIFY posChanged)
|
||||||
Q_PROPERTY(int repeat READ repeat WRITE setRepeat NOTIFY repeatChanged)
|
Q_PROPERTY(int repeat READ repeat WRITE setRepeat NOTIFY repeatChanged)
|
||||||
Q_PROPERTY(QString currentPlayListName READ currentPlayListName NOTIFY currentPlayListNameChanged)
|
Q_PROPERTY(QString currentPlayListName READ currentPlayListName NOTIFY currentPlayListNameChanged)
|
||||||
|
Q_PROPERTY(int playState READ playState NOTIFY playStateChanged)
|
||||||
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
@ -74,7 +75,7 @@ public slots:
|
|||||||
* @brief currentPlayList
|
* @brief currentPlayList
|
||||||
* @return return current Play List
|
* @return return current Play List
|
||||||
*/
|
*/
|
||||||
const QList<syncLib::SongHeader> *currentPlayList() const;
|
const QList<SongStorage> *currentPlayList() const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief currentPlayListName
|
* @brief currentPlayListName
|
||||||
@ -138,7 +139,7 @@ public slots:
|
|||||||
* @param name - name of selected playList
|
* @param name - name of selected playList
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
bool getPlayList(QList<syncLib::SongHeader> &playList, const QString& name);
|
bool getPlayList(QList<SongStorage> &playList, const QString& name);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief lastError - message of last error
|
* @brief lastError - message of last error
|
||||||
@ -222,6 +223,17 @@ public slots:
|
|||||||
*/
|
*/
|
||||||
bool removeFromPlayList(int id, const QString& playList);
|
bool removeFromPlayList(int id, const QString& playList);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief playState
|
||||||
|
* @return playState current song ( )
|
||||||
|
* @value 0 is no repeat
|
||||||
|
* @value 1 is single repeat
|
||||||
|
* @value 2 is single playlist
|
||||||
|
* @value 3 is repeat playlist
|
||||||
|
* @value 4 is random play
|
||||||
|
*/
|
||||||
|
int playState()const;
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -278,6 +290,12 @@ signals:
|
|||||||
*/
|
*/
|
||||||
void currentPlayListNameChanged();
|
void currentPlayListNameChanged();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief playStateChanged
|
||||||
|
* emited when state of playing song changed
|
||||||
|
*/
|
||||||
|
void playStateChanged();
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // SYNCENGINE_H
|
#endif // SYNCENGINE_H
|
||||||
|
@ -3,6 +3,9 @@
|
|||||||
|
|
||||||
// general otions
|
// general otions
|
||||||
#define CURRENT_PLAYLIST_KEY "currentPlayList"
|
#define CURRENT_PLAYLIST_KEY "currentPlayList"
|
||||||
|
#define MAIN_FOLDER_KEY "songsfolder"
|
||||||
|
#define MAIN_FOLDER "soundBand"
|
||||||
|
|
||||||
|
|
||||||
// LIB VERSION
|
// LIB VERSION
|
||||||
#define MAJOR_VERSION 0
|
#define MAJOR_VERSION 0
|
||||||
|
177
sync/mysql.cpp
177
sync/mysql.cpp
@ -2,6 +2,8 @@
|
|||||||
#include <QSqlQuery>
|
#include <QSqlQuery>
|
||||||
#include <QtSql>
|
#include <QtSql>
|
||||||
#include "exaptions.h"
|
#include "exaptions.h"
|
||||||
|
#include <QSettings>
|
||||||
|
#include "playlist.h"
|
||||||
|
|
||||||
namespace syncLib{
|
namespace syncLib{
|
||||||
|
|
||||||
@ -44,6 +46,8 @@ bool MySql::exec(QSqlQuery *sq,const QString& sqlFile){
|
|||||||
void MySql::initDB(const QString &database){
|
void MySql::initDB(const QString &database){
|
||||||
if(db) return;
|
if(db) return;
|
||||||
dataBaseName = database;
|
dataBaseName = database;
|
||||||
|
QSettings settings;
|
||||||
|
songDir = settings.value(MAIN_FOLDER_KEY, QDir::homePath() + "/soundBand").toString();
|
||||||
db = new QSqlDatabase();
|
db = new QSqlDatabase();
|
||||||
*db = QSqlDatabase::addDatabase("QSQLITE", database);
|
*db = QSqlDatabase::addDatabase("QSQLITE", database);
|
||||||
QDir d(QString("./%0").arg(dataBaseName));
|
QDir d(QString("./%0").arg(dataBaseName));
|
||||||
@ -51,23 +55,11 @@ void MySql::initDB(const QString &database){
|
|||||||
if(db->open()){
|
if(db->open()){
|
||||||
qyery = new QSqlQuery(*db);
|
qyery = new QSqlQuery(*db);
|
||||||
|
|
||||||
// /*
|
|
||||||
// *https://stackoverflow.com/questions/40863216/sqlite-why-is-foreign-key-constraint-not-working-here
|
|
||||||
// */
|
|
||||||
|
|
||||||
// QString qyer = QString("PRAGMA foreign_keys = ON");
|
|
||||||
// if(!qyery->exec(qyer)){
|
|
||||||
// sqlErrorLog(qyer);
|
|
||||||
// throw InitDBError();
|
|
||||||
// delete db;
|
|
||||||
// return;
|
|
||||||
// }
|
|
||||||
|
|
||||||
QString qyer = QString("CREATE TABLE IF NOT EXISTS songs("
|
QString qyer = QString("CREATE TABLE IF NOT EXISTS songs("
|
||||||
"id INTEGER PRIMARY KEY AUTOINCREMENT, "
|
"id INTEGER PRIMARY KEY AUTOINCREMENT, "
|
||||||
"name VARCHAR(100), "
|
"name VARCHAR(100), "
|
||||||
"size INT NOT NULL, "
|
"size INT NOT NULL, "
|
||||||
"data BLOB NOT NULL "
|
"data TEXT NOT NULL "
|
||||||
")");
|
")");
|
||||||
if(!qyery->exec(qyer)){
|
if(!qyery->exec(qyer)){
|
||||||
sqlErrorLog(qyer);
|
sqlErrorLog(qyer);
|
||||||
@ -127,15 +119,95 @@ void MySql::initDB(const QString &database){
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool MySql::find(const QMediaContent &song, SongStorage &response){
|
||||||
|
QList<SongStorage> songs;
|
||||||
|
|
||||||
|
if(!updateAvailableSongs(songs)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
for(SongStorage &i: songs){
|
||||||
|
if(i == song){
|
||||||
|
response = i;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
bool MySql::find(const QMediaContent &song, SongHeader &response){
|
||||||
|
QList<SongStorage> songs;
|
||||||
|
|
||||||
|
if(!updateAvailableSongs(songs)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
for(SongStorage &i: songs){
|
||||||
|
if(i == song){
|
||||||
|
response = (SongHeader&)i;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
bool MySql::find(const SongHeader &song, QMediaContent &response){
|
||||||
|
QList<SongStorage> songs;
|
||||||
|
|
||||||
|
if(!updateAvailableSongs(songs)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
for(SongStorage &i: songs){
|
||||||
|
if((SongHeader&)i == song){
|
||||||
|
response = i.toMedia();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void MySql::setSoundDir(const QString &str){
|
||||||
|
songDir = str;
|
||||||
|
QSettings().setValue(MAIN_FOLDER_KEY, songDir);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool MySql::saveToStorage(QUrl &url, const Song &song) const{
|
||||||
|
if(!song.isValid()){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
QFile file(songDir + "/" + song.name);
|
||||||
|
|
||||||
|
if(!file.open(QIODevice::WriteOnly | QIODevice::Truncate)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
file.write(song.source.data(), song.source.length());
|
||||||
|
file.close();
|
||||||
|
|
||||||
|
url = QUrl::fromLocalFile(songDir + "/" + song.name);
|
||||||
|
|
||||||
|
return url.isValid();
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
void MySql::sqlErrorLog(const QString &qyery)const{
|
void MySql::sqlErrorLog(const QString &qyery)const{
|
||||||
#ifdef QT_DEBUG
|
#ifdef QT_DEBUG
|
||||||
qDebug()<< qyery << ": fail:\n " <<this->qyery->lastError();
|
qDebug()<< qyery << ": fail:\n " <<this->qyery->lastError();
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
int MySql::save(const Song &song){
|
int MySql::save(const SongStorage &song){
|
||||||
QString qyer = QString("SELECT id from songs where name='%0' and size=%1").arg(song.name,
|
|
||||||
QString::number(song.size));
|
QString qyer = QString("SELECT id from songs where name='%0' and size=%1").
|
||||||
|
arg(song.name, QString::number(song.size));
|
||||||
|
|
||||||
if(!qyery->exec(qyer)){
|
if(!qyery->exec(qyer)){
|
||||||
sqlErrorLog(qyer);
|
sqlErrorLog(qyer);
|
||||||
return -1;
|
return -1;
|
||||||
@ -146,15 +218,11 @@ int MySql::save(const Song &song){
|
|||||||
}
|
}
|
||||||
|
|
||||||
qyer = QString("INSERT INTO songs (name,size,data) VALUES "
|
qyer = QString("INSERT INTO songs (name,size,data) VALUES "
|
||||||
"('%0',%1,:val)").arg(song.name,
|
"('%0',%1,'%2')").arg(song.name,
|
||||||
QString::number(song.size));
|
QString::number(song.size),
|
||||||
if(!qyery->prepare(qyer)){
|
song.url.path());
|
||||||
sqlErrorLog(qyer + " prepare error");
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
qyery->bindValue(":val",song.source);
|
if(!qyery->exec(qyer)){
|
||||||
if(!qyery->exec()){
|
|
||||||
sqlErrorLog(qyer);
|
sqlErrorLog(qyer);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@ -169,18 +237,28 @@ int MySql::save(const Song &song){
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int MySql::save(const Song &song){
|
||||||
|
|
||||||
|
|
||||||
|
QUrl url;
|
||||||
|
if(!saveToStorage(url, song)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return save(SongStorage(url));
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
int MySql::save(const QString &url){
|
int MySql::save(const QString &url){
|
||||||
QFile f(QUrl(url).toLocalFile());
|
|
||||||
if(!f.open(QIODevice::ReadOnly)){
|
QUrl qurl = QUrl(url);
|
||||||
|
|
||||||
|
if(!qurl.isValid()){
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
QByteArray bytes = f.readAll();
|
|
||||||
f.close();
|
SongStorage song(qurl);
|
||||||
QString name = url.right(url.lastIndexOf(QRegularExpression("[\\/]"))); // meby [[\\\/]]
|
|
||||||
Song song;
|
|
||||||
song.name = name;
|
|
||||||
song.size = bytes.size();
|
|
||||||
song.source = bytes;
|
|
||||||
|
|
||||||
if(!song.isNameValid()){
|
if(!song.isNameValid()){
|
||||||
return -1;
|
return -1;
|
||||||
@ -190,8 +268,7 @@ int MySql::save(const QString &url){
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool MySql::load(const SongHeader &song,Song &result){
|
bool MySql::load(const SongHeader &song, SongStorage &result){
|
||||||
result.clear();
|
|
||||||
if(song.id > -1){
|
if(song.id > -1){
|
||||||
QString qyer = QString("SELECT * from songs where id=%0").arg(song.id);
|
QString qyer = QString("SELECT * from songs where id=%0").arg(song.id);
|
||||||
if(!qyery->exec(qyer)){
|
if(!qyery->exec(qyer)){
|
||||||
@ -213,17 +290,17 @@ bool MySql::load(const SongHeader &song,Song &result){
|
|||||||
result.id = qyery->value(0).toInt();
|
result.id = qyery->value(0).toInt();
|
||||||
result.name = qyery->value(1).toString();
|
result.name = qyery->value(1).toString();
|
||||||
result.size = qyery->value(2).toInt();
|
result.size = qyery->value(2).toInt();
|
||||||
result.source = qyery->value(3).toByteArray();
|
result.url = QUrl::fromLocalFile(qyery->value(3).toString());
|
||||||
return true;
|
return result.isValid();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool MySql::updateAvailableSongs(QList<SongHeader>& list, const QString& playList, bool forEditing){
|
bool MySql::updateAvailableSongs(QList<SongStorage>& list, const QString& playList, bool forEditing){
|
||||||
QString qyer;
|
QString qyer;
|
||||||
|
|
||||||
if(playList.isEmpty() || playList == ALL_SONGS_LIST || forEditing){
|
if(playList.isEmpty() || playList == ALL_SONGS_LIST || forEditing){
|
||||||
qyer = QString("SELECT id,name,size from songs");
|
qyer = QString("SELECT * from songs");
|
||||||
}else{
|
}else{
|
||||||
qyer = QString("SELECT id,name,size from songs where "
|
qyer = QString("SELECT * from songs where "
|
||||||
"id in (select song from playlistsdata where "
|
"id in (select song from playlistsdata where "
|
||||||
"playlist='%0')").arg(playList);
|
"playlist='%0')").arg(playList);
|
||||||
}
|
}
|
||||||
@ -236,11 +313,13 @@ bool MySql::updateAvailableSongs(QList<SongHeader>& list, const QString& playLis
|
|||||||
list.clear();
|
list.clear();
|
||||||
|
|
||||||
while(qyery->next()){
|
while(qyery->next()){
|
||||||
SongHeader song;
|
SongStorage song;
|
||||||
song.isSelected = !forEditing || playList == ALL_SONGS_LIST;
|
song.isSelected = !forEditing || playList == ALL_SONGS_LIST;
|
||||||
song.id = qyery->value(0).toInt();
|
song.id = qyery->value(0).toInt();
|
||||||
song.name = qyery->value(1).toString();
|
song.name = qyery->value(1).toString();
|
||||||
song.size = qyery->value(2).toInt();
|
song.size = qyery->value(2).toInt();
|
||||||
|
song.url = QUrl::fromLocalFile(qyery->value(3).toString());
|
||||||
|
|
||||||
list.push_back(song);
|
list.push_back(song);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -255,7 +334,7 @@ bool MySql::updateAvailableSongs(QList<SongHeader>& list, const QString& playLis
|
|||||||
}
|
}
|
||||||
|
|
||||||
while(qyery->next()){
|
while(qyery->next()){
|
||||||
for(SongHeader& item:list){
|
for(SongStorage& item:list){
|
||||||
int id = qyery->value(0).toInt();
|
int id = qyery->value(0).toInt();
|
||||||
if(item.id == id){
|
if(item.id == id){
|
||||||
item.isSelected = true;
|
item.isSelected = true;
|
||||||
@ -265,19 +344,21 @@ bool MySql::updateAvailableSongs(QList<SongHeader>& list, const QString& playLis
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool MySql::updateAvailableSongs(QStringList& list, const QString& playList){
|
bool MySql::updateAvailableSongs(PlayList& list, const QString& playList, bool forEditing){
|
||||||
|
|
||||||
QList<SongHeader> tempList;
|
QList<SongStorage> tempList;
|
||||||
|
list.clear();
|
||||||
|
|
||||||
if(!updateAvailableSongs(tempList, playList))
|
if(!updateAvailableSongs(tempList, playList, forEditing))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
for(SongHeader &header : tempList){
|
for(SongStorage &header : tempList){
|
||||||
list.push_back(header.name);
|
if(!list.addMedia(header)){
|
||||||
|
this->removeSong(header);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
60
sync/mysql.h
60
sync/mysql.h
@ -1,7 +1,7 @@
|
|||||||
#ifndef MYSQL_H
|
#ifndef MYSQL_H
|
||||||
#define MYSQL_H
|
#define MYSQL_H
|
||||||
#include <QString>
|
#include <QString>
|
||||||
#include "song.h"
|
#include "playlist.h"
|
||||||
|
|
||||||
class QSqlDatabase;
|
class QSqlDatabase;
|
||||||
class QSqlQuery;
|
class QSqlQuery;
|
||||||
@ -14,6 +14,7 @@ private:
|
|||||||
QSqlDatabase *db;
|
QSqlDatabase *db;
|
||||||
QSqlQuery *qyery;
|
QSqlQuery *qyery;
|
||||||
QString dataBaseName;
|
QString dataBaseName;
|
||||||
|
QString songDir;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief sqlErrorLog show sql error
|
* @brief sqlErrorLog show sql error
|
||||||
@ -21,6 +22,14 @@ private:
|
|||||||
*/
|
*/
|
||||||
void sqlErrorLog(const QString& qyery) const;
|
void sqlErrorLog(const QString& qyery) const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief saveToStorage save song as file into hdd
|
||||||
|
* @param url - url of song after save
|
||||||
|
* @param song - saved song
|
||||||
|
* @return true if all done
|
||||||
|
*/
|
||||||
|
bool saveToStorage(QUrl& url, const Song& song)const;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
MySql(const QString& databasename);
|
MySql(const QString& databasename);
|
||||||
/**
|
/**
|
||||||
@ -28,13 +37,56 @@ public:
|
|||||||
*/
|
*/
|
||||||
void initDB(const QString& database = DATABASE_NAME );
|
void initDB(const QString& database = DATABASE_NAME );
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief find - find song
|
||||||
|
* @param song - song header
|
||||||
|
* @param response Media Content of finded song
|
||||||
|
* @return true if song finded
|
||||||
|
*/
|
||||||
|
bool find(const SongHeader& song, QMediaContent& response);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief find - find song
|
||||||
|
* @param song - song header
|
||||||
|
* @param response Media Content of finded song
|
||||||
|
* @return true if song finded
|
||||||
|
*/
|
||||||
|
bool find(const QMediaContent& song, SongHeader& response);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief find - find song
|
||||||
|
* @param song - media Content
|
||||||
|
* @param response header of finded song
|
||||||
|
* @return true if song finded
|
||||||
|
*/
|
||||||
|
bool find(const QMediaContent& song, SongStorage &response);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief setSoundDir
|
||||||
|
* @param str
|
||||||
|
*/
|
||||||
|
void setSoundDir(const QString& str);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief findSong
|
||||||
|
* @param song
|
||||||
|
*/
|
||||||
|
bool findSong(const SongHeader &song);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief load song of database;
|
* @brief load song of database;
|
||||||
* @brief song -
|
* @brief song -
|
||||||
* @brief result - the resulting value;
|
* @brief result - the resulting value;
|
||||||
* @return true if everything's done
|
* @return true if everything's done
|
||||||
*/
|
*/
|
||||||
bool load(const SongHeader &song, Song &result);
|
bool load(const SongHeader &song, SongStorage &result);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief save media data into local database.
|
||||||
|
* @param song savining media data.
|
||||||
|
* @return id of song saved on local database.
|
||||||
|
*/
|
||||||
|
int save(const SongStorage &song);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief save media data into local database.
|
* @brief save media data into local database.
|
||||||
@ -62,7 +114,7 @@ public:
|
|||||||
* @param forEdit - flag for editing play list. If this flag = true then return all available songs with corect flag 'isSelect'
|
* @param forEdit - flag for editing play list. If this flag = true then return all available songs with corect flag 'isSelect'
|
||||||
* @return true if all done
|
* @return true if all done
|
||||||
*/
|
*/
|
||||||
bool updateAvailableSongs(QList<SongHeader>& list, const QString &playList = "", bool forEditing = false);
|
bool updateAvailableSongs(QList<SongStorage>& list, const QString &playList = "", bool forEditing = false);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief updateAvelableSongs will update the list of participants of songs.
|
* @brief updateAvelableSongs will update the list of participants of songs.
|
||||||
@ -70,7 +122,7 @@ public:
|
|||||||
* @param playList - play list of songs (string).
|
* @param playList - play list of songs (string).
|
||||||
* @return true if all done
|
* @return true if all done
|
||||||
*/
|
*/
|
||||||
bool updateAvailableSongs(QStringList& list, const QString &playList = "");
|
bool updateAvailableSongs(PlayList& list, const QString &playList = "", bool forEditing = false);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief removeSong - remove song from local database.
|
* @brief removeSong - remove song from local database.
|
||||||
|
@ -12,24 +12,6 @@ Player::Player(const QString &bufferFile, QObject *parent, Flags flags):
|
|||||||
bufferVolume = 0;
|
bufferVolume = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Player::setMediaFromBytes(const QByteArray &array){
|
|
||||||
QFile f(buffer);
|
|
||||||
if(!f.open(QIODevice::WriteOnly | QIODevice::Truncate)){
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(array.length() != f.write(array.data(),array.length())){
|
|
||||||
|
|
||||||
f.close();
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
f.close();
|
|
||||||
|
|
||||||
setMedia(QUrl::fromLocalFile(QDir("./").absoluteFilePath(buffer)));
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Player::syncBegin(){
|
void Player::syncBegin(){
|
||||||
|
|
||||||
bufferVolume = volume();
|
bufferVolume = volume();
|
||||||
|
@ -21,13 +21,6 @@ public:
|
|||||||
|
|
||||||
Player(const QString& bufferFile, QObject *parent = Q_NULLPTR, Flags flags = Flags());
|
Player(const QString& bufferFile, QObject *parent = Q_NULLPTR, Flags flags = Flags());
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief setMediaFromBytes
|
|
||||||
* @param array of song data
|
|
||||||
* @return true if all done
|
|
||||||
*/
|
|
||||||
bool setMediaFromBytes(const QByteArray& array);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief syncBegin - palyer waiting for sunced.
|
* @brief syncBegin - palyer waiting for sunced.
|
||||||
*/
|
*/
|
||||||
|
93
sync/playlist.cpp
Normal file
93
sync/playlist.cpp
Normal file
@ -0,0 +1,93 @@
|
|||||||
|
#include "playlist.h"
|
||||||
|
|
||||||
|
PlayList::PlayList()
|
||||||
|
{
|
||||||
|
playListInfo.clear();
|
||||||
|
playList = new QMediaPlaylist();
|
||||||
|
}
|
||||||
|
|
||||||
|
QList<SongStorage>* PlayList::getInfo(){
|
||||||
|
return &playListInfo;
|
||||||
|
}
|
||||||
|
|
||||||
|
QMediaPlaylist* PlayList::getList(){
|
||||||
|
return playList;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PlayList::clear(){
|
||||||
|
playList->clear();
|
||||||
|
playListInfo.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PlayList::addMedia(const SongStorage &song){
|
||||||
|
if(!song.isValid())
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if(!playList->addMedia(song.toMedia()))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
playListInfo.push_back(song);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PlayList::next()const{
|
||||||
|
playList->next();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PlayList::prev()const{
|
||||||
|
playList->previous();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PlayList::isValid()const{
|
||||||
|
return playListInfo.size() == playList->mediaCount();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PlayList::isEmpty()const{
|
||||||
|
return playList->isEmpty() && playListInfo.isEmpty();
|
||||||
|
}
|
||||||
|
|
||||||
|
const SongHeader *PlayList::currentHeader()const{
|
||||||
|
if(playList->isEmpty() || playList->currentIndex() < 0)
|
||||||
|
return nullptr;
|
||||||
|
|
||||||
|
return static_cast<const SongHeader*>(&playListInfo[playList->currentIndex()]);
|
||||||
|
}
|
||||||
|
|
||||||
|
const SongStorage *PlayList::currentSong()const{
|
||||||
|
if(playList->isEmpty() || playList->currentIndex() < 0)
|
||||||
|
return nullptr;
|
||||||
|
|
||||||
|
return &playListInfo[playList->currentIndex()];
|
||||||
|
}
|
||||||
|
|
||||||
|
int PlayList::size()const{
|
||||||
|
return playList->mediaCount();
|
||||||
|
}
|
||||||
|
|
||||||
|
int PlayList::find(const SongHeader &header)const{
|
||||||
|
for(int i = 0; i < playList->mediaCount(); ++i) {
|
||||||
|
if(header == playList->media(i)) {
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PlayList::selectSong(int index){
|
||||||
|
if(playList->mediaCount() <= index || index < 0){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
playList->setCurrentIndex(index);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PlayList::selectSong(const SongHeader &header){
|
||||||
|
return selectSong(find(header));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
PlayList::~PlayList(){
|
||||||
|
delete playList;
|
||||||
|
}
|
113
sync/playlist.h
Normal file
113
sync/playlist.h
Normal file
@ -0,0 +1,113 @@
|
|||||||
|
#ifndef PLAYLIST_H
|
||||||
|
#define PLAYLIST_H
|
||||||
|
#include <QMediaPlaylist>
|
||||||
|
#include "song.h"
|
||||||
|
|
||||||
|
using namespace syncLib;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief The PlayList class
|
||||||
|
* palyList with songs info
|
||||||
|
*/
|
||||||
|
class PlayList
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
/**
|
||||||
|
* @brief playList media play list
|
||||||
|
*/
|
||||||
|
QMediaPlaylist *playList;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief playListInfo - info from databas
|
||||||
|
*/
|
||||||
|
QList<SongStorage> playListInfo;
|
||||||
|
public:
|
||||||
|
PlayList();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief getInfo
|
||||||
|
* @return info from database about songs
|
||||||
|
*/
|
||||||
|
QList<SongStorage>* getInfo();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief clear this play list
|
||||||
|
*/
|
||||||
|
void clear();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief addMedia media content into playList
|
||||||
|
* @param song - media content
|
||||||
|
* @return true if all done
|
||||||
|
*/
|
||||||
|
bool addMedia(const SongStorage& song);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief next
|
||||||
|
*/
|
||||||
|
void next()const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief prev
|
||||||
|
*/
|
||||||
|
void prev()const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief isValid
|
||||||
|
* @return true if this object valid
|
||||||
|
*/
|
||||||
|
bool isValid()const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief isEmpty
|
||||||
|
* @return true if playlist empty
|
||||||
|
*/
|
||||||
|
bool isEmpty()const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief getlist
|
||||||
|
* @return return pointer to media content
|
||||||
|
*/
|
||||||
|
QMediaPlaylist* getList();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief currentHeader
|
||||||
|
* @return header of curent song
|
||||||
|
*/
|
||||||
|
const SongHeader* currentHeader()const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief currentStorage
|
||||||
|
* @return header of curent song
|
||||||
|
*/
|
||||||
|
const SongStorage* currentSong()const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief size
|
||||||
|
* @return count of media items of playlist
|
||||||
|
*/
|
||||||
|
int size()const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief find
|
||||||
|
* @return index of finded media
|
||||||
|
*/
|
||||||
|
int find(const SongHeader& header)const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief selectSong
|
||||||
|
* @return true if song selected
|
||||||
|
*/
|
||||||
|
bool selectSong(int index);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief selectSong
|
||||||
|
* @param header of selecting song
|
||||||
|
* @return if song selected return true;
|
||||||
|
*/
|
||||||
|
bool selectSong(const SongHeader& header);
|
||||||
|
|
||||||
|
~PlayList();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // PLAYLIST_H
|
159
sync/song.cpp
159
sync/song.cpp
@ -1,5 +1,8 @@
|
|||||||
#include "song.h"
|
#include "song.h"
|
||||||
#include <QStringList>
|
#include <QStringList>
|
||||||
|
#include <QRegularExpression>
|
||||||
|
#include <QFile>
|
||||||
|
|
||||||
namespace syncLib{
|
namespace syncLib{
|
||||||
|
|
||||||
static const QStringList ValidSongs = {".mp3", ".wav", ".ogg"};
|
static const QStringList ValidSongs = {".mp3", ".wav", ".ogg"};
|
||||||
@ -11,6 +14,31 @@ SongHeader::SongHeader()
|
|||||||
this->size = 0;
|
this->size = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool SongHeader::getName(QString & name, const QUrl &url) const {
|
||||||
|
if(url.isLocalFile() && url.isValid()){
|
||||||
|
name = url.fileName();
|
||||||
|
name = name.right(name.lastIndexOf(QRegularExpression("[\\\/]")));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
bool SongHeader::getSize(int & size, const QUrl &url) const {
|
||||||
|
if(url.isLocalFile() && url.isValid()){
|
||||||
|
QFile f(url.toLocalFile());
|
||||||
|
if(!f.exists()){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
size = f.size();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
SongHeader& SongHeader::operator =(const SongHeader& right){
|
SongHeader& SongHeader::operator =(const SongHeader& right){
|
||||||
this->id = right.id;
|
this->id = right.id;
|
||||||
this->name = right.name;
|
this->name = right.name;
|
||||||
@ -18,15 +46,35 @@ SongHeader& SongHeader::operator =(const SongHeader& right){
|
|||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool SongHeader::operator ==(const SongHeader& right){
|
SongHeader& SongHeader::operator =(const QMediaContent& right){
|
||||||
|
this->id = -1;
|
||||||
|
if(!getName(name, right.canonicalUrl())){
|
||||||
|
name.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!getSize(this->size, right.canonicalUrl())){
|
||||||
|
this->size = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool SongHeader::operator ==(const SongHeader& right)const{
|
||||||
return this->name == right.name && this->size == right.size;
|
return this->name == right.name && this->size == right.size;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned int SongHeader::getSize() const{
|
bool SongHeader::operator ==(const QMediaContent& right)const{
|
||||||
QByteArray size;
|
QString name;
|
||||||
QDataStream stream(size);
|
if(!getName(name, right.canonicalUrl())){
|
||||||
stream << id << name << this->size;
|
return false;
|
||||||
return size.size();
|
}
|
||||||
|
|
||||||
|
int size;;
|
||||||
|
if(!getSize(size, right.canonicalUrl())){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return this->name == name && this->size == size;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool SongHeader::isNameValid() const{
|
bool SongHeader::isNameValid() const{
|
||||||
@ -45,14 +93,6 @@ bool SongHeader::isValid() const{
|
|||||||
|
|
||||||
SongHeader::~SongHeader(){}
|
SongHeader::~SongHeader(){}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Song::Song():
|
|
||||||
SongHeader()
|
|
||||||
{
|
|
||||||
source.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
QDataStream& operator << (QDataStream& stream, const SongHeader& song){
|
QDataStream& operator << (QDataStream& stream, const SongHeader& song){
|
||||||
stream << song.id;
|
stream << song.id;
|
||||||
stream << song.name;
|
stream << song.name;
|
||||||
@ -66,6 +106,93 @@ QDataStream& operator >> (QDataStream& stream, SongHeader& song){
|
|||||||
return stream;
|
return stream;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
SongStorage::SongStorage():
|
||||||
|
SongHeader()
|
||||||
|
{
|
||||||
|
url.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
SongStorage::SongStorage(const SongHeader& from)
|
||||||
|
:SongStorage::SongStorage()
|
||||||
|
{
|
||||||
|
this->id = from.id;
|
||||||
|
this->name = from.name;
|
||||||
|
this->size = from.size;
|
||||||
|
}
|
||||||
|
|
||||||
|
SongStorage::SongStorage(const QUrl& from)
|
||||||
|
:SongStorage::SongStorage()
|
||||||
|
{
|
||||||
|
if(!from.isValid() || !from.isLocalFile()){
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
QFile f(from.toLocalFile());
|
||||||
|
this->size = f.size();
|
||||||
|
f.close();
|
||||||
|
|
||||||
|
this->id = -1;
|
||||||
|
url = from;
|
||||||
|
if(!getName(name, from)){
|
||||||
|
name.clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
SongStorage::SongStorage(const QMediaContent& from)
|
||||||
|
:SongStorage::SongStorage(from.canonicalUrl())
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
const QUrl& SongStorage::getSource()const{
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool SongStorage::isValid() const{
|
||||||
|
return SongHeader::isValid() && url.isValid() && QFile(url.toLocalFile()).exists();
|
||||||
|
}
|
||||||
|
|
||||||
|
SongStorage::~SongStorage(){
|
||||||
|
url.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
QMediaContent SongStorage::toMedia()const{
|
||||||
|
return QMediaContent(url);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool SongStorage::toSong(Song&)const{
|
||||||
|
Song song(*((SongHeader*)this));
|
||||||
|
|
||||||
|
QFile f(url.toLocalFile());
|
||||||
|
|
||||||
|
if(!f.open(QIODevice::ReadOnly))
|
||||||
|
return false;
|
||||||
|
song.source = f.readAll();
|
||||||
|
|
||||||
|
f.close();
|
||||||
|
return song.isValid();
|
||||||
|
}
|
||||||
|
|
||||||
|
QDataStream& operator << (QDataStream& stream,const SongStorage& song){
|
||||||
|
stream << static_cast<const SongHeader&>(song);
|
||||||
|
stream << song.url;
|
||||||
|
return stream;
|
||||||
|
}
|
||||||
|
|
||||||
|
QDataStream& operator >> (QDataStream& stream, SongStorage& song){
|
||||||
|
stream >> static_cast<SongHeader&>(song);
|
||||||
|
stream >> song.url;
|
||||||
|
return stream;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Song::Song():
|
||||||
|
SongHeader()
|
||||||
|
{
|
||||||
|
source.clear();
|
||||||
|
}
|
||||||
|
|
||||||
Song::Song(const SongHeader& from)
|
Song::Song(const SongHeader& from)
|
||||||
:Song::Song()
|
:Song::Song()
|
||||||
{
|
{
|
||||||
@ -78,10 +205,6 @@ void Song::clear(){
|
|||||||
source.clear();
|
source.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned int Song::getSize() const{
|
|
||||||
return SongHeader::getSize() + source.size();
|
|
||||||
}
|
|
||||||
|
|
||||||
const QByteArray& Song::getSource()const{
|
const QByteArray& Song::getSource()const{
|
||||||
return source;
|
return source;
|
||||||
}
|
}
|
||||||
|
37
sync/song.h
37
sync/song.h
@ -4,6 +4,7 @@
|
|||||||
#include <QByteArray>
|
#include <QByteArray>
|
||||||
#include <QDataStream>
|
#include <QDataStream>
|
||||||
#include "chronotime.h"
|
#include "chronotime.h"
|
||||||
|
#include <QMediaContent>
|
||||||
|
|
||||||
namespace syncLib {
|
namespace syncLib {
|
||||||
|
|
||||||
@ -24,7 +25,9 @@ struct Syncer
|
|||||||
* (id,size and name)
|
* (id,size and name)
|
||||||
*/
|
*/
|
||||||
class SongHeader{
|
class SongHeader{
|
||||||
|
protected:
|
||||||
|
bool getName(QString &name, const QUrl& url)const;
|
||||||
|
bool getSize(int &size, const QUrl& url)const;
|
||||||
public:
|
public:
|
||||||
bool isSelected;
|
bool isSelected;
|
||||||
int id;
|
int id;
|
||||||
@ -32,8 +35,10 @@ public:
|
|||||||
int size;
|
int size;
|
||||||
SongHeader();
|
SongHeader();
|
||||||
SongHeader& operator = (const SongHeader& right);
|
SongHeader& operator = (const SongHeader& right);
|
||||||
bool operator == (const SongHeader& right);
|
SongHeader& operator = (const QMediaContent& right);
|
||||||
virtual unsigned int getSize() const;
|
|
||||||
|
bool operator == (const SongHeader& right)const;
|
||||||
|
bool operator == (const QMediaContent& right)const;
|
||||||
bool isNameValid() const;
|
bool isNameValid() const;
|
||||||
virtual bool isValid() const;
|
virtual bool isValid() const;
|
||||||
virtual ~SongHeader();
|
virtual ~SongHeader();
|
||||||
@ -61,12 +66,36 @@ public:
|
|||||||
Song(const SongHeader& from);
|
Song(const SongHeader& from);
|
||||||
void clear();
|
void clear();
|
||||||
const QByteArray& getSource()const;
|
const QByteArray& getSource()const;
|
||||||
unsigned int getSize() const;
|
|
||||||
bool isValid() const;
|
bool isValid() const;
|
||||||
~Song();
|
~Song();
|
||||||
friend QDataStream& operator << (QDataStream& stream, const Song& song);
|
friend QDataStream& operator << (QDataStream& stream, const Song& song);
|
||||||
friend QDataStream& operator >> (QDataStream& stream, Song& song);
|
friend QDataStream& operator >> (QDataStream& stream, Song& song);
|
||||||
friend class MySql;
|
friend class MySql;
|
||||||
|
friend class SongStorage;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief The SongStorage class
|
||||||
|
* header with url to song source
|
||||||
|
*/
|
||||||
|
class SongStorage : public SongHeader {
|
||||||
|
private:
|
||||||
|
QUrl url;
|
||||||
|
public:
|
||||||
|
SongStorage();
|
||||||
|
SongStorage(const SongHeader& from);
|
||||||
|
SongStorage(const QUrl& url);
|
||||||
|
SongStorage(const QMediaContent& media);
|
||||||
|
const QUrl& getSource()const;
|
||||||
|
bool toSong(Song &)const;
|
||||||
|
QMediaContent toMedia()const;
|
||||||
|
bool isValid() const;
|
||||||
|
~SongStorage();
|
||||||
|
friend QDataStream& operator << (QDataStream& stream, const SongStorage& song);
|
||||||
|
friend QDataStream& operator >> (QDataStream& stream, SongStorage& song);
|
||||||
|
friend class MySql;
|
||||||
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
#endif // SONG_H
|
#endif // SONG_H
|
||||||
|
198
sync/sync.cpp
198
sync/sync.cpp
@ -22,11 +22,14 @@ Sync::Sync(const QString &address, int port, const QString &datadir):
|
|||||||
if(!player->isAvailable()){
|
if(!player->isAvailable()){
|
||||||
throw MediaException();
|
throw MediaException();
|
||||||
}
|
}
|
||||||
|
playList = new PlayList;
|
||||||
|
|
||||||
|
player->setPlaylist(playList->getList());
|
||||||
|
|
||||||
|
|
||||||
fbroadcaster = false;
|
fbroadcaster = false;
|
||||||
resyncCount = 0;
|
resyncCount = 0;
|
||||||
lastSyncTime = 0;
|
lastSyncTime = 0;
|
||||||
currentSongIndex = 0;
|
|
||||||
ping = 0;
|
ping = 0;
|
||||||
|
|
||||||
sql = new MySql(datadir);
|
sql = new MySql(datadir);
|
||||||
@ -41,7 +44,15 @@ MySql* Sync::getSqlApi(){
|
|||||||
return sql;
|
return sql;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::updateSongs(QList<SongHeader>& list, const QString& playList){
|
bool Sync::setSingle(const QMediaContent& media){
|
||||||
|
playList->clear();
|
||||||
|
playList->addMedia(media);
|
||||||
|
|
||||||
|
emit currentPlayListChanged();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Sync::updateSongs(PlayList& list, const QString& playList){
|
||||||
if(!sql->updateAvailableSongs(list, playList)){
|
if(!sql->updateAvailableSongs(list, playList)){
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -59,28 +70,54 @@ const QString& Sync::getPlayListName() const{
|
|||||||
return lastUsedPlayList;
|
return lastUsedPlayList;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::findHeader(const Song &song){
|
bool Sync::play(bool fbroadcast){
|
||||||
|
fbroadcaster = fbroadcast;
|
||||||
|
|
||||||
|
if(fbroadcaster){
|
||||||
|
player->play();
|
||||||
|
sync();
|
||||||
|
}else{
|
||||||
|
player->syncBegin();
|
||||||
|
}
|
||||||
|
emit currentSongChanged();
|
||||||
|
|
||||||
for(int i = 0; i < playList.size(); i++){
|
|
||||||
if(playList[i] == static_cast<SongHeader>(song)){
|
|
||||||
currentSongIndex = i;
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool Sync::play(const SongStorage &song, bool fbroadcast){
|
||||||
|
|
||||||
|
if(!song.isValid()){
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
if(playList->selectSong(song)){
|
||||||
|
return play(fbroadcast);
|
||||||
|
}
|
||||||
|
|
||||||
|
playList->clear();
|
||||||
|
playList->addMedia(song);
|
||||||
|
|
||||||
|
return play(fbroadcast);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::play(const SongHeader &header, bool fbroadcast){
|
bool Sync::play(const SongHeader &header, bool fbroadcast){
|
||||||
|
|
||||||
Song song;
|
if(!header.isValid()){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(playList->selectSong(header)){
|
||||||
|
return play(fbroadcast);
|
||||||
|
}
|
||||||
|
|
||||||
|
SongStorage song;
|
||||||
SongHeader newheader = header;
|
SongHeader newheader = header;
|
||||||
newheader.id = -1;
|
newheader.id = -1;
|
||||||
if(!sql->load(newheader, song)){
|
if(!sql->load(newheader, song)){
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return Sync::play(song, fbroadcast);
|
return play(song, fbroadcast);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::play(const Song &song, bool fbroadcast){
|
bool Sync::play(const Song &song, bool fbroadcast){
|
||||||
@ -89,27 +126,27 @@ bool Sync::play(const Song &song, bool fbroadcast){
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!player->setMediaFromBytes(song.getSource())){
|
QMediaContent savedSong;
|
||||||
return false;
|
if(!sql->find(static_cast<const SongHeader&>(song), savedSong) && sql->save(song) > -1 &&
|
||||||
}
|
!sql->find((SongHeader&)song, savedSong)){
|
||||||
|
|
||||||
fbroadcaster = fbroadcast;
|
|
||||||
|
|
||||||
if(!findHeader(song) && sql->save(song) > -1 &&
|
|
||||||
updateSongs(playList) && !findHeader(song)){
|
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(fbroadcaster){
|
return play(savedSong, fbroadcast);
|
||||||
player->play();
|
|
||||||
sync();
|
|
||||||
}else{
|
|
||||||
player->syncBegin();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
emit currentSongChanged();
|
bool Sync::play(const QMediaContent& media, bool fbroadcast){
|
||||||
return true;
|
|
||||||
|
if(media.isNull()){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!setSingle(media)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return Sync::play(fbroadcast);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::play(int id_song, bool fbroadcast){
|
bool Sync::play(int id_song, bool fbroadcast){
|
||||||
@ -119,9 +156,12 @@ bool Sync::play(int id_song, bool fbroadcast){
|
|||||||
}
|
}
|
||||||
|
|
||||||
SongHeader header;
|
SongHeader header;
|
||||||
|
SongStorage song;
|
||||||
header.id = id_song;
|
header.id = id_song;
|
||||||
Song song;
|
|
||||||
sql->load(header, song);
|
if(!sql->load(header, song)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
return Sync::play(song, fbroadcast);
|
return Sync::play(song, fbroadcast);
|
||||||
}
|
}
|
||||||
@ -135,22 +175,21 @@ bool Sync::play(QString url){
|
|||||||
return Sync::play(id);
|
return Sync::play(id);
|
||||||
}
|
}
|
||||||
|
|
||||||
Repeat Sync::repeat()const{
|
QMediaPlaylist::PlaybackMode Sync::repeat()const{
|
||||||
return _repeat;
|
return playList->getList()->playbackMode();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Sync::setRepeat(Repeat flag){
|
void Sync::setRepeat(QMediaPlaylist::PlaybackMode flag){
|
||||||
_repeat = flag;
|
playList->getList()->setPlaybackMode(flag);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::pause(bool state){
|
bool Sync::pause(bool state){
|
||||||
|
|
||||||
if(!fbroadcaster){
|
if(player->state() == QMediaPlayer::StoppedState){
|
||||||
|
if(playList->isEmpty())
|
||||||
if(playList.isEmpty())
|
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
return play(playList[0]);
|
return play();
|
||||||
}
|
}
|
||||||
|
|
||||||
if(state){
|
if(state){
|
||||||
@ -189,6 +228,9 @@ bool Sync::sync(const Syncer &sync, milliseconds ping){
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @todo thi nead send a hedaer
|
||||||
|
*/
|
||||||
void Sync::sync(){
|
void Sync::sync(){
|
||||||
|
|
||||||
if(fbroadcaster)
|
if(fbroadcaster)
|
||||||
@ -196,7 +238,7 @@ void Sync::sync(){
|
|||||||
|
|
||||||
package pac;
|
package pac;
|
||||||
if(!createPackage(t_sync, pac)){
|
if(!createPackage(t_sync, pac)){
|
||||||
throw CreatePackageExaption();
|
CreatePackageExaption();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
node->WriteAll(pac.parseTo());
|
node->WriteAll(pac.parseTo());
|
||||||
@ -252,18 +294,17 @@ bool Sync::createPackage(Type type, package &pac){
|
|||||||
}
|
}
|
||||||
|
|
||||||
if(type & TypePackage::t_song_h && fbroadcaster){
|
if(type & TypePackage::t_song_h && fbroadcaster){
|
||||||
if(currentSongIndex < 0)
|
if(playList->getList()->currentIndex() < 0)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
pac.header = playList[currentSongIndex];
|
pac.header = *playList->currentHeader();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if(type & TypePackage::t_song && fbroadcaster){
|
if(type & TypePackage::t_song && fbroadcaster){
|
||||||
if(currentSongIndex < 0)
|
if(playList->getList()->currentIndex() < 0)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if(!sql->load(playList[currentSongIndex], pac.source))
|
if(!playList->currentSong()->toSong(pac.source))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -387,7 +428,7 @@ void Sync::packageRender(ETcpSocket *socket){
|
|||||||
|
|
||||||
// if requst from client
|
// if requst from client
|
||||||
if(pkg.getType() & t_play & t_sync){
|
if(pkg.getType() & t_play & t_sync){
|
||||||
if(currentSongIndex < 0){
|
if(playList->getList()->currentIndex() < 0){
|
||||||
throw SyncError();
|
throw SyncError();
|
||||||
socket->nextItem();
|
socket->nextItem();
|
||||||
continue;
|
continue;
|
||||||
@ -443,32 +484,27 @@ void Sync::deepScaned(QList<ETcpSocket *> * list){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Sync::endPlay(QMediaPlayer::State state){
|
void Sync::endPlay(QMediaPlayer::State state){
|
||||||
if(state == QMediaPlayer::StoppedState){
|
|
||||||
|
|
||||||
switch (_repeat) {
|
switch (state) {
|
||||||
case allPlayListRandom:
|
case QMediaPlayer::StoppedState:
|
||||||
next(true);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case allPlayList:
|
|
||||||
next(false);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case oneMusic:
|
|
||||||
play(playList[currentSongIndex]);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
currentSongIndex = -1;
|
|
||||||
fbroadcaster = false;
|
fbroadcaster = false;
|
||||||
break;
|
break;
|
||||||
|
case QMediaPlayer::PlayingState:
|
||||||
|
sync();
|
||||||
|
break;
|
||||||
|
|
||||||
|
case QMediaPlayer::PausedState:
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
emit playStateChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
QString Sync::getVersion(){
|
QString Sync::getVersion(){
|
||||||
return QString(tr("Version") + "%0.%1.%2").arg(MAJOR_VERSION).arg(MINOR_VERSION).arg(REVISION_VERSION);
|
return QString(tr("Version") + "%0.%1.%2").
|
||||||
|
arg(MAJOR_VERSION).arg(MINOR_VERSION).arg(REVISION_VERSION);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::setValume(unsigned int valume){
|
bool Sync::setValume(unsigned int valume){
|
||||||
@ -488,19 +524,16 @@ unsigned int Sync::seek() const{
|
|||||||
return player->position();
|
return player->position();
|
||||||
}
|
}
|
||||||
|
|
||||||
const QList<SongHeader>* Sync::getPlayList() const{
|
const QList<SongStorage>* Sync::getPlayList() const{
|
||||||
return &playList;
|
return playList->getInfo();
|
||||||
}
|
}
|
||||||
|
|
||||||
int Sync::getCurrentSongIndex()const{
|
int Sync::getCurrentSongIndex()const{
|
||||||
return currentSongIndex;
|
return playList->getList()->currentIndex();
|
||||||
}
|
}
|
||||||
|
|
||||||
const SongHeader* Sync::getCurrentSong() const{
|
const SongStorage* Sync::getCurrentSong() const{
|
||||||
if(currentSongIndex < 0 || currentSongIndex >= playList.size()){
|
return playList->currentSong();
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
return &playList[currentSongIndex];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
qint64 Sync::getEndPoint() const {
|
qint64 Sync::getEndPoint() const {
|
||||||
@ -509,48 +542,53 @@ qint64 Sync::getEndPoint() const {
|
|||||||
|
|
||||||
int Sync::addNewSong(const QString &url){
|
int Sync::addNewSong(const QString &url){
|
||||||
int result = sql->save(url);
|
int result = sql->save(url);
|
||||||
updateSongs(playList);
|
updateSongs(*playList);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::updatePlayList(const QString &_playList){
|
bool Sync::updatePlayList(const QString &_playList){
|
||||||
if(!updateSongs(playList, _playList)){
|
if(!updateSongs(*playList, _playList)){
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!playList.size())
|
if(!playList->size())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if(fbroadcaster){
|
if(fbroadcaster){
|
||||||
play(playList.first());
|
play(fbroadcaster);
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::next(bool random){
|
bool Sync::next(){
|
||||||
if(playList.isEmpty())
|
if(playList->isEmpty())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
currentSongIndex = (currentSongIndex + ((random)? rand() % 10000:1)) % playList.size();
|
playList->next();
|
||||||
return play(playList[currentSongIndex]);
|
emit currentSongChanged();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Sync::prev(){
|
bool Sync::prev(){
|
||||||
if(playList.isEmpty())
|
if(playList->isEmpty())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
--currentSongIndex;
|
playList->prev();
|
||||||
if(currentSongIndex < 0)
|
emit currentSongChanged();
|
||||||
currentSongIndex = playList.size() - 1;
|
return true;
|
||||||
return play(playList[currentSongIndex]);
|
}
|
||||||
|
|
||||||
|
QMediaPlayer::State Sync::playState()const{
|
||||||
|
return player->state();
|
||||||
}
|
}
|
||||||
|
|
||||||
Sync::~Sync(){
|
Sync::~Sync(){
|
||||||
delete node;
|
delete node;
|
||||||
delete player;
|
delete player;
|
||||||
delete sql;
|
delete sql;
|
||||||
|
delete playList;
|
||||||
servers.clear();
|
servers.clear();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
68
sync/sync.h
68
sync/sync.h
@ -6,7 +6,9 @@
|
|||||||
#include <chrono>
|
#include <chrono>
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
#include "mysql.h"
|
#include "mysql.h"
|
||||||
|
#include <QMediaPlaylist>
|
||||||
#include "player.h"
|
#include "player.h"
|
||||||
|
#include "playlist.h"
|
||||||
|
|
||||||
namespace syncLib {
|
namespace syncLib {
|
||||||
|
|
||||||
@ -14,8 +16,6 @@ typedef std::chrono::time_point<std::chrono::high_resolution_clock> Clock;
|
|||||||
|
|
||||||
class Node;
|
class Node;
|
||||||
|
|
||||||
enum Repeat{noRepeat, oneMusic, allPlayList, allPlayListRandom};
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief The Sync class is main class of this library.
|
* @brief The Sync class is main class of this library.
|
||||||
@ -27,9 +27,8 @@ class Sync : public QObject
|
|||||||
private:
|
private:
|
||||||
Node *node;
|
Node *node;
|
||||||
Player *player;
|
Player *player;
|
||||||
QList<SongHeader> playList;
|
PlayList *playList;
|
||||||
QString lastUsedPlayList;
|
QString lastUsedPlayList;
|
||||||
int currentSongIndex;
|
|
||||||
QList<ETcpSocket*> servers;
|
QList<ETcpSocket*> servers;
|
||||||
bool fbroadcaster;
|
bool fbroadcaster;
|
||||||
int resyncCount;
|
int resyncCount;
|
||||||
@ -38,13 +37,6 @@ private:
|
|||||||
LocalScanner deepScaner;
|
LocalScanner deepScaner;
|
||||||
MySql *sql;
|
MySql *sql;
|
||||||
int port;
|
int port;
|
||||||
Repeat _repeat;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief findHeader set current song if playList have playng song
|
|
||||||
* @return true if all done
|
|
||||||
*/
|
|
||||||
bool findHeader(const Song& song);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief rescan - search for existing servers
|
* @brief rescan - search for existing servers
|
||||||
@ -62,11 +54,17 @@ private:
|
|||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief setSingle set singl or temp playlist
|
||||||
|
* @return true if all done
|
||||||
|
*/
|
||||||
|
bool setSingle(const QMediaContent& media);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief updateSongs use method update avelable songs from sql database
|
* @brief updateSongs use method update avelable songs from sql database
|
||||||
* @return true if all done
|
* @return true if all done
|
||||||
*/
|
*/
|
||||||
bool updateSongs(QList<SongHeader> &list, const QString &playList = "");
|
bool updateSongs(PlayList &list, const QString &playList = "");
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief packageRender - the handler of all messages received.
|
* @brief packageRender - the handler of all messages received.
|
||||||
@ -96,13 +94,13 @@ public:
|
|||||||
* @brief repeat
|
* @brief repeat
|
||||||
* @return flag of repeat
|
* @return flag of repeat
|
||||||
*/
|
*/
|
||||||
Repeat repeat()const;
|
QMediaPlaylist::PlaybackMode repeat()const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief setRepeat
|
* @brief setRepeat
|
||||||
* @param flag new flag of repeat
|
* @param flag new flag of repeat
|
||||||
*/
|
*/
|
||||||
void setRepeat(Repeat flag);
|
void setRepeat(QMediaPlaylist::PlaybackMode flag);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief getSqlApi
|
* @brief getSqlApi
|
||||||
@ -110,6 +108,21 @@ public:
|
|||||||
*/
|
*/
|
||||||
MySql* getSqlApi();
|
MySql* getSqlApi();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Play song in this device, if device has not supported playning media data this method throw MediaExcrption.
|
||||||
|
* @param fbroadcast - server broadcasting sound.
|
||||||
|
* @return true if all done else false.
|
||||||
|
*/
|
||||||
|
bool play(bool fbroadcast = true);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Play song in this device, if device has not supported playning media data this method throw MediaExcrption.
|
||||||
|
* @param header of song
|
||||||
|
* @param fbroadcast - server broadcasting sound.
|
||||||
|
* @return true if all done else false.
|
||||||
|
*/
|
||||||
|
bool play(const QMediaContent &media, bool fbroadcast = true);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Play song in this device, if device has not supported playning media data this method throw MediaExcrption.
|
* @brief Play song in this device, if device has not supported playning media data this method throw MediaExcrption.
|
||||||
* @param header of song
|
* @param header of song
|
||||||
@ -117,6 +130,15 @@ public:
|
|||||||
* @return true if all done else false.
|
* @return true if all done else false.
|
||||||
*/
|
*/
|
||||||
bool play(const SongHeader &header, bool fbroadcast = true);
|
bool play(const SongHeader &header, bool fbroadcast = true);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Play song in this device, if device has not supported playning media data this method throw MediaExcrption.
|
||||||
|
* @param header of song
|
||||||
|
* @param fbroadcast - server broadcasting sound.
|
||||||
|
* @return true if all done else false.
|
||||||
|
*/
|
||||||
|
bool play(const SongStorage &song, bool fbroadcast = true);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Play song in this device, if device has not supported playning media data this method throw MediaExcrption.
|
* @brief Play song in this device, if device has not supported playning media data this method throw MediaExcrption.
|
||||||
* @param song playning media data.
|
* @param song playning media data.
|
||||||
@ -228,7 +250,7 @@ public:
|
|||||||
* @brief getPlayList
|
* @brief getPlayList
|
||||||
* @return list of available songs
|
* @return list of available songs
|
||||||
*/
|
*/
|
||||||
const QList<SongHeader> *getPlayList() const;
|
const QList<SongStorage> *getPlayList() const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief SongHeader::getCurrentSongIndex
|
* @brief SongHeader::getCurrentSongIndex
|
||||||
@ -240,7 +262,7 @@ public:
|
|||||||
* @brief getCurrentSong
|
* @brief getCurrentSong
|
||||||
* @return playing song.
|
* @return playing song.
|
||||||
*/
|
*/
|
||||||
const SongHeader *getCurrentSong() const;
|
const SongStorage *getCurrentSong() const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief getEndPoint
|
* @brief getEndPoint
|
||||||
@ -266,7 +288,7 @@ public:
|
|||||||
* @brief next
|
* @brief next
|
||||||
* @return true if all done;
|
* @return true if all done;
|
||||||
*/
|
*/
|
||||||
bool next(bool random = false);
|
bool next();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief prev
|
* @brief prev
|
||||||
@ -274,6 +296,12 @@ public:
|
|||||||
*/
|
*/
|
||||||
bool prev();
|
bool prev();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief playState
|
||||||
|
* @return state of media data
|
||||||
|
*/
|
||||||
|
QMediaPlayer::State playState()const;
|
||||||
|
|
||||||
Sync(const QString &address = DEFAULT_ADRESS, int port = DEFAULT_PORT, const QString& datadir = DATABASE_NAME);
|
Sync(const QString &address = DEFAULT_ADRESS, int port = DEFAULT_PORT, const QString& datadir = DATABASE_NAME);
|
||||||
~Sync();
|
~Sync();
|
||||||
|
|
||||||
@ -310,6 +338,12 @@ signals:
|
|||||||
*/
|
*/
|
||||||
void currentSongChanged();
|
void currentSongChanged();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief playStateChanged
|
||||||
|
* emited when state of playing song changed
|
||||||
|
*/
|
||||||
|
void playStateChanged();
|
||||||
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user