Merge remote-tracking branch 'origin/master'

This commit is contained in:
Dorian Zedler 2020-10-03 21:48:22 +02:00
commit 3c4b6bb0e0
Signed by: dorian
GPG key ID: D3B255CB8BC7CD37
5 changed files with 64 additions and 32 deletions

View file

@ -134,7 +134,7 @@ private slots:
void handleTimerWantsToBeDisabledChange(ScStwTimer* timer, bool wantsToBeDisabled); void handleTimerWantsToBeDisabledChange(ScStwTimer* timer, bool wantsToBeDisabled);
int handleFalseStart(); int handleFalseStart();
bool playSoundsAndStartTimers(); bool playSoundsAndStartTimers();
bool doDelayAndSoundOfCurrentStartState(double *timeOfSoundPlaybackStart = nullptr); ScStwSoundPlayer::PlayResult doDelayAndSoundOfCurrentStartState(double *timeOfSoundPlaybackStart = nullptr);
void technicalIncident(); void technicalIncident();
/** /**

View file

@ -49,6 +49,12 @@ public:
FalseStart = 3 FalseStart = 3
}; };
enum PlayResult {
Success = 0,
Cancelled = -1,
Error = -2
};
private: private:
/*! /*!
* \brief A map containing all sound files * \brief A map containing all sound files
@ -91,16 +97,16 @@ public slots:
* \param action The action to play (0: AtYourMarks, 1:Ready, 2:Start) * \param action The action to play (0: AtYourMarks, 1:Ready, 2:Start)
* \param volume The volume to play at * \param volume The volume to play at
* \param timeOfStop The time the playback actually started (msecs since epoch) * \param timeOfStop The time the playback actually started (msecs since epoch)
* \return true if the playback was successfully started, false otherwise * \return TODO true if the playback was successfully started, false otherwise
*/ */
bool play(StartSound sound, double volume, double *timeOfStart = nullptr); ScStwSoundPlayer::PlayResult play(StartSound sound, double volume, double *timeOfStart = nullptr);
/*! /*!
* \brief Function to wait for the playback to finish * \brief Function to wait for the playback to finish
* \param timeOfStop the point in time when the plyback actually stopped (msecs since epoch) * \param timeOfStop the point in time when the plyback actually stopped (msecs since epoch)
* \return false if there was any error (eg. there was no playback currently), true otherwise * \return false if there was any error (eg. there was no playback currently), true otherwise
*/ */
bool waitForSoundFinish(double *timeOfStop = nullptr); ScStwSoundPlayer::PlayResult waitForSoundFinish(double *timeOfStop = nullptr);
/*! /*!
* \brief Function to cancel the current playback * \brief Function to cancel the current playback

View file

@ -197,6 +197,8 @@ void ScStwRace::technicalIncident() {
foreach(ScStwTimer *timer, this->timers){ foreach(ScStwTimer *timer, this->timers){
timer->cancel(); timer->cancel();
} }
this->soundPlayer->cancel();
this->setState(INCIDENT); this->setState(INCIDENT);
} }
@ -223,8 +225,16 @@ bool ScStwRace::playSoundsAndStartTimers() {
return true; return true;
// The check if all timers are ready has already happened at this point // The check if all timers are ready has already happened at this point
if(!this->doDelayAndSoundOfCurrentStartState()) ScStwSoundPlayer::PlayResult res = this->doDelayAndSoundOfCurrentStartState();
if(res == ScStwSoundPlayer::Error) {
qDebug() << "[ERROR][RACE] error playing at your marks sound";
this->technicalIncident();
return false; return false;
}
else if(res == ScStwSoundPlayer::Cancelled) {
return false;
}
// check if the start was cancelled // check if the start was cancelled
if(!this->isStarting()) if(!this->isStarting())
@ -234,8 +244,6 @@ bool ScStwRace::playSoundsAndStartTimers() {
// do climber readiness tests // do climber readiness tests
// wait until both climbers are ready
// if the automatic ready tone is enabled, wait for the climbers to become ready // if the automatic ready tone is enabled, wait for the climbers to become ready
if(this->competitionMode && this->getSoundEnabledSetting(ScStwSoundPlayer::Ready)) { if(this->competitionMode && this->getSoundEnabledSetting(ScStwSoundPlayer::Ready)) {
@ -290,11 +298,16 @@ bool ScStwRace::playSoundsAndStartTimers() {
qDebug() << "[DEBUG][RACE] Wait finished, starting now!"; qDebug() << "[DEBUG][RACE] Wait finished, starting now!";
// play ready tone // play ready tone
if(!this->soundPlayer->play(ScStwSoundPlayer::Ready, this->getSoundVolume())) { ScStwSoundPlayer::PlayResult res = this->soundPlayer->play(ScStwSoundPlayer::Ready, this->getSoundVolume());
qDebug() << "[ERROR][RACE] Ready sound returned false!";
if(res == ScStwSoundPlayer::Error) {
qDebug() << "[ERROR][RACE] error playing ready sound";
this->technicalIncident(); this->technicalIncident();
return false; return false;
} }
else if(res == ScStwSoundPlayer::Cancelled) {
return false;
}
} }
else if(this->competitionMode) { else if(this->competitionMode) {
// wait for climbers and manual start // wait for climbers and manual start
@ -308,8 +321,14 @@ bool ScStwRace::playSoundsAndStartTimers() {
} while(loopExitCode != LoopManualExit || !this->getIsReadyForNextState()); } while(loopExitCode != LoopManualExit || !this->getIsReadyForNextState());
} }
else { else {
if(!this->doDelayAndSoundOfCurrentStartState()) { ScStwSoundPlayer::PlayResult res = this->doDelayAndSoundOfCurrentStartState();
this->cancel();
if(res == ScStwSoundPlayer::Error) {
qDebug() << "[ERROR][RACE] error playing ready sound";
this->technicalIncident();
return false;
}
else if(res == ScStwSoundPlayer::Cancelled) {
return false; return false;
} }
} }
@ -319,10 +338,16 @@ bool ScStwRace::playSoundsAndStartTimers() {
// play start tone // play start tone
double timeOfSoundPlaybackStart; double timeOfSoundPlaybackStart;
if(!this->doDelayAndSoundOfCurrentStartState(&timeOfSoundPlaybackStart)) { res = this->doDelayAndSoundOfCurrentStartState(&timeOfSoundPlaybackStart);
if(res == ScStwSoundPlayer::Error) {
qDebug() << "[ERROR][RACE] error playing at your marks sound";
this->technicalIncident(); this->technicalIncident();
return false; return false;
} }
else if(res == ScStwSoundPlayer::Cancelled) {
return false;
}
// perform start // perform start
@ -339,7 +364,7 @@ bool ScStwRace::playSoundsAndStartTimers() {
return false; return false;
} }
if(!this->soundPlayer->waitForSoundFinish()) { if(this->soundPlayer->waitForSoundFinish() == ScStwSoundPlayer::Error) {
qDebug() << "[ERROR][RACE] start sound wait error"; qDebug() << "[ERROR][RACE] start sound wait error";
this->technicalIncident(); this->technicalIncident();
return false; return false;
@ -347,7 +372,7 @@ bool ScStwRace::playSoundsAndStartTimers() {
// check if a false start occured // check if a false start occured
if(!this->isStarting()) if(!this->isStarting())
return true; return false;
this->setState(RUNNING); this->setState(RUNNING);
@ -356,7 +381,7 @@ bool ScStwRace::playSoundsAndStartTimers() {
} }
bool ScStwRace::doDelayAndSoundOfCurrentStartState(double *timeOfSoundPlaybackStart) { ScStwSoundPlayer::PlayResult ScStwRace::doDelayAndSoundOfCurrentStartState(double *timeOfSoundPlaybackStart) {
ScStwSoundPlayer::StartSound sound = this->getSoundForState(this->state); ScStwSoundPlayer::StartSound sound = this->getSoundForState(this->state);
if(this->getSoundEnabledSetting(sound)) { if(this->getSoundEnabledSetting(sound)) {
@ -374,18 +399,18 @@ bool ScStwRace::doDelayAndSoundOfCurrentStartState(double *timeOfSoundPlaybackSt
emit this->currentStartDelayChanged(); emit this->currentStartDelayChanged();
if(this->startWaitLoop->exec() == LoopCancelExit) if(this->startWaitLoop->exec() == LoopCancelExit)
return false; return ScStwSoundPlayer::Cancelled;
} }
} }
if(!this->isStarting()) if(!this->isStarting())
return false; return ScStwSoundPlayer::Error;
if(!this->soundPlayer->play(sound, this->getSoundVolume(), timeOfSoundPlaybackStart))
return false; return this->soundPlayer->play(sound, this->getSoundVolume(), timeOfSoundPlaybackStart);
} }
return true; return ScStwSoundPlayer::Success;
} }
void ScStwRace::setState(RaceState newState) { void ScStwRace::setState(RaceState newState) {

View file

@ -35,9 +35,11 @@ ScStwSoundPlayer::ScStwSoundPlayer(QObject *parent) : QObject(parent)
connect(this->soundEffect, &QSoundEffect::playingChanged, this->waitLoop, &QEventLoop::quit); connect(this->soundEffect, &QSoundEffect::playingChanged, this->waitLoop, &QEventLoop::quit);
} }
bool ScStwSoundPlayer::play(ScStwSoundPlayer::StartSound sound, double volume, double *timeOfStart) { ScStwSoundPlayer::PlayResult ScStwSoundPlayer::play(ScStwSoundPlayer::StartSound sound, double volume, double *timeOfStart) {
if(!this->soundFiles.contains(sound)) if(!this->soundFiles.contains(sound)) {
return false; qDebug() << "[ERROR][SoundPlayer] Sound file was not found for sound" << sound;
return ScStwSoundPlayer::Error;
}
// stop playback // stop playback
if(this->soundEffect->isPlaying()) if(this->soundEffect->isPlaying())
@ -55,6 +57,7 @@ bool ScStwSoundPlayer::play(ScStwSoundPlayer::StartSound sound, double volume, d
// wait for the effect to load // wait for the effect to load
QEventLoop loop; QEventLoop loop;
while(this->soundEffect->status() != QSoundEffect::Ready) { while(this->soundEffect->status() != QSoundEffect::Ready) {
qDebug() << "[DEBUG][Sound] Sound is not ready yet, status is: " << this->soundEffect->status();
QObject::connect(this->soundEffect, &QSoundEffect::statusChanged, &loop, &QEventLoop::quit); QObject::connect(this->soundEffect, &QSoundEffect::statusChanged, &loop, &QEventLoop::quit);
loop.exec(); loop.exec();
} }
@ -76,7 +79,7 @@ bool ScStwSoundPlayer::play(ScStwSoundPlayer::StartSound sound, double volume, d
if(sound < Start) if(sound < Start)
return this->waitForSoundFinish(); return this->waitForSoundFinish();
return true; return ScStwSoundPlayer::Success;
} }
bool ScStwSoundPlayer::cancel() { bool ScStwSoundPlayer::cancel() {
@ -85,17 +88,18 @@ bool ScStwSoundPlayer::cancel() {
// stop playback // stop playback
this->soundEffect->stop(); this->soundEffect->stop();
this->waitLoop->quit(); this->waitLoop->exit(-1);
return true; return true;
} }
bool ScStwSoundPlayer::waitForSoundFinish(double *timeOfStop) { ScStwSoundPlayer::PlayResult ScStwSoundPlayer::waitForSoundFinish(double *timeOfStop) {
if(!this->soundEffect->isPlaying()) if(!this->soundEffect->isPlaying())
return false; return ScStwSoundPlayer::Error;
// wait until the audio output reports the sound is over // wait until the audio output reports the sound is over
waitLoop->exec(); if(waitLoop->exec() == -1)
return ScStwSoundPlayer::Cancelled;
// wait until the sound is actually over // wait until the sound is actually over
// the timeOffset is the buffer time before the audio started! // the timeOffset is the buffer time before the audio started!
@ -113,7 +117,7 @@ bool ScStwSoundPlayer::waitForSoundFinish(double *timeOfStop) {
*timeOfStop = QDateTime::currentMSecsSinceEpoch() - latency; *timeOfStop = QDateTime::currentMSecsSinceEpoch() - latency;
} }
return true; return ScStwSoundPlayer::Success;
} }
bool ScStwSoundPlayer::isPlaying() { bool ScStwSoundPlayer::isPlaying() {

View file

@ -217,9 +217,6 @@ QString ScStwTimer::getLetter() {
} }
QString ScStwTimer::getText() { QString ScStwTimer::getText() {
qDebug() << "getting text: start time: " << this->startTime << " state: " << this->state;
QString newText = ""; QString newText = "";
int newTime = 0; int newTime = 0;
switch (this->state) { switch (this->state) {