163 lines
6.0 KiB
C++
Executable File
163 lines
6.0 KiB
C++
Executable File
/**
|
|
* @RDE_HEADER@
|
|
* State Machine handler for Exercise Control
|
|
* $Id$
|
|
* $HeadURL$
|
|
* $Author$
|
|
*/
|
|
|
|
#include "exercise_state_machine.h"
|
|
#include "exercise_state_manager.h"
|
|
#include "exercise_state_base.h"
|
|
|
|
#include "object_exercise.h"
|
|
#include "settings.h"
|
|
#include "logger.h"
|
|
|
|
namespace ExerciseManagement
|
|
{
|
|
|
|
ExerciseStateMachine::ExerciseStateMachine(ObjectExercise* objExe, QObject *parent)
|
|
: QObject(parent)
|
|
, m_stateManager(new ExerciseStateManager(objExe, this))
|
|
, m_stateMachine(new QStateMachine(this))
|
|
, m_exercise(objExe)
|
|
, m_logger(getLogger("ExerciseStateMachine"))
|
|
{
|
|
qRegisterMetaType<ExerciseManagement::ExerciseState>("ExerciseManagement::ExerciseState");
|
|
|
|
m_exerciseStates.insert(ExerciseState::Unknown, new Unknown(m_exercise));
|
|
m_exerciseStates.insert(ExerciseState::Created, new Creation(m_exercise));
|
|
m_exerciseStates.insert(ExerciseState::Started, new Start(m_exercise));
|
|
m_exerciseStates.insert(ExerciseState::Stopped, new Stop(m_exercise));
|
|
m_exerciseStates.insert(ExerciseState::Paused, new Pause(m_exercise));
|
|
m_exerciseStates.insert(ExerciseState::Terminated, new Terminate(m_exercise));
|
|
|
|
// Define transitions from one state to the other
|
|
// ----------------------------------------------------------------------------------------------------------
|
|
// ** Unknown
|
|
// => Created
|
|
m_exerciseStates[ExerciseState::Unknown]->addTransition(m_stateManager, &ExerciseStateManager::stateCreated,
|
|
m_exerciseStates[ExerciseState::Created]);
|
|
// ** Created
|
|
// => Started
|
|
m_exerciseStates[ExerciseState::Created]->addTransition(m_stateManager, &ExerciseStateManager::stateStarted,
|
|
m_exerciseStates[ExerciseState::Started]);
|
|
// => Terminated
|
|
m_exerciseStates[ExerciseState::Created]->addTransition(m_stateManager, &ExerciseStateManager::stateTerminated,
|
|
m_exerciseStates[ExerciseState::Terminated]);
|
|
// ** Started
|
|
// => Paused
|
|
m_exerciseStates[ExerciseState::Started]->addTransition(m_stateManager, &ExerciseStateManager::statePaused,
|
|
m_exerciseStates[ExerciseState::Paused]);
|
|
// => Stopped
|
|
m_exerciseStates[ExerciseState::Started]->addTransition(m_stateManager, &ExerciseStateManager::stateStopped,
|
|
m_exerciseStates[ExerciseState::Stopped]);
|
|
// ** Paused
|
|
// => Stopped
|
|
m_exerciseStates[ExerciseState::Paused]->addTransition(m_stateManager, &ExerciseStateManager::stateStopped,
|
|
m_exerciseStates[ExerciseState::Stopped]);
|
|
// => Resumed (= Started)
|
|
m_exerciseStates[ExerciseState::Paused]->addTransition(m_stateManager, &ExerciseStateManager::stateStarted,
|
|
m_exerciseStates[ExerciseState::Started]);
|
|
|
|
// ** Stopped
|
|
// => Terminated
|
|
m_exerciseStates[ExerciseState::Stopped]->addTransition(m_stateManager, &ExerciseStateManager::stateTerminated,
|
|
m_exerciseStates[ExerciseState::Terminated]);
|
|
|
|
// ** Terminated
|
|
// => Stopped
|
|
if ( ExerciseManagement::Settings::enableExerciseTerminatedToStopped())
|
|
{
|
|
m_exerciseStates[ExerciseState::Terminated]->addTransition(m_stateManager, &ExerciseStateManager::stateStopped,
|
|
m_exerciseStates[ExerciseState::Stopped]);
|
|
}
|
|
|
|
// ----------------------------------------------------------------------------------------------------------
|
|
|
|
//States zur StateMachine hinzufügen
|
|
for (ExerciseStateBase *state : qAsConst(m_exerciseStates))
|
|
{
|
|
DEBUG_LOG(m_logger) << "Ex " << exerciseId() << ": state: " << state->exerciseState();
|
|
m_stateMachine->addState(state);
|
|
connect(state, &ExerciseStateBase::entered, this, &ExerciseStateMachine::onEnteredState);
|
|
}
|
|
|
|
DEBUG_LOG(m_logger) << "Ex " << exerciseId() << ": Constructor ExerciseStateMachine: size m_exerciseStates = " << m_exerciseStates.size();
|
|
}
|
|
|
|
ExerciseStateMachine::~ExerciseStateMachine()
|
|
{
|
|
qDeleteAll(m_exerciseStates);
|
|
delete m_stateManager;
|
|
delete m_stateMachine;
|
|
}
|
|
|
|
bool ExerciseStateMachine::init()
|
|
{
|
|
if (m_stateMachine->isRunning())
|
|
return false;
|
|
|
|
DEBUG_LOG(m_logger) << "Ex " << exerciseId() << ": Init ExerciseStateMachine ";
|
|
// initialise current exerciseState
|
|
ExerciseStateBase *currentExerciseState = getStateFromId(m_exercise->exerciseState());
|
|
|
|
DEBUG_LOG(m_logger) << "Ex " << exerciseId() << ": State = "
|
|
<< ExerciseStateManager::toString(m_exercise->exerciseState());
|
|
|
|
m_stateMachine->setInitialState(currentExerciseState);
|
|
m_stateMachine->start();
|
|
|
|
m_stateManager->setInitial(m_exercise->exerciseState());
|
|
|
|
DEBUG_LOG(m_logger) << "Ex " << exerciseId() << ": ==> Done Init ExerciseStateMachine ";
|
|
|
|
return true;
|
|
}
|
|
|
|
ExerciseManagement::ExerciseState ExerciseStateMachine::getCurrentState()
|
|
{
|
|
return m_exercise->exerciseState();
|
|
}
|
|
|
|
bool ExerciseStateMachine::switchToState(ExerciseState newExerciseState)
|
|
{
|
|
return m_stateManager->triggerSwitchState(newExerciseState);
|
|
}
|
|
|
|
void ExerciseStateMachine::onEnteredState()
|
|
{
|
|
DEBUG_LOG(m_logger) << "Ex " << exerciseId() << ": ExerciseStateMachine - onEnteredState";
|
|
|
|
ExerciseStateBase *s = qobject_cast<ExerciseStateBase*>(sender());
|
|
if (!s)
|
|
return;
|
|
|
|
DEBUG_LOG(m_logger) << "Ex " << exerciseId() << ": ExerciseStateBase : " << s->exerciseState();
|
|
|
|
m_stateManager->setCurrent(s->exerciseState());
|
|
|
|
emit exerciseStateChanged(s->exerciseState());
|
|
}
|
|
|
|
//----------------------------------------
|
|
|
|
ExerciseStateBase* ExerciseStateMachine::getStateFromId(ExerciseState exerciseState)
|
|
{
|
|
ExerciseStateBase *s = m_exerciseStates.value(exerciseState);
|
|
if (!s)
|
|
s = m_exerciseStates.value(ExerciseState::Unknown);
|
|
return s;
|
|
}
|
|
|
|
//----------------------------------------
|
|
|
|
int ExerciseStateMachine::exerciseId() const
|
|
{
|
|
return m_exercise ? m_exercise->id() : -1;
|
|
}
|
|
|
|
|
|
} // namespace ExerciseManagement
|