QT + Comment appeler un emplacement à partir du code C ++ personnalisé exécuté dans un thread différent
Je suis nouveau sur QT et je fais un certain apprentissage.
Je voudrais déclencher une fente pour modifier une interface graphique widget à partir d'un C++ fil(Actuellement un Qthread).
Malheureusement je reçois un: ASSERTION failed: Q_ASSERT(qApp && qApp->thread() == QThread::currentThread());
voici un code:
(PRINCIPAL + classe Thread)
class mythread : public QThread
{
public:
mythread(mywindow* win){this->w = win;};
mywindow* w;
void run()
{
w->ui.textEdit->append("Hello"); //<--ASSERT FAIL
//I have also try to call a slots within mywindow which also fail.
};
};
int main(int argc, char *argv[])
{
QApplication* a = new QApplication(argc, argv);
mywindow* w = new mywindow();
w->show();
mythread* thr = new mythread(w);
thr->start();
return a->exec();
}
Fenêtre:
class mywindow : public QMainWindow
{
Q_OBJECT
public:
mywindow (QWidget *parent = 0, Qt::WFlags flags = 0);
~mywindow ();
Ui::mywindow ui;
private:
public slots:
void newLog(QString &log);
};
Donc je suis curieux de savoir comment mettre à jour la partie interface utilisateur par le code dans un thread différent.
Merci pour votre aide
source d'informationauteur | 2009-07-17
Vous devez vous connecter pour publier un commentaire.
En plus de stribika réponseje trouve souvent qu'il est plus facile d'utiliser un signal/slot de connexion. Vous pouvez spécifier qu'il devrait être en file d'attente de connexion lorsque vous vous connectez, pour éviter des problèmes avec le fil de signaux dans le contexte de l'objet propriétaire.
stribika eu presque droite:
cjhuitt du droit, si: Vous voulez généralement à déclarer un signal sur le fil et de le connecter à la
append()
fente, pour obtenir l'objet de gestion de durée de vie pour le libre (le bien, pour le prix d'un mineur de l'interface changement). Sur un passage, l'argument supplémentaire:de cjhuitt la réponse n'est pas plus nécessaire (il a été, dans l'intervalle Qt <= 4.1), depuis
connect()
par défautQt::AutoConnection
qui maintenant (Qt >= 4.2) fait la bonne chose et commute entre l'attente et la connexion directe de mode basé surQThread::currentThread()
et le fil de l'affinité du récepteurQObject
à émettent temps (au lieu de l'expéditeur et du récepteur d'affinité au moment de la connexion).Vous devez utiliser QMetaObject::invokeMethod. Par exemple:
(Le code ci-dessus vient d'ici: http://www.qtforum.org/article/26801/qt4-threads-and-widgets.html)
Je ne pense pas que vous êtes autorisé à appeler directement les choses que les résultats de la peinture des événements de toute
les autres threads que le thread principal. Ce sera le résultat d'un crash.
Je pense que vous pouvez utiliser la boucle d'événements d'appeler les choses de manière asynchrone pour que le thread gui ramasse et fait la mise à jour du thread principal, qui est ce que cjhuitt suggère.
Que si notre fil d'affinité dit GUI, mais nous ne sommes pas dans le thread GUI, ni dans un QThread?
Ce que je veux dire, c'est un non-Qt (notification) thread appelle un QObject de l'interface de la méthode, dans laquelle nous émettons un AutoConnected signal. Le Fil de l'affinité de la QObject est thread Principal, mais la procédure est en fait appelé à partir d'un autre thread. Ce que l'intervalle Qt faire ici?