PyQt5中drawComplexControl获取QMdiSubWindow标题栏状态失败求解
解决PyQt5中QMdiSubWindow标题栏激活状态判断失效问题
在PyQt5的drawComplexControl函数中判断QMdiSubWindow标题栏激活状态时,直接用==匹配State_Active无法生效,这是因为titleBarState是位掩码类型,需要用按位与操作来检测对应位是否被设置,同时要注意State_Active的正确归属类。
错误原因分析
- 原代码中使用
option.titleBarState == QProxyStyle.State_Active,但titleBarState可能包含多个状态位的组合,直接用等于判断会忽略其他状态位的影响。 State_Active属于QStyle类而非QProxyStyle,虽然QProxyStyle继承自QStyle,但直接用QProxyStyle调用属于冗余写法,且可能引发潜在问题。
修正后的代码
from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5.QtWidgets import QProxyStyle, QStyle, QStyleOptionTitleBar class MyProxyStyle(QtWidgets.QProxyStyle): def drawComplexControl(self, control: QStyle.ComplexControl, option: QStyleOptionTitleBar, painter: QtGui.QPainter, widget=None) -> None: # 使用按位与操作检测激活状态位 if option.titleBarState & QStyle.State_Active: print("active") super().drawComplexControl(control, option, painter, widget) class Mywindow(QtWidgets.QMainWindow): def __init__(self, parent=None): super(Mywindow, self).__init__(parent) self.setWindowTitle("Customized style") self.mdiarea = QtWidgets.QMdiArea() self.setCentralWidget(self.mdiarea) self.mdiarea.setWindowTitle("Test") self.window = QtWidgets.QWidget() self.window.setMinimumSize(160, 120) self.window2 = QtWidgets.QWidget() self.window2.setMinimumSize(320, 220) sw1 = QtWidgets.QMdiSubWindow() sw1.setWindowTitle("Test") sw1.setWidget(self.window) sw2 = QtWidgets.QMdiSubWindow() sw2.setWindowTitle("Test2") sw2.setWidget(self.window2) self.mdiarea.addSubWindow(sw1) self.mdiarea.addSubWindow(sw2) if __name__ == "__main__": import sys app = QtWidgets.QApplication(sys.argv) my_style = MyProxyStyle("fusion") app.setStyle(my_style) view = Mywindow() view.show() sys.exit(app.exec_())
关键修改点
- 将判断逻辑从
==改为按位与&,这和C++源码中的option->titleBarState & QStyle::State_Active逻辑保持一致,能正确检测激活状态位是否被设置。 - 引用
QStyle.State_Active而非QProxyStyle.State_Active,确保状态常量的正确来源。
内容的提问来源于stack exchange,提问作者Houssam Farag
相关产品推荐
相关产品推荐

