web-dev-qa-db-fra.com

Python: fenêtre contextuelle PyQt

J'ai donc créé mon interface graphique avec Qt pour mon Python. Je suis maintenant arrivé à une situation où, après avoir appuyé sur un bouton, le report approprié est exécuté, nous effectuons quelques tâches puis Je dois ouvrir une fenêtre distincte contenant une ou deux choses. Mais je n'arrive pas à comprendre comment créer cette nouvelle fenêtre séparée. Quelqu'un pourrait-il me donner un exemple de création d'une fenêtre?

22
Morphine

Une erreur courante qui peut vous rendre fou est d'oublier de stocker le handle de la fenêtre contextuelle que vous créez dans une variable python qui restera active (par exemple dans un membre de données de la fenêtre principale).

Ce qui suit est un programme simple qui crée une fenêtre principale avec un bouton où appuyer sur le bouton ouvre une fenêtre contextuelle

#!/usr/bin/env python
#-*- coding: utf-8 -*-

import sys
from PyQt4.Qt import *

class MyPopup(QWidget):
    def __init__(self):
        QWidget.__init__(self)

    def paintEvent(self, e):
        dc = QPainter(self)
        dc.drawLine(0, 0, 100, 100)
        dc.drawLine(100, 0, 0, 100)

class MainWindow(QMainWindow):
    def __init__(self, *args):
        QMainWindow.__init__(self, *args)
        self.cw = QWidget(self)
        self.setCentralWidget(self.cw)
        self.btn1 = QPushButton("Click me", self.cw)
        self.btn1.setGeometry(QRect(0, 0, 100, 30))
        self.connect(self.btn1, SIGNAL("clicked()"), self.doit)
        self.w = None

    def doit(self):
        print "Opening a new popup window..."
        self.w = MyPopup()
        self.w.setGeometry(QRect(100, 100, 400, 200))
        self.w.show()

class App(QApplication):
    def __init__(self, *args):
        QApplication.__init__(self, *args)
        self.main = MainWindow()
        self.connect(self, SIGNAL("lastWindowClosed()"), self.byebye )
        self.main.show()

    def byebye( self ):
        self.exit(0)

def main(args):
    global app
    app = App(args)
    app.exec_()

if __name__ == "__main__":
    main(sys.argv)

Ce que je pense peut être surprenant pour les utilisateurs de Python et c'est peut-être le problème auquel vous êtes confronté est le fait que si vous ne stockez pas une référence au nouveau widget dans la principale, par exemple en utilisant w = MyPopup(...) au lieu de self.w = MyPopup(...) la fenêtre n'apparaît pas (en fait, elle est créée et elle est immédiatement détruite).

La raison en est que lorsque la variable locale w sort du domaine d'application car personne ne fait explicitement référence au widget, le widget est supprimé. Cela peut être vu clairement parce que si vous appuyez à nouveau sur le bouton, vous verrez que lorsque la deuxième fenêtre contextuelle apparaît, la première est fermée.

Cela signifie également que si vous avez besoin de créer plusieurs popups, vous devez par exemple les mettre dans une liste python et vous devez les supprimer de cette liste une fois les popups fermés par l'utilisateur. L'équivalent dans l'exemple peut être remplacé par self.w = [] dans le constructeur, puis faire self.w.append(MyPopup(...)). Cela vous permettrait d'ouvrir plusieurs fenêtres contextuelles.

45
6502

En général, vous affichez simplement plusieurs fenêtres sans parent avec someQWidget.show(), comme:

w1 = QLabel("Window 1")
w2 = QLabel("Window 2")
w1.show()
w2.show()

Mais très probablement, vous voulez une boîte de dialogue standard modale comme this . Assurez-vous également de comprendre boîtes de dialogue modales .

3
flying sheep