Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I make a subclass of QMessageBox with flag modifications?

I was trying to make the text in a QMessageBox selectable, and I found that if i modify the "setTextInteractionFlags" on QMessageBox, this solves the problem. However, when I tried to do this, my PyQt (or more specifically, PySide) complains that this attribute does not exist. So I instead try to add this feature in as a style sheet, however upon trying to create my own custom class of QMessageBox, this does not seem to work at all.

I then tried to make a QMessageBox manually, and that seemed to work.

Here is the code:

from PyQt4 import QtCore
from PyQt4 import QtGui
import sys

class CustomQMessageBox(QtGui.QMessageBox):
    def __init__(self, *args, **kwargs):
        QtGui.QMessageBox.__init__(self, *args, **kwargs)
        self.setStyleSheet("QMessageBox { messagebox-text-interaction-flags: 5; }")


class Window(QtGui.QWidget):

    def __init__(self, parent=None):
        QtGui.QWidget.__init__(self, parent)
        self.setWindowTitle('Test UI')
        self.setMinimumSize(225, 150)
        self.uiWidget = QtGui.QWidget()

        self.verticalLayout = QtGui.QVBoxLayout(self.uiWidget)

        self.enterListLabel = QtGui.QLabel(self.uiWidget)
        self.enterListLabel.setText('Enter list of names')
        self.verticalLayout.addWidget(self.enterListLabel)

        self.lyt = QtGui.QVBoxLayout()
        self.lyt.addWidget(self.uiWidget)

        self.setLayout(self.lyt)

        #This does NOT work
        cacheFixConfirm = CustomQMessageBox.question(self.uiWidget, 'Message Box', 'something', QtGui.QMessageBox.StandardButton.Yes | QtGui.QMessageBox.StandardButton.No)

        #This does
        confirmDialogBox = QtGui.QMessageBox()
        confirmDialogBox.setWindowTitle('Message Box')
        confirmDialogBox.setIcon(QtGui.QMessageBox.Question)
        confirmDialogBox.setText('sdlkfjl;asdjfosdijflsdkfjsdklfjsdkljfio')
        confirmDialogBox.setStyleSheet("QMessageBox { messagebox-text-interaction-flags: 5; }")
        confirmDialogBox.addButton(QtGui.QPushButton('Yes', parent=confirmDialogBox), QtGui.QMessageBox.YesRole)
        confirmDialogBox.addButton(QtGui.QPushButton('No', parent=confirmDialogBox), QtGui.QMessageBox.NoRole)
        confirmDialogBox.exec_()

if __name__ == "__main__":
    app = QtWidgets.QApplication(sys.argv)
    window = Window()
    window.show()
    sys.exit(app.exec_())

I am just wondering why that second example works, while the first example that attempts to use the custom class does not...

like image 218
user3696118 Avatar asked Sep 03 '25 09:09

user3696118


1 Answers

The problem is that the static methods about, aboutQt, critical, information, question and warning do not use the derived class but the QMessageBox, something similar to:

class MessageBox(QMessageBox):
    @staticmethod
    def foo(self, arg1, ...):
        w = QMessageBox()
        ...

Therefore, even if you set that property in MessageBox it will not work since it will not apply to classes that are not MessageBox.

So depending on what you want there are the following options:

  1. Apply the same property to all existing QMessageBox (including its derived classes):
app.setStyleSheet("QMessageBox { messagebox-text-interaction-flags: 5; }")
  1. Applying the StyleSheet to ui.Widget that was established as a parent when invoking the question() method will apply to all of your children:
self.uiWidget.setStyleSheet("QMessageBox { messagebox-text-interaction-flags: 5; }")
cacheFixConfirm = CustomQMessageBox.question(
    self.uiWidget,
    "Message Box",
    "something",
    QtGui.QMessageBox.StandardButton.Yes | QtGui.QMessageBox.StandardButton.No,
)
  1. Do not use the static method.
messagebox = CustomQMessageBox(
    QtGui.QMessageBox.Question,
    "Message Box",
    "something",
    QtGui.QMessageBox.NoButton,
    self.uiWidget,
)
messagebox.addButton(QtGui.QMessageBox.Yes)
messagebox.addButton(QtGui.QMessageBox.No)
messagebox.exec_()
like image 75
eyllanesc Avatar answered Sep 04 '25 23:09

eyllanesc