IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Multithreading Discussion :

QThread et wait dialog


Sujet :

Multithreading

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Futur Membre du Club
    Inscrit en
    Juin 2008
    Messages
    5
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 5
    Par défaut QThread et wait dialog
    Bonjour,

    Je rencontre en ce moment des problèmes de développement relatifs au multithreading sous Qt 4.3.4, j'aimerais avoir votre avis sur la question:

    Il s'agit de créer une wait dialog au sein d'une application. Celle ci doit faire défiler une suite d'image PNG en actualisant un timer au fil du temps, tandis qu'une opération lourde se produit (chargement de données, export).
    J'ai donc créé une classe dérivé de QThread qui envoit un signal au GUI thread pour l'actualiser. Le problème est que le slot du GUI thread n'est appelé qu'à la fin de l'opération. En utilisant Qt:irectConnection pour connecter directement le thread au GUI thread, j'ai pour résultat que la méthode d'update qui actualise la wait dialog est alors appelé depuis ce thread (au lieu du GUI thread comme c'était le cas avec Qt::AutoConnection par default), ce qui provoque un crash.

    Je précise que lorsque j'utilise Qt::AutoConnection par défault pour le connect, j'arrive à afficher la suite de png lorsque le GUI thread est libre.

    La question est finalement comment libérer le GUI thread des opérations qu'il est en train de réaliser à une fréquence donnée pour lui faire réaliser d'autres opérations. Avec un timer dans le GUI thread le résultat est le même.

    En parcourant le forum, je n'ai pas trouvé de solutions à ce problème.

    Si vous avez des pistes, merci de m'éclaircir

    Cdt,

    Coco

  2. #2
    yan
    yan est déconnecté
    Rédacteur
    Avatar de yan
    Homme Profil pro
    Ingénieur expert
    Inscrit en
    Mars 2004
    Messages
    10 035
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations professionnelles :
    Activité : Ingénieur expert
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Mars 2004
    Messages : 10 035
    Par défaut
    Salut
    En utilisant Qt:irectConnection pour connecter directement le thread au GUI thread, j'ai pour résultat que la méthode d'update qui actualise la wait dialog est alors appelé depuis ce thread (au lieu du GUI thread comme c'était le cas avec Qt::AutoConnection par default), ce qui provoque un crash.
    Ce doit même être un assert non?

    Pourquoi as tu besoin d'un thread??? un QTimer suffirait largement

  3. #3
    Futur Membre du Club
    Inscrit en
    Juin 2008
    Messages
    5
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 5
    Par défaut Oups
    "Warning: Slots that generate window system events or use window system functions must not be connected to a signal that is emitted from a thread that is not the GUI thread."

    Sans résoudre quoi que soit, ça m'indique que ma manière de procéder était crado

  4. #4
    yan
    yan est déconnecté
    Rédacteur
    Avatar de yan
    Homme Profil pro
    Ingénieur expert
    Inscrit en
    Mars 2004
    Messages
    10 035
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations professionnelles :
    Activité : Ingénieur expert
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Mars 2004
    Messages : 10 035
    Par défaut
    EN gros, JAMAIS DE TRAITEMENT GUI DANS UNE THREAD.
    Hors que tu oblige une connection direct, le slot sera directement appelé par le emit de la thread, qui va l'executer.

  5. #5
    Futur Membre du Club
    Inscrit en
    Juin 2008
    Messages
    5
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 5
    Par défaut
    Merci pour ces informations

    Effectivement, c'était un assert

    J'ai essayé le QTimer, qui je le pensais, aurait du suffir. C'est parce qu'il ne fonctionnait pas que j'en suis venu à des solutions moins orthodoxes...

    Voilà le code que j'avais écrit à la base pour ma wait dialog:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    WaitDialog::WaitDialog(QWidget* pParent, Qt::WindowFlags pFlag)
    :QDialog(pParent)
    ,mFrame(0)
    {
    	setWindowFlags(pFlag);
    	mUi.setupUi(this);
    	mStartTime.start();
    	QTimer::singleShot(100, this, SLOT(updateInfos()));
    }
     
    void WaitDialog::updateInfos()
    {
    	// Set current pixmap 
    	if
    		(mFrame == mWaitDialogPixmaps->size())
    	{
    		mFrame = 0;
    	}
    	mUi.label->setPixmap((*mWaitDialogPixmaps)[mFrame++]);
     
    	// Set elapsed time.
    	QTime lElapsed(0, 0, 0, 0);
    	lElapsed = lElapsed.addMSecs(mStartTime.elapsed());
    	mUi.mLElapsedTime->setText(lElapsed.toString("HH:mm:ss"));
    	QApplication::processEvents();
    	QTimer::singleShot(100, this, SLOT(updateInfos()));
    }
     
    void VA_WaitDialog::showInstance()	
    {
    	if
    		(!msInstance)
    	{
    		msInstance = new VA_WaitDialog();
    		msInstance->show();
    	}
    }
     
    void VA_WaitDialog::hideInstance()
    {
    	  if
                  (msInstance)
              delete msInstance;
    }
    Celle ci était utilisée dans ma main window de cette manière:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    VA_WaitDialog::showInstance();
    // TRAITEMENT LOURD
    // ...
    void VA_WaitDialog::hideInstance();
    On voyait une fenêtre modale grise figée apparaître sans le défilement des png et du ellapsed time qui disparaissait à la fin du traitement.
    Ca aurait du marcher... Je comprends pas.

    Une idée?

  6. #6
    Futur Membre du Club
    Inscrit en
    Juin 2008
    Messages
    5
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 5
    Par défaut
    Les deux premières méthodes appartiennent à VA_WaitDialog
    C'est une erreur de copier coller

  7. #7
    yan
    yan est déconnecté
    Rédacteur
    Avatar de yan
    Homme Profil pro
    Ingénieur expert
    Inscrit en
    Mars 2004
    Messages
    10 035
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations professionnelles :
    Activité : Ingénieur expert
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Mars 2004
    Messages : 10 035
    Par défaut
    C'est grisé car la thread principale effectue ta tache lourd. Elle ne peut donc effectuer autre chose.
    Une methode pas terrible est d'appeler qApp->processEvents () pendant ton gros traitement.

    Et un manière bien meilleur utiliser une thread ce qui t'as voulue faire, mais faut décorélé l'ihm du traitement.

    Comment se déroule l'exécution du traitement?

Discussions similaires

  1. Utilisation de la fonction wait() de QThread
    Par Invité dans le forum Débuter
    Réponses: 4
    Dernier message: 22/05/2010, 14h05
  2. Waiting a QThread
    Par uriotcea dans le forum Multithreading
    Réponses: 3
    Dernier message: 23/05/2008, 15h34
  3. Pop-up d'une dialog box a partir d'un bouton
    Par bobbyjack dans le forum MFC
    Réponses: 21
    Dernier message: 13/09/2005, 15h32
  4. [awt][dialog]
    Par Ultra-FX dans le forum Agents de placement/Fenêtres
    Réponses: 4
    Dernier message: 06/11/2002, 16h22
  5. Quoi ?! Common Dialog fait crasher DirectDraw ?
    Par Magus (Dave) dans le forum DirectX
    Réponses: 4
    Dernier message: 21/10/2002, 19h01

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo