为什么我的QLabel小部件没有出现在此线程中?

时间:2019-10-02 18:09:15

标签: python python-3.x pyqt pyqt5

所以我正在使用PyQt5作为UI的消息传递应用程序。但是我有这个问题,由于某种原因我的小部件没有出现。我什至不知道为什么,即使我似乎已经在另一个Python脚本上进行了尝试。但是,当我将列表中的内容实现时,它似乎不起作用。

有问题的代码部分:

 class MainWindow():
    def __init__(self,Authenticated,Username):
        if Authenticated == True:
            self.App = QtWidgets.QApplication([])
            self.LoadedApp = uic.loadUi("Developer hub main window.ui")

            self.LoadedApp.UsernameText.setText("Username : " + Username)

            self.MessageBoxQWidget = self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget")
            self.MessageBoxContainer = self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget").findChild(QVBoxLayout,"MessageBoxContainer")

            self.LoadedApp.SendMessageButton.clicked.connect(self.SendMessage)
            self.LoadedApp.DeleteMessageButton.clicked.connect(self.DeleteMessage)

            self.MessageBoxQWidget.setLayout(self.MessageBoxContainer)

            Thread(target = self.UpdateMessages).start()

            self.LoadedApp.MessageBoxScrollArea.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOn)
            self.LoadedApp.MessageBoxScrollArea.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
            self.LoadedApp.MessageBoxScrollArea.setWidget(self.MessageBoxQWidget)

            self.LoadedApp.show()
            self.App.exec()

    def SendMessage(self):
        print("Sending message")
        DateTimeNow = str(datetime.datetime.now())
        DateTimeNow = DateTimeNow[0:16]
        global Username

        MessageObject = {
            "Username" : Username,
            "Message" : self.LoadedApp.MessageInput.toPlainText(),
            "Time" : DateTimeNow
        }
        MessageData.insert_one(MessageObject)

        print(self.LoadedApp.MessageInput.toPlainText())
        self.DeleteMessage()

    def DeleteMessage(self):
        self.LoadedApp.MessageInput.clear()

    def UpdateMessages(self):
        while True:
            print("Update")
            for Index in range(0,self.MessageBoxContainer.count()):
                print(Index)
                Widget = self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget").findChild(QVBoxLayout,"MessageBoxContainer").findChild(QLabel,"Message"+str(Index))
                if Widget is not None:
                    print("Found")
                    Widget.setParent(None)

            FetchedMessages = GetData("Messages",None,None)
            MessageIndex = 0
            for Message in FetchedMessages:
                MessageLabel = QtWidgets.QLabel()
                MessageLabel.setFixedSize(511, 31)
                MessageLabel.setStyleSheet("color: rgb(0,0,0);background-color: rgb(255, 255, 255);font: 10pt \"Eras Demi ITC\";")
                MessageLabel.setText(Message)
                MessageLabel.setObjectName("Message"+str(MessageIndex))
                self.MessageBoxContainer.addWidget(MessageLabel)
                MessageIndex +=1
                print(Message)

            self.MessageBoxQWidget.setLayout(self.MessageBoxContainer)
            self.LoadedApp.show()
            time.sleep(5)

有关代码的信息: 该函数在PyQt5窗口的类中。 “ FetchedMessages”是一个函数,它返回一个包含多个循环循环的字符串的列表。然后就是制作QLabel并将其发送到MessageBoxContainer的地方。 “ MessageBoxContainer”等于 self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget").findChild(QVBoxLayout,"MessageBoxContainer") 并且“ MessageBoxQWidget”等于self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget")

这是UI的层次结构: enter image description here

运行程序时没有错误。只是QLabel根本没有出现。这是我运行程序时的结果:

enter image description here

但是在我的其他测试脚本中,我得到了:

enter image description here

但是另一个脚本未在等待5秒的while true循环内在线程中运行该函数。如您所见,这是我为第二个脚本的函数编写的代码:

