QUiLoader:使用自定义小部件加载.ui文件的要求? [英] QUiLoader: requirements for loading .ui file with custom widgets?

查看:633
本文介绍了QUiLoader:使用自定义小部件加载.ui文件的要求?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用Qt5-Designer创建了一个UI,通过调用

I've created a UI using Qt5-Designer which I load at runtime by calling

QUiLoader().load(qfile_object, this);

像charm一样工作,但现在我提升了一些 QLabel 元素到小部件类 MyQLabel 与从 QLabel 派生。

Works like charm but now I've promoted some QLabel elements to a widget class MyQLabel with is derived from QLabel.

当我现在尝试加载UI时,我会为每个已推广的窗口小部件发出警告:

When I now try to load the UI I get a warning for each promoted widget:

"QFormBuilder was unable to create a custom widget of the class 'MyQLabel'; defaulting to base class 'QLabel'."

类如下所示:

class MyQLabel : public QLabel {
    Q_OBJECT
  public:
    MyQLabel(QWidget *parent = nullptr) : QLabel(parent) {}
};

已经自动 - moc 链接到我的可执行文件。

It's been auto-moc'ed and linked against my executable.

我有一种感觉,不知怎的,我必须告诉 QUiLoader 使用它,但我不知道如何..

I have the feeling that somehow I have to tell QUiLoader about my class before trying to use it but I don't know how..

我必须为此创建一个插件吗?有没有办法重现, QUiLoader 会检查它吗?

Do I have to create a plugin for this? Is there a way to reproduce, what to QUiLoader does to examine it?

推荐答案

您需要创建自己的导出版本 QUiLoader ,并提供工厂方法的实现 QUiLoader :: createWidget

You need to create your own derived version of QUiLoader, and provide an implementation of the factory method QUiLoader::createWidget that can create your widgets.

您可以将这个因素导入一个由 QUiLoader 。它必须实施 QDesignerCustomWidgetInterface 实例。有关插件的完整示例,请参见自定义小部件插件示例

You could factor this out into a plugin that gets loaded by the QUiLoader. It would have to implement a QDesignerCustomWidgetInterface instance. See the Custom Widget Plugin Example for a complete example of a plugin.

// https://github.com/KubaO/stackoverflown/tree/master/questions/uiloader-custom-37775472
#include <QtUiTools>
#include <QtWidgets>

const char uiData[] =
    "<ui version=\"4.0\"><class>Widget</class><widget class=\"MyWidget\" name=\"Widget\">\n"
        "<property name=\"windowTitle\" ><string>Widget</string></property>\n"
        "</widget><pixmapfunction></pixmapfunction><resources/><connections/>\n"
    "</ui>";

class MyWidget : public QLabel
{
    Q_OBJECT
    bool m_closed = false;
public:
    MyWidget(QWidget* parent = 0) : QLabel("This is MyWidget", parent) {}
    bool isClosed() const { return m_closed; }
    void closeEvent(QCloseEvent *) Q_DECL_OVERRIDE { m_closed = true; }
};

class MyUiLoader : public QUiLoader {
public:
    MyUiLoader(QObject * parent = 0) : QUiLoader(parent) {}
    QWidget * createWidget(const QString & className, QWidget * parent = 0,
                           const QString & name = QString()) {
        if (className == "MyWidget") {
            MyWidget * w = new MyWidget(parent);
            w->setObjectName(name);
            return w;
        }
        return QUiLoader::createWidget(className, parent, name);
    }
};

int main(int argc, char *argv[])
{
    QApplication app(argc, argv);
    QBuffer buf;
    buf.setData(uiData, sizeof(uiData));
    MyUiLoader uiLoader;
    auto uiMain = qobject_cast<MyWidget*>(uiLoader.load(&buf));
    uiMain->show();
    return app.exec();
}

#include "main.moc"

这篇关于QUiLoader:使用自定义小部件加载.ui文件的要求?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