PyQt窗口在打开后关闭 [英] PyQt window closes after opening

查看:25
本文介绍了PyQt窗口在打开后关闭的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有两个文件,分别是main.pyclient_window.py。我想在进度条完成进度后显示客户端窗口。但我发现客户端窗口会立即打开和关闭。谁能建议如何更改代码,以便我掌握正确的逻辑?

这是main.py

"""
This module defines the User Interface
"""

import sys
import time

from cloudL.ui import client_window

from PyQt4 import QtGui

from PyQt4 import QtCore
from PyQt4.QtGui import *


class ProgressBarWidget(QtGui.QDialog):

    def __init__(self, parent=None):
        super(ProgressBarWidget, self).__init__(parent)
        layout = QtGui.QVBoxLayout(self)

        self.label = QLabel()
        self.tryAgain = QPushButton("Try Again")
        self.progressBar = QtGui.QProgressBar(self)
        self.progressBar.setRange(0,100)
        self.tryAgain.setEnabled(False)

        layout.addWidget(self.label)
        layout.addWidget(self.progressBar)
        layout.addWidget(self.tryAgain)

        self.myLongTask = TaskThread()
        self.myLongTask.notifyProgress.connect(self.onProgress)
        self.myLongTask.start()

    def onStart(self):
        self.tryAgain.setEnabled(False)
        self.myLongTask.start()
        self.label.setText("")

    def onProgress(self, i):
        self.progressBar.setValue(i)
        if(self.progressBar.value() == 100):
            #app = QApplication(sys.argv)
            #global ex
            ex = client_window.main()
            ex.show()
            #ex.main()
            #ex.show()
            #sys.exit(app.exec_())
        else:
            self.tryAgain.setEnabled(True)
            self.tryAgain.clicked.connect(self.onStart)
            self.label.setText("Cannot connect to Server! Please Try Again!")


class TaskThread(QtCore.QThread):
    notifyProgress = QtCore.pyqtSignal(int)
    def run(self):
        for i in range(101):
            self.notifyProgress.emit(i)
            time.sleep(0.005)

class MainWindow(QWidget):
    """
    This window will be the first screen to appear
    """

    def __init__(self, parent = None):
        super(MainWindow, self).__init__(parent)
        """
        Initializes parameters required by the MainWindow
        """
        self.option = ""       # to specify the if the selected option is Server or Client
        self.ex = None

    def main(self):
        """
        This function is the origin where the initiation of the control takes place
        :return: Returns nothing
        """

        mainLayout = QVBoxLayout()
        mainLayout.setAlignment(QtCore.Qt.AlignCenter)

        radioLayout = QHBoxLayout()
        mainLayout.setAlignment(QtCore.Qt.AlignCenter)

        label = QLabel()
        label.setText("Select whether to act as a Server or a Client")
        labelFont = QFont()
        labelFont.setBold(True)
        labelFont.setPointSize(15)
        label.setFont(labelFont)

        mainLayout.addWidget(label)
        mainLayout.addStretch()

        b1 = QRadioButton("Server")
        b1.setChecked(True)
        b1.toggled.connect(lambda : btnstate(b1))
        radioLayout.addWidget(b1)

        b2 = QRadioButton("Client")
        b2.toggled.connect(lambda : btnstate(b2))
        radioLayout.addWidget(b2)

        self.option = ""

        def btnstate(b):
            """
            Nested function to define the action when radio button is toggled
            :param b: Button which is toggled currently
            :return: Returns nothing
            """
            if b.text() == "Server" and b.isChecked() == True:
                self.option = "Server"

            if b.text() == "Client" and b.isChecked() == True:
                self.option = "Client"

        start = QPushButton("Start")

        mainLayout.addLayout(radioLayout)
        mainLayout.addStretch()
        mainLayout.addWidget(start)

        self.setLayout(mainLayout)
        self.setGeometry(400, 200, 300, 300)
        self.setWindowTitle("CloudL")

        start.clicked.connect(self.showdialog)

    def showdialog(self):
        """
        A sample message box to check and display which option is chosen
        :return: Returns nothing
        """
        #app = QApplication(sys.argv)
        self.ex = ProgressBarWidget(self)
        self.ex.setGeometry(400, 200, 500, 150)
        self.destroy()
        self.ex.setWindowTitle("CloudL")
        self.ex.show()


