0

I'm currently working on a GUI application in Qt. My application consists of a lot of widgets styled using CSS classes. These widgets change their appearance often during runtime. I have run into a problem that sometime the changed styles don't apply. A quick google search suggested using unpolish(), then polish() and update(). However, I found out that these lines often cause segfault.

This is a functional, but very simplified version of my code:

from PyQt5.QtWidgets import QApplication, QMainWindow, QLabel
from PyQt5.QtCore import QThread
import sys, time, faulthandler

class SegmFaultWindow(QMainWindow):
    def __init__(self):
        super().__init__()
        self.label = QLabel("label", self)
        self.setCentralWidget(self.label)
        self.show()
        self.worker = SegmFaultWorker(self)
        self.worker.start()

class SegmFaultWorker(QThread):
    def __init__(self, window):
        super().__init__()
        self.window = window
    def updateStyle(self, widget):
        widget.style().unpolish(widget)
        widget.style().polish(widget)
        widget.update()
    def run(self):
        while True:
            time.sleep(0.1)
            self.window.label.setStyleSheet("background-color: lightblue;")
            self.updateStyle(self.window.label)

if __name__ == '__main__':
    faulthandler.enable()
    app = QApplication(sys.argv)
    window = SegmFaultWindow()
    sys.exit(app.exec_())

Every time I run the program, it prints out something like this:

Could not parse stylesheet of object QLabel(0x2d22190)
Could not parse stylesheet of object QLabel(0x2d22190)
Could not parse stylesheet of object QLabel(0x2d22190)
Fatal Python error: Segmentation fault

Current thread 0x00007fea0effd700 (most recent call first):
  File "/home/emon/SegmFault.py", line 20 in updateStyle
  File "/home/emon/SegmFault.py", line 26 in run

Thread 0x00007fea2874d740 (most recent call first):
  File "/home/emon/SegmFault.py", line 32 in <module>
Segmentation fault (core dumped)

I don't know why this is happening. Is it a bug or am I using it wrong? Or is there a better way to force style update?

Qwerty-uiop
  • 11
  • 1
  • 2
  • 1
    It's not a bug: widgets (anything directly related to the UI) are *not* thread safe. If you want to communicate between the worker thread and the main UI thread, you must use signals, there's no alternative. Create a signal in the thread, emit it when you need to update the label, and connect it to a function that applies the stylesheet in the main class. – musicamante Sep 30 '21 at 14:40
  • 1
    Is a thread even necessary for this? As it stands, once the gui-related stuff is removed, the thread won't have any useful work left to do at all. – ekhumoro Sep 30 '21 at 15:28

0 Answers0