QObject (QPlainTextEdit) & Multithreading questions
Im en train d'essayer d'apprendre de Réseautage avec Python asyncore et pyqt4.
J'ai codé un petit serveur, qui, fondamentalement, est à l'écoute sur un port, et renvoie tous les messages qu'il reçoit à l'expéditeur.
Depuis deux qts QApplication.exec_()
et asyncore.loop()
sont des fonctions qui ne retournent jamais je ne pourrais pas commencer dans un thread, donc je l'ai regardé asyncore.loop()
dans un autre fil de démon.
Chaque fois que mon serveur de classe (dérivé de asyncore.dispatcher
) établit ou des gouttes d'une connexion, ou envoie/reçoit un message, il appelle les méthodes de ma classe de fenêtre (dérivé de QtGui.QMainWindow
), qui affiche les informations dans un QPlainTextEdit
.
Mais le texte n'est pas visible, sauf si vous définissez le texte avec la souris.
Python console affiche le msg d'erreur suivant:
QObject::connect: Cannot queue arguments of type 'QTextBlock'
(Make sure 'QTextBlock' is registered using qRegisterMetaType().)
QObject::connect: Cannot queue arguments of type 'QTextCursor'
(Make sure 'QTextCursor' is registered using qRegisterMetaType().)
J'ai lu sur certains forum, que ce soit causé par l'appel de qt-fonctions à partir d'un autre Thread, et que l'utilisation de signaux & fentes au lieu de la plaine d'appel de fonction peut résoudre le problème, mais j'ai essayé de signaux aswell, et j'obtiens toujours cette erreur.
Donc, (si c'est vraiment la cause de mes problèmes) quel est la bonne manière d'appeler les méthodes d'un objet de qt à partir d'un autre thread ?
EDIT pour Plus d'Info:
le asyncore.loop() qui est situé dans l'enfant du fil, et bien ce n'est pas vraiment de blocage, mais seulement lors de l'exécution de asyncore.loop() mon Serveur de classe (asyncore.répartiteur) peut faire du réseautage.
Ainsi, lors de l'exécution de asyncore.loop() les méthodes de ma classe de Serveur SONT appelés par asyncore.loop() (=enfant thread), et dans ces je
essayé d'émettre les signaux de la classe de fenêtre exécute dans le thread principal
EDIT: Semble que je l'ai eu à travailler maintenant, j'ai eu des erreurs dans mon code, tout fonctionne comme prévu avec des signaux de maintenant.
EDIT: petit exemple: http://paste2.org/p/635612 (lien mort)
OriginalL'auteur smerlin | 2010-01-20
Vous devez vous connecter pour publier un commentaire.
Il semble que vous essayez d'accéder à QtGui classes à partir d'un thread autre que le thread principal. Comme dans d'autres kits graphiques (par exemple, Java Swing), ce n'est pas permis. À partir de la Fils et QObjects page web:
Une solution est d'utiliser les signaux et les slots pour la communication entre le thread principal (où les objets GUI live) et votre thread secondaire(s). Fondamentalement, vous émettez des signaux dans un thread qui l'a livré à la QObjects par l'autre thread. La page ci-dessus, a une bonne discussion de ce. En fait, l'ensemble de la section sur Support des threads dans Qt est une bonne lecture.
Un potentiel problème que vous pourriez rencontrer, c'est que, normalement, pour obtenir tous les signaux et les slots de travail de soutien dans les threads, vous devez lancer une boucle d'événement de l'enfant thread à l'aide de
QThread::exec()
(ou le PyQt équivalent), de sorte que les signaux peuvent être livrés à des fentes dans la QObjects qui y vivent. Dans votre cas, il semble que vous faites un appel de blocage àasyncore.loop()
, qui va vous empêcher de faire cela. Mais, si vous avez seulement besoin d'émettre des signaux dans un seul sens (de l'enfant au fil des widgets dans le thread principal), je ne pense pas que vous aurez un problème.J'ai totalement oublié d'essayer QThread... mais comment puis-je utiliser QThreads pour mon Problème ??, depuis QThreads
exec()_
méthode est une méthode de blocage de nouveau, donc je ne peux pas l'exécuter dans le même thread comme mon Serveur de classe. <br/>@e8johan: j'ai eu les mêmes messages d'erreur lorsque je n'ai pas utiliser des signaux ..OriginalL'auteur Rob H