Остановка QStateMachine с безусловными переходами - PullRequest
0 голосов
/ 17 октября 2018

Я пытаюсь смоделировать процесс с помощью QStateMachine, который я могу прервать, используя какой-то сигнал «стоп».Для целей тестирования я строю этот простой StateMachine:

StateMachineWrapper::StateMachineWrapper(QObject *parent) : QObject(parent)
{
    sm = new QStateMachine(this);

    QState *running = new QState(sm);
    QState *stopped = new QState(sm);

    QState* stateA = new QState(running);
    QState* stateB = new QState(running);
    QState* stateC = new QState(running);

    stateA->addTransition(stateB);
    stateB->addTransition(stateC);
    stateC->addTransition(stateA);
    running->addTransition(this, &StateMachineWrapper::stopSM, stopped);

    connect(stateA, &QState::entered, this, &StateMachineWrapper::onA);
    connect(stateB, &QState::entered, this, &StateMachineWrapper::onB);
    connect(stateC, &QState::entered, this, &StateMachineWrapper::onC);
    connect(stopped, &QState::entered, this, &StateMachineWrapper::onStopped);

    sm->setInitialState(running);
    running->setInitialState(stateA);
}

void StateMachineWrapper::onA()
{
    qDebug() << "State A";
}
void StateMachineWrapper::onB()
{
    qDebug() << "State B";
}
void StateMachineWrapper::onC()
{
    qDebug() << "State C";
}

void StateMachineWrapper::onStopped()
{
    qDebug() << "State Stopped";
}

void StateMachineWrapper::onStartSM()
{
    sm->start();
}

void StateMachineWrapper::onStopSM()
{
    qDebug() << "Trying to Stop SM";
    emit stopSM();
}

В основном StateMachine имеет цикл, состоящий из трех состояний A, B и C. Они вложены в родительский «Running» -QState.В реальных приложениях это может быть какой-то цикл управления или просто процесс, содержащий много состояний.

Я хочу иметь возможность остановить этот процесс с помощью сигнала.Чтобы добиться этого, я создал состояние «Stopped» с переходом, который должен срабатывать для определенного сигнала (здесь: stopSM).

Однако это не работает, потому что QStateMachine, похоже, не возвращается в EventLoop IУгадай.Я знаю, что мог бы достичь этого, если бы я создал событие для каждого существующего перехода в этом StateMachine и не использовал бы безусловные переходы.Но это также означало бы большие накладные расходы, если мой StateMachine состоит из> 100 состояний.

Есть ли способ заставить мой StateMachine реагировать на внешние сигналы, такие как «стоп-сигнал» в приведенном выше примере?

...