"""
Execute the required action
"""
app = QApplication(sys.argv)
ex = MainWindow()
ex.main()
ex.show()
sys.exit(app.exec_())

客户端_window.py如下:

#client_window.py

import sys
from PyQt4 import QtCore

from PyQt4.QtGui import *
from PyQt4.QtCore import *

class myListWidget(QListWidget):
    def Clicked(self, item):
        QMessageBox.information(self, "ListWidget", "You clicked: " + item.text())


class Example(QWidget):
    def __init__(self):
        super(Example, self).__init__()
        self.listWidget = None
        self.initUI()

    def initUI(self):
        hbox = QHBoxLayout(self)

        topleftLayout = QVBoxLayout()
        topleftLayout.setAlignment(QtCore.Qt.AlignTop)
        topleft = QFrame()
        topleft.setFrameShape(QFrame.StyledPanel)
        label = QLabel()
        label.setText("SERVER LIST")
        label.setAlignment(QtCore.Qt.AlignCenter)
        topleftLayout.addWidget(label)
        self.addServerList(topleftLayout)
        topleft.setLayout(topleftLayout)
        bottom = QFrame()
        bottom.setFrameShape(QFrame.StyledPanel)

        splitter1 = QSplitter(Qt.Horizontal)
        textedit = QTextEdit()
        splitter1.addWidget(topleft)
        splitter1.addWidget(textedit)
        splitter1.setSizes([100, 200])

        splitter2 = QSplitter(Qt.Vertical)
        splitter2.addWidget(splitter1)
        splitter2.addWidget(bottom)
        splitter2.setSizes([225, 100])

        hbox.addWidget(splitter2)

        self.setLayout(hbox)
        QApplication.setStyle(QStyleFactory.create('Cleanlooks'))

        self.setGeometry(300, 300, 300, 200)
        self.setWindowTitle('QSplitter demo')
        self.showMaximized()

    def addServerList(self, layout):
        self.listWidget = myListWidget()
        self.listWidget.resize(300, 120)

        self.listWidget.addItem("Item 1");
        self.listWidget.addItem("Item 2");
        self.listWidget.addItem("Item 3");
        self.listWidget.addItem("Item 4");

        self.listWidget.setWindowTitle('PyQT QListwidget Demo')
        self.listWidget.itemClicked.connect(self.listWidget.Clicked)
        layout.addWidget(self.listWidget)


def main():
    ex = Example()
    ex.showMaximized()
    return ex


if __name__ == '__main__':
    app = QApplication(sys.argv)
    main()
    sys.exit(app.exec_())

我正在呼叫client_window,地址:

def onProgress(self, i):
    self.progressBar.setValue(i)
    if(self.progressBar.value() == 100):
        #app = QApplication(sys.argv)
        #global ex
        ex = client_window.main()
        ex.show()
        #ex.main()
        #ex.show()
        #sys.exit(app.exec_())
    else:
        self.tryAgain.setEnabled(True)
        self.tryAgain.clicked.connect(self.onStart)
        self.label.setText("Cannot connect to Server! Please Try Again!")

此外,如果我在客户端窗口中包括行app = QApplication(sys.argv)sys.exit(app.exec_()),我会收到以下错误:

QCoreApplication::exec:事件循环已在运行pyqt错误

推荐答案

您需要保留对客户端窗口的引用,否则它将在onProgress返回时立即被垃圾回收:

def onProgress(self, i):
    self.progressBar.setValue(i)
    if self.progressBar.value() == 100:
        self.client_window = client_window.main()
    else:
        self.tryAgain.setEnabled(True)
        self.tryAgain.clicked.connect(self.onStart)
        self.label.setText("Cannot connect to Server! Please Try Again!")

这篇关于PyQt窗口在打开后关闭的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