Obj3ctiv3_C_88
Obj3ctiv3_C_88

Reputation: 1528

How to update QLabel in while loop

It feels like I should just be able to set up an event listener that runs an AJAX like call to update a qlabel but this seems to be endlessly complicated with QT.

Basically what I'm attempting to do is update the text in a QLabel. This happens on an infinite loop that breaks when a button is clicked (AKA something like a Slot that contains a flag). The reason for this is I'm essentially reading in a text file on the fly which is updated by the user. When the user saves the text file the content updates on the QLabel. When the user is happy with the text they hit "send". It then kills the listener and E-Mails the text content to a pre-defined E-Mail address. This is work related so the user story has been changed considerably but the overall concept is what I'm going for.

I tried doing something like setting a flag and this listening by doing the following:

    while not self.flag_set:
        self.my_text = text_read_module.get_text(self)
        self.label_60.setText(self.my_text)
        QCoreApplication.processEvents()
        sleep(2)

I also tried pushing this into it's own process and terminating when the button containing the terminate signal is called

Both of them fail to display any content on the screen but I can tell they're running thanks to some handy dandy print statements

PS This was done in Python but hopefully it is easy to ready for C++ users

Any idea on how to get this working? Thanks!

Upvotes: 0

Views: 2932

Answers (1)

Brendan Abel
Brendan Abel

Reputation: 37509

In Qt/PyQt, the method for triggering callbacks is the Signal/Slot system. Generally, if you need to continuously do some operation, and occasionally update the GUI based on that operation, you would create a worker thread that sends updates back to the main thread using Signals. For example, you could create a worker thread that continuously checks the file for updates and when it detects a change, it could send data back to the main thread using a signal. Your main thread GUI would listen for that signal and update the GUI accordingly.

Luckily, in your case, Qt already has a class that does this called QFileSystemWatcher, so you don't need to manually create a separate thread with signals.

class MyWidget(QtGui.QWidget):

    def __init__(self):
        super(MyWidget, self).__init__()
        self.label = QtGui.QLabel(self)
        self.watcher = QtCore.QFileSystemWatcher(self)
        self.watcher.addPath('/path/to/file')
        self.watcher.fileChanged.connect(self.updateLabel)

    def updateLabel(self, path):
        with open(path, 'r') as f:
            self.label.setText(f.read())

Upvotes: 4

Related Questions