私がやりたかったのは、Qt ステート マシンを構築することです。問題は、自分のトランジションをトリガーできないことでした (自分のイベントは言うまでもなく)。与えられた答えは良いですが、コードが乱雑になります。QT トランジションを使用できないのに QT ステート マシンを使用する必要があるのはなぜですか? 上記の最初の問題は、新しいプロジェクトを作成すると解決されます。QT クリエーターは非常に面倒です。しかし、ここで私の解決策が他の人に役立つかもしれません。
最初に私の状態:
class ServerState : public QState
{
Q_OBJECT
public:
ServerState(QPushButton * pushButton);
~ServerState();
public slots:
void buttonWasClicked();
protected:
void onEntry(QEvent *e);
void onExit(QEvent *e);
private:
QPushButton * pushButton;
};
通常ですが、スロットを追加したことがわかります。このスロットにより、ボトム信号またはウィジェット マウス プレス信号を接続できます。
このような:
QStateMachine *machine = new QStateMachine(this);
ServerState *s1 = new ServerState(connectButton);
connect(connectButton, SIGNAL(clicked()), s1, SLOT(buttonWasClicked()));
machine->addState(s1);
s1->addTransition(connectTransition);
私がする必要があるのは、次のような宣言されたイベントを発生させることだけです:
#define RegisterToServerEventIndex User+5
class ConnectToServerEvent : public QEvent
{
public:
ConnectToServerEvent() : QEvent(QEvent::Type(QEvent::ConnectToServerEventIndex))
{}
};
スロットが呼び出されたとき:
void ServerState::buttonWasClicked()
{
this->machine()->postEvent(new ConnectToServerEvent());
qDebug("ServerState::buttonWasClicked");
}
QT ステート マシンは、すべての Transitions を呼び出し、この状態にリンクします。
ConnectToServerTransition::ConnectToServerTransition(QPushButton * pushButtonB,ServerSkeleton* serverSkeleton)
{
this->pushButtonB = pushButtonB;
this->pushButtonB->hide();
this->serverSkeleton = serverSkeleton;
qDebug("ConnectToServerTransition::ConnectToServerTransition");
}
bool ConnectToServerTransition::eventTest(QEvent *e)
{
return (e->type() == QEvent::ConnectToServerEventIndex);
}
void ConnectToServerTransition::onTransition(QEvent *e)
{
if (true == this->serverSkeleton->initalisieren())
{
this->pushButtonB->show();
}else{
qDebug("Conection to Server faild");
}
emit kill();
return;
}
あえて投稿するほど素晴らしいものは何ですか?まず、Qt SM をウィジェットにリンクして、マウス プレス イベントまたはその他の何かが呼び出され、生データを後でプログラムで必要なレベルに処理できます。あとは、シグナルを発行するだけです。
void Widget::mousePressEvent(QMouseEvent *event){
Coordinates current;
current.line = 0;
current.row = A;
current.row = (Row) (event->x() / 30); // 30 = breite von einen Feld
current.line = event->y() / 30; // 30 = länge von einen Feld
emit this->clicked(current);
return;
}
次に、この強化された情報 (現在) が、作業を行う正しいトランジションを呼び出すことを選択した状態のスロットに渡されます。必要に応じて、さらにトランジションをリンクできます。
しかし、最も重要なのは、トランジションを再プログラムする必要がないことです。これは、私が本当に嫌いだと思います。
助けてくれてありがとう、私はそれを一人ではできませんでした。