class MainWindow():
    def __init__(self,Authenticated,Username):
        if Authenticated == True:
            self.App = QtWidgets.QApplication([])
            self.LoadedApp = uic.loadUi("Developer hub main window.ui")

            self.LoadedApp.UsernameText.setText("Username : " + Username)

            MessageBoxQWidget = self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget")
            MessageBoxContainer = self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget").findChild(QVBoxLayout,"MessageBoxContainer")
            self.Messages = []

            for x in range(1,30):
                self.Messages.append("Test [29/9/2019 - 13:50] : Hello"+ str(x))

            print(self.Messages)

            for Message in self.Messages:
                MessageLabel = QtWidgets.QLabel()
                MessageLabel.setFixedSize(511, 31)
                MessageLabel.setStyleSheet("color: rgb(0,0,0);background-color: rgb(255, 255, 255);font: 10pt \"Eras Demi ITC\";")
                MessageLabel.setText(Message)
                MessageBoxContainer.addWidget(MessageLabel)

                #How to remove a label [Below]
                #MessageLabel.setParent(None)

                # An attribute of the class is created with setattr()
                #setattr(self, "{}_infor_label".format(Message), MessageLabel)


            MessageBoxQWidget.setLayout(MessageBoxContainer)

            self.LoadedApp.MessageBoxScrollArea.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOn)
            self.LoadedApp.MessageBoxScrollArea.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
            self.LoadedApp.MessageBoxScrollArea.setWidget(MessageBoxQWidget)

            self.LoadedApp.SendMessageButton.clicked.connect(self.SendMessage)
            self.LoadedApp.DeleteMessageButton.clicked.connect(self.DeleteMessage)

            self.LoadedApp.show()
            self.App.exec()

    def SendMessage(self):
        print("Sending message")
        print(self.LoadedApp.MessageInput.toPlainText())
        self.DeleteMessage()

    def DeleteMessage(self):
        self.LoadedApp.MessageInput.clear()

有什么帮助吗?如果您需要更多背景信息或更多信息,请这样说,我会提供。

[编辑]

这是简化的代码。我得到了消息和小的“更新”打印语句,每5秒可以使用一次,但QLabel却没有出现:

class MainWindow():
    def __init__(self,Username):
            self.App = QtWidgets.QApplication([])
            self.LoadedApp = uic.loadUi("Developer hub main window.ui")

            self.MessageBoxQWidget = self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget")
            self.MessageBoxContainer = self.LoadedApp.MessageBoxScrollArea.findChild(QWidget,"MessageBoxQWidget").findChild(QVBoxLayout,"MessageBoxContainer")
            self.MessageBoxQWidget.setLayout(self.MessageBoxContainer)

            Thread(target = self.UpdateMessages).start()

            self.LoadedApp.MessageBoxScrollArea.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOn)
            self.LoadedApp.MessageBoxScrollArea.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
            self.LoadedApp.MessageBoxScrollArea.setWidget(self.MessageBoxQWidget)
            self.LoadedApp.show()
            self.App.exec()

    def UpdateMessages(self):
        while True:
            print("Update")
            FetchedMessages = ["Message1Example","Message2Example","Message3Example"]
            MessageIndex = 0
            for Message in FetchedMessages:
                MessageLabel = QtWidgets.QLabel()
                MessageLabel.setFixedSize(511, 31)
                MessageLabel.setStyleSheet("color: rgb(0,0,0);background-color: rgb(255, 255, 255);font: 10pt \"Eras Demi ITC\";")
                MessageLabel.setText(Message)
                MessageLabel.setObjectName("Message"+str(MessageIndex))
                self.MessageBoxContainer.addWidget(MessageLabel)
                MessageIndex +=1
                print(Message)
            time.sleep(5)

这也是用户界面:https://cdn.discordapp.com/attachments/624702116845453315/629719792286433301/Developer_hub_main_window.ui

1 个答案:

答案 0 :(得分:0)

如果您要执行定期任务,则不必使用带有time.sleep()的线程,因为Qt不允许在另一线程中创建或修改GUI的一部分,请使用QTimer。

    # ..    
    self.LoadedApp.show()
    timer = QtCore.QTimer(interval=5*1000, timeout=self.UpdateMessages)
    self.UpdateMessages()
    timer.start()

    self.App.exec()

def UpdateMessages(self):
    FetchedMessages = ["Message1Example","Message2Example","Message3Example"]
    for MessageIndex, Message in enumerate(FetchedMessages):
        MessageLabel = QtWidgets.QLabel()
        MessageLabel.setFixedSize(511, 31)
        MessageLabel.setStyleSheet("color: rgb(0,0,0);background-color: rgb(255, 255, 255);font: 10pt \"Eras Demi ITC\";")
        MessageLabel.setText(Message)
        MessageLabel.setObjectName("Message{}".format(MessageIndex))
        self.MessageBoxContainer.addWidget(MessageLabel)
        print(Message)