fix previous button, single point of definition

This commit is contained in:
Anika Raemer 2021-10-13 15:06:09 +02:00
parent a483a380d6
commit 75308b4423
4 changed files with 100 additions and 34 deletions

View file

@ -1,7 +1,7 @@
#include "MusicPlayer.h" #include "MusicPlayer.h"
#include <QDir> #include <QDir>
#include <QMediaPlaylist> #include <QMediaPlaylist>
#include <controllers/SettingsHandler.h>
MusicPlayer::MusicPlayer(QObject *parent) : QMediaPlayer(parent) MusicPlayer::MusicPlayer(QObject *parent) : QMediaPlayer(parent)
@ -98,7 +98,7 @@ bool MusicPlayer::hasPrevious() const
/* player inits with currentIndex -1 and hence previousIndex = last index /* player inits with currentIndex -1 and hence previousIndex = last index
* until started. Yet, previousButton should initially be disabled. * until started. Yet, previousButton should initially be disabled.
*/ */
return previousIndex >= 0 && previousIndex >= playlist()->currentIndex(); return previousIndex >= 0 && previousIndex < playlist()->currentIndex();
} }
double MusicPlayer::getProgress() const double MusicPlayer::getProgress() const
@ -111,17 +111,17 @@ double MusicPlayer::getProgress() const
QString MusicPlayer::getMediaTitle() const QString MusicPlayer::getMediaTitle() const
{ {
return mMediaTitle; return metaData("Title").toString();
} }
QString MusicPlayer::getMediaLength() QString MusicPlayer::getMediaDuration() const
{ {
return timeToString(duration()); return millisecondsToString(duration());
} }
QString MusicPlayer::getTime() QString MusicPlayer::getPosition() const
{ {
return timeToString(position()); return millisecondsToString(position());
} }
void MusicPlayer::clearPlaylist() void MusicPlayer::clearPlaylist()
@ -144,7 +144,7 @@ void MusicPlayer::readMedia(const QString& path)
} }
// add audio files to playlist // add audio files to playlist
dir.setNameFilters({"*.mp3", "*.flac"}); dir.setNameFilters(SettingsHandler::getAudioFileNameFilters());
auto files = dir.entryInfoList(QDir::Files); auto files = dir.entryInfoList(QDir::Files);
for(auto file:files){ for(auto file:files){
auto fileName = file.absoluteFilePath(); auto fileName = file.absoluteFilePath();
@ -153,11 +153,13 @@ void MusicPlayer::readMedia(const QString& path)
} }
} }
QString MusicPlayer::timeToString(int time) QString MusicPlayer::millisecondsToString(int timeInMilliseconds) const
{ {
int sec = time/1000; int seconds = timeInMilliseconds/1000; // ms to secons
int min = sec/60; int minutes = seconds/60; //seconds to minutes
sec = sec-min*60; seconds %= 60; // seconds remaining after subtracting minutes
QString secStr = (sec < 10) ? "0"+QString::number(sec) : QString::number(sec); // format according to [M]M:ss
return QString::number(min) + ":" + secStr; // at leading zero to seconds if necessary
QString secStr = (seconds < 10) ? "0"+QString::number(seconds) : QString::number(seconds);
return QString::number(minutes) + ":" + secStr;
} }

View file

@ -6,7 +6,10 @@
#include <models/NavigationItemModel.h> #include <models/NavigationItemModel.h>
/** /**
* @brief MusicPlayer providing interface to QML and Navigation * @brief MusicPlayer providing interface to QML and Navigation.
*
* Adds media from directory referenced by the current navigation item to
* playlist and provides interface to QML MusicPlayer.
*/ */
class MusicPlayer : public QMediaPlayer class MusicPlayer : public QMediaPlayer
{ {
@ -17,9 +20,9 @@ class MusicPlayer : public QMediaPlayer
Q_PROPERTY(bool pHasPrevious READ hasPrevious NOTIFY hasPreviousChanged) Q_PROPERTY(bool pHasPrevious READ hasPrevious NOTIFY hasPreviousChanged)
Q_PROPERTY(bool pIsPlaying READ isPlaying NOTIFY isPlayingChanged) Q_PROPERTY(bool pIsPlaying READ isPlaying NOTIFY isPlayingChanged)
Q_PROPERTY(double pProgress READ getProgress NOTIFY progressChanged) Q_PROPERTY(double pProgress READ getProgress NOTIFY progressChanged)
Q_PROPERTY(QString pMediaLength READ getMediaLength NOTIFY mediaLengthChanged) Q_PROPERTY(QString pMediaLength READ getMediaDuration NOTIFY mediaLengthChanged)
Q_PROPERTY(QString pTime READ getTime NOTIFY progressChanged) Q_PROPERTY(QString pTime READ getPosition NOTIFY progressChanged)
Q_PROPERTY(QString pMediaTitle READ getMediaTitle NOTIFY mediaTitleChanged) Q_PROPERTY(QString pMediaTitle READ getMediaTitle NOTIFY metaDataChanged)
signals: signals:
void navigateTo(NavigationItemModel *item); void navigateTo(NavigationItemModel *item);
@ -29,12 +32,16 @@ signals:
void isPlayingChanged(); void isPlayingChanged();
void progressChanged(); void progressChanged();
void mediaLengthChanged(); void mediaLengthChanged();
void mediaTitleChanged();
public: public:
MusicPlayer(QObject *parent = Q_NULLPTR); MusicPlayer(QObject *parent = Q_NULLPTR);
~MusicPlayer() =default; ~MusicPlayer() =default;
/**
* @brief Init playlist with media from directory referenced by item.
* @param item Navigation item representing a leaf
* @see void readMedia(const QString& path)
*/
void init(NavigationItemModel* item); void init(NavigationItemModel* item);
/** /**
@ -42,23 +49,71 @@ public:
* @return Path to media cover image. * @return Path to media cover image.
*/ */
inline const QString& getCoverImageSource() const {return mCurrentItem->getImageSource();} inline const QString& getCoverImageSource() const {return mCurrentItem->getImageSource();}
/**
* @brief Indicates whether the media player is currently playing a track.
* @return true if media player is playing a track.
*/
bool isPlaying() const; bool isPlaying() const;
/**
* @brief Indicates whether there is a next item in the playlist.
* @return True if there is a next item in the playlist
* Does not wrap.
*/
bool hasNext() const; bool hasNext() const;
/**
* @brief Indicates whether there is a previous item in the playlist.
* @return True if there is a previous item in the playlist
* Does not wrap.
*/
bool hasPrevious() const; bool hasPrevious() const;
/**
* @brief Get media progress as value in between 0 and 1
* @return Media progress
* 0 corresponds to the beginning and 1 to the end of the current track.
*/
double getProgress() const; double getProgress() const;
/**
* @brief Get current media title extracted from media meta data (id3 tags)
* @return Current media title
*/
QString getMediaTitle() const; QString getMediaTitle() const;
QString getMediaLength(); /**
QString getTime(); * @brief Get duration of the current track
* @return Duration of the current track formatted as string
* @see QMediaPlayer::duration()
* @see millisecondsToString(int timeInMilliseconds) const
*/
QString getMediaDuration() const;
/**
* @brief Get current position within the track
* @return Postion within the track formatted as string
* @see QMediaPlayer::position()
* @see millisecondsToString(int timeInMilliseconds) const
*/
QString getPosition() const;
public slots: public slots:
/**
* @brief Navigate back to navgation list
*/
void navigateBack(); void navigateBack();
/**
* @brief Play or pause music depending on whether it is currently playing
*/
void playPause(); void playPause();
/**
* @brief Stop music and reset track to first track in playlist
*/
void stopMusic(); void stopMusic();
/**
* @brief Play next track in current playlist if available
*/
void playNext(); void playNext();
/**
* @brief Replay previoustrack in current playlist if available
*/
void playPrevious(); void playPrevious();
private: private:
@ -66,20 +121,22 @@ private:
* @brief Resets playlist to first track if playlist exists and is non-empty * @brief Resets playlist to first track if playlist exists and is non-empty
*/ */
void resetPlaylistToFirstTrack(); void resetPlaylistToFirstTrack();
/**
* @brief Clear the current playlist
*/
void clearPlaylist(); void clearPlaylist();
/**
* @brief Add all media from path to playlist
* @param path Path to media
*/
void readMedia(const QString& path); void readMedia(const QString& path);
/** /**
* @brief Transforms time in milliseconds into a string * @brief Format time in milliseconds acoording to [M]m:ss
* @param time Time in ms * @param time Time in ms
* @return * @return formateted string
* @todo use QDateTime
*/ */
QString timeToString(int time); QString millisecondsToString(int timeInMilliseconds) const;
int mCurrentMediaItemLength = 0;
int mCurrentTime = 0;
double mCurrentMediaItemProgress = 0;
QString mMediaTitle = QString("");
NavigationItemModel* mCurrentItem = nullptr; NavigationItemModel* mCurrentItem = nullptr;
}; };

View file

@ -1,4 +1,5 @@
#include "NavigationController.h" #include "NavigationController.h"
#include <controllers/SettingsHandler.h>
#include <QDir> #include <QDir>
#include <QDebug> #include <QDebug>
@ -75,18 +76,18 @@ bool NavigationController::checkContent(const QString &path)
{ {
bool valid = false; bool valid = false;
auto dir =QDir(path); auto dir =QDir(path);
// directory must either contain subdirectories or media files
auto subDirsNames = dir.entryList(QDir::AllDirs); auto subDirsNames = dir.entryList(QDir::AllDirs);
if(subDirsNames.length() > 0) { if(subDirsNames.length() > 0) {
valid = true; valid = true;
} else { } else {
dir.setNameFilters(SettingsHandler::getAudioFileNameFilters());
auto fileNames = dir.entryList(QDir::Files); auto fileNames = dir.entryList(QDir::Files);
int numAudio = 0; int numAudio = 0;
for(auto file:fileNames){ for(auto file:fileNames){
if(file.endsWith(".flac") || file.endsWith(".mp3")){
numAudio++; numAudio++;
} }
} valid = numAudio > 0;
if(numAudio > 0) valid = true;
} }
return valid; return valid;
} }

View file

@ -17,6 +17,12 @@ public:
static SettingsHandler* createSettingsHandlerAndFillWithDefaultsIfMissing(QSettings* settings); static SettingsHandler* createSettingsHandlerAndFillWithDefaultsIfMissing(QSettings* settings);
/**
* @brief Provides a name filter for QDir that can be used to filter all audio files with valid formats.
* @return name filter for QDir
*/
static QStringList getAudioFileNameFilters() {return {"*.mp3", "*.flac"};}
inline void setSettings(QSettings* settings) { mSettings = settings;} inline void setSettings(QSettings* settings) { mSettings = settings;}
inline QSettings* getSettings() const { return mSettings; } inline QSettings* getSettings() const { return mSettings; }
void fillWithDefaultIfMissing(); void fillWithDefaultIfMissing();