Skip to main content
 首页 » 编程设计

python之PyQt 中的 QUiLoader.createWidget 等价物

2025年05月04日26freeliver54

我有一个 PySide 应用程序,我正在研究使其与 PyQt4 兼容。显然这应该不会太难,但我想尽量减少必要的代码更改次数。我遇到的最大差异(影响我的程序)是 PyQt 不包装 QUiLoader 类。

现在我意识到我仍然可以使用 PyQt 中的 uic 模块加载 ui 文件,但是我目前在 PySide 中使用 QUiLoader 的子类,它实现了一些我想要的自定义功能尽可能保留。

功能如下。我将 QUiLoader 子类化并覆盖了 createWidget() 方法。我的新实现允许您在应用程序运行时动态注册小部件促销。我可以这样做,因为 createWidget() 方法负责从 ui 文件实例化小部件,之后(我相信)标准 QUiLoader 实现应用 ui 文件中的指定属性。

我的问题是,是否有类似的方法可以在 PyQt 中覆盖以在运行时动态设置小部件提升,而不必通过 Qt Designer 和 ui 文件静态设置它。

附言我正在寻找对现有代码进行最少更改的解决方案。例如,如果我可以用在 PyQt 下提供等效行为的类替换我的 PySide QUiLoader 子类,那将是理想的。

编辑: 该实现将使用类似的东西:

loader = UiLoader() 
loader.registerCustomPromotion("myWidgetNameInQtDesigner",ClassToPromoteTo) 
ui = loader.load('myUiFile.ui') 

这实际上是我在 PySide 中使用 QUiLoader 的子类所做的。 .ui 文件中名称为 "myWidgetNameInQtDesigner" 的任何小部件都将被实例化为 ClassToPromoteTo 的实例。

请您参考如下方法:

事实证明这很容易,只要您愿意在 Qt Designer 中推广相关的小部件。

想法是向 sys.modules 添加一个虚拟模块,然后动态修改它包含的自定义小部件类。

因此,如果在 Qt Designer 中提升小部件时将“头文件”设置为“mylib.dummy”,则在使用 PyQt 加载 ui 文件时,您将执行如下操作:

from types import ModuleType 
 
# dummy module 
module = sys.modules['mylib.dummy'] = ModuleType('dummy') 
 
if mode == 'FOO': 
    module.TextEdit = FooTextEdit 
    module.LineEdit = FooLineEdit 
    module.PushButton = FooPushButton 
elif mode == 'BAR': 
    module.TextEdit = BarTextEdit 
    module.LineEdit = BarLineEdit 
    module.PushButton = BarPushButton 
else: 
    module.TextEdit = QTextEdit 
    module.LineEdit = QLineEdit 
    module.PushButton = QPushButton 
 
# loadUi/loadUiType will add the following import line: 
# from mylib.dummy import TextEdit, LineEdit, PushButton 
WidgetUI = uic.loadUiType('mywidget.ui'))[0] 
ui = WidgetUI()