Python 如何确保停靠的Qt窗口具有带有深色平台主题的可见控件?

Python 如何确保停靠的Qt窗口具有带有深色平台主题的可见控件?,python,qt,pyqt,Python,Qt,Pyqt,考虑以下PyQt程序 导入系统 从PyQt5导入QtCore、QtWidgets 类dockdemo(QtWidgets.QMainWindow): def uuu init uuu(self,parent=None): 超级(dockdemo,self)。\uuuu init\uuuu(父级) self.items=QtWidgets.QDockWidget(“可停靠”,self) self.listWidget=qtwidts.QListWidget() self.listWidget.ad

考虑以下PyQt程序

导入系统 从PyQt5导入QtCore、QtWidgets 类dockdemo(QtWidgets.QMainWindow): def uuu init uuu(self,parent=None): 超级(dockdemo,self)。\uuuu init\uuuu(父级) self.items=QtWidgets.QDockWidget(“可停靠”,self) self.listWidget=qtwidts.QListWidget() self.listWidget.addItem(“item1”) self.listWidget.addItem(“item2”) self.listWidget.addItem(“item3”) self.items.setWidget(self.listWidget) self.addDockWidget(QtCore.Qt.RightDockWidgetArea,self.items) self.setWindowTitle(“Dock演示”) def main(): app=qtwidts.QApplication(sys.argv) ex=dockdemo() 例如:show() sys.exit(app.exec_()) 如果uuuu name uuuuuu='\uuuuuuu main\uuuuuuu': main() 这可以很好地工作,并生成一个简单的停靠窗口:

然而,这并不符合我的GTK2黑暗平台主题。如果我通过设置
Qt\u QPA\u PLATFORMTHEME=gtk2
强制Qt这样做,我会得到以下结果:

停靠窗口的控件几乎与背景颜色相同,因此很难看到

< C++中的GNU八度表在平台主题中正确显示了自己的停靠控件控件:

Octave的停靠小部件在不使用系统主题时也会显示正确的控件

我怀疑这可能是因为这里设置了一些CSS,但我不知道具体是什么:


我做错什么了吗?感觉像是一个错误,Qt没有正确设置停靠窗口控件的颜色,除非你做一些额外的事情(我还不知道额外的可能是什么)。

不幸的是,Linux默认的Qt Fusion样式停靠图标在
QFusionStyle
(也是在
QCommonStyle
中,这是一种退步)。它们从来没有按照主题上色。很多“标准”图标都是这样的,但很多都是彩色/不透明的,因此背景没有太大区别

要覆盖它们,您需要使用CSS或自定义的
QProxyStyle

您可以从链接到的示例中看到它是如何在CSS中完成的

QDockWidget
{
标题栏关闭图标:url(close.svg);
标题栏普通图标:url(restore.svg);
}
定制QStyle更复杂一些

class AppStyle:公共QProxyStyle
{
公众:
使用QProxyStyle::QProxyStyle;
QIcon standardIcon(StandardPixmap standardIcon,常数QStyleOption*option=nullptr,常数QWidget*widget=nullptr)常数覆盖
{
开关(标准图标){
案例SP_标题BarnormalButton:
返回QIcon(“restore.svg”);
案例SP_标题栏关闭按钮:
案例SP_DockWidgetCloseButton:
返回QIcon(“close.svg”);
违约:
return baseStyle()->standardIcon(standardIcon,option,widget);
}
}
QPixmap standardPixmap(standardPixmap stdPixmap,const QStyleOption*option=nullptr,const QWidget*widget=nullptr)常量覆盖
{
开关(stdpix映射){
案例SP_标题BarnormalButton:
案例SP_标题栏关闭按钮:
案例SP_DockWidgetCloseButton:
返回标准图标(stdPixmap,option,widget).pixmap(option->rect.size());
违约:
return baseStyle()->standardPixmap(stdPixmap、选项、小部件);
}
}
};
在这两种情况下,你都需要知道主题的用法(例如它是黑暗的)。你会对每个主题使用不同的(或动态的)CSS,或者你的自定义<代码> QPROXYLYTYS> /Cord>会返回正确的基色图标。例如,在C++中你甚至可以确定当前调色板背景是否是暗的(低色值)。然后基于此返回不同的图标

是的,这可能被认为是一个“错误”或缺陷,因为Qt不能“自动”处理黑暗系统主题——当尝试将应用程序皮肤设置为黑暗时,不管桌面主题是什么,这也很烦人。但这就是生活


P.S.OHOPS,刚刚意识到我给Python问题提供了一个C++例子…我不使用Python和Qt,所以恐怕这是我能做的最好的。

< P>不幸的是,Linux默认QT融合风格的停靠图标是在 QFuxSturths<代码>中的XPM格式图像(也在QuoCyrase中是后退)很多“标准”图标都是这样的,但很多都是彩色/不透明的,所以背景没有太大的区别

要覆盖它们,您需要使用CSS或自定义的
QProxyStyle

您可以从链接到的示例中看到它是如何在CSS中完成的

QDockWidget
{
标题栏关闭图标:url(close.svg);
标题栏普通图标:url(restore.svg);
}
定制QStyle更复杂一些

class AppStyle:公共QProxyStyle
{
公众:
使用QProxyStyle::QProxyStyle;
QIcon standardIcon(StandardPixmap standardIcon,常数QStyleOption*option=nullptr,常数QWidget*widget=nullptr)常数覆盖
{
开关(标准图标){
案例SP_标题BarnormalButton:
返回QIcon(“restore.svg”);
案例SP_标题栏关闭按钮:
案例SP_DockWidgetCloseButton:
返回QIcon(“close.svg”);
违约:
return baseStyle()->standardIcon(standardIcon,option,widget);
}
}
QPixmap standardPixmap(standardPixmap stdPixmap,const QStyleOption*option=nullptr,const QWidget*widget=nullptr)常量覆盖
{
开关(stdpix映射){
案例SP_标题BarnormalButton:
案例SP_标题栏关闭按钮:
案例SP_DockWidgetCloseButton:
返回标准图标(stdPixmap,option,widget).pixmap(option->rect.size());
违约:
return baseStyle()->standardPixmap(stdPixmap、选项、小部件);
}
}
};