Maison >développement back-end >C++ >Comment mettre à jour en toute sécurité une fenêtre principale de Qt à partir d'un autre thread ?

Comment mettre à jour en toute sécurité une fenêtre principale de Qt à partir d'un autre thread ?

DDD
DDDoriginal
2024-10-26 13:52:31835parcourir

How to Safely Update a Qt Main Window from a Different Thread?

Qt - Mise à jour de la fenêtre principale à partir d'un thread différent

Introduction :

Les applications Qt multithread peuvent rencontrer des situations où des processus en cours d'exécution dans la fenêtre principale doivent être mis à jour à partir d’un thread secondaire. Cependant, il n’est pas conseillé d’accéder directement à l’interface utilisateur de la fenêtre principale à partir d’un autre thread. Cet article explique comment mettre à jour en toute sécurité la fenêtre principale à partir d'un autre thread en exploitant les signaux et les emplacements des threads.

Énoncé du problème :

Dans le code fourni, la classe mythread tente d'ajouter un QLabel au horizontalLayout_4 de la fenêtre principale à partir d'un thread séparé. Cependant, la ligne ana->ui->horizontalLayout_4->addWidget(label) ne parvient pas à se compiler.

Solution :

Pour résoudre ce problème, un Une approche plus appropriée consiste à placer les modifications de l'interface utilisateur dans un emplacement de la fenêtre principale et à connecter un signal de thread à cet emplacement. Cela garantit que la fonctionnalité de l'interface graphique reste dans le thread principal et peut être signalée à partir d'autres threads.

Voici un exemple :

Interface utilisateur principale (MainUI.h et MainUI.cpp) :

<code class="cpp">class MainUI : public QWidget
{
    Q_OBJECT

public:
    explicit MainUI(QWidget *parent = 0) : QWidget(parent)
    {
        // Initialize layout and thread
        layout = new QHBoxLayout(this);
        setLayout(layout);

        QThread *thread = new QThread(this);
        GUIUpdater *updater = new GUIUpdater();
        updater->moveToThread(thread);

        // Connect thread signal to main window slot
        connect(updater, SIGNAL(requestNewLabel(QString)), this, SLOT(createLabel(QString)));
        connect(thread, SIGNAL(destroyed()), updater, SLOT(deleteLater()));

        // Initiate label creation from thread
        updater->newLabel("path/to/image.png");
    }

public slots:
    void createLabel(const QString &imgSource)
    {
        // Create and add label to layout in main thread
        QPixmap i1(imgSource);
        QLabel *label = new QLabel(this);
        label->setPixmap(i1);
        layout->addWidget(label);
    }

private:
    QHBoxLayout *layout;
};</code>

Objet Worker (GUIUpdater.h et GUIUpdater.cpp) :

<code class="cpp">class GUIUpdater : public QObject
{
    Q_OBJECT

public:
    explicit GUIUpdater(QObject *parent = 0) : QObject(parent) {}

    void newLabel(const QString &image)
    {
        // Emit signal to main window
        emit requestNewLabel(image);
    }

signals:
    void requestNewLabel(const QString &);
};</code>

Dans cet exemple :

  • MainUI est la fenêtre principale qui reçoit les mises à jour de l'interface utilisateur.
  • GUIUpdater est un objet de travail créé dans un thread séparé.
  • Lorsque GUIUpdater::newLabel est appelé à partir du thread séparé, il émet la requêteNewLabel. signal.
  • L'emplacement MainUI.createLabel est connecté au signal requestNewLabel, permettant aux mises à jour de l'interface graphique d'être effectuées en toute sécurité dans le thread principal.

En utilisant cette approche, des modifications de l'interface utilisateur sont effectuées dans le thread principal tout en lançant le processus à partir d’un thread séparé. Cela garantit la sécurité des threads et évite les problèmes potentiels lors de l'accès à l'interface utilisateur de la fenêtre principale à partir de différents threads.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn