Qt/Qml和方法重载 [英] Qt/Qml and method overloads

查看:282
本文介绍了Qt/Qml和方法重载的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在从Qml内部调用重载的C ++方法并试图了解其背后的原因时,就遇到了Qt框架的怪异行为.假设我有一个QList<QVariant>类,它具有以下方法:

Just came across a weird behavior of Qt framework while invoking overloaded C++ methods from within Qml and trying to understand the reason behind it. Let's say I have a QList<QVariant>-like class with the following methods:

...
Q_SLOT void append(const QVariant &item);
Q_SLOT void append(const QVariantList &items);
Q_SLOT void insert(int index, const QVariant &item);
Q_SLOT void insert(int index, const QVariantList &items);
...

Qml:

onclicked: {
  var itemCount = myListObject.size();
  myListObject.insert(itemCount, "Item " + (itemCount + 1));
}

Qt决定以items参数设置为 a null QVariant 为空的QVariantList调用void insert(int index, const QVariantList &items)重载,而不是用QString包裹在void insert(int index, const QVariant &item)中的void insert(int index, const QVariant &item)重载c7>.

Qt somehow decides to invoke the void insert(int index, const QVariantList &items) overload with items argument set to a null QVariant an empty QVariantList instead of the void insert(int index, const QVariant &item) overload with QString wrapped in QVariant.

现在,如果我按如下所示更改声明的顺序,则可以按预期工作:

Now if I change the order of declarations as follows, it works as expected:

Q_SLOT void insert(int index, const QVariantList &items);
Q_SLOT void insert(int index, const QVariant &item);

我在Qt框架的文档中找不到有关声明顺序及其在调用过程中如何影响方法解析方式的任何信息.

I could not find anything under Qt framework's documentation regarding the order of declarations and how it affects the way methods are resolved during invoke.

有人可以解释吗?谢谢.

Can someone please explain? Thank you.

推荐答案

此问题与JavaScript中的重载有关.一旦了解了它,您就会了解代码怪异行为" 的原因.只需查看 Javascript中的函数重载-最佳做法.

This question is related to overloading in JavaScript. Once you get to known with it -- you understand reason of "weird behavior" of your code. Just take a look at Function overloading in Javascript - Best practices.

简而言之-我建议您下一步:由于您可以在两侧(QML和Qt/C ++)上操作QVariant变量-将变量作为参数传递,并在Qt/C ++端对其进行处理希望.

In few words -- I recommend you to do next: since you can operate QVariant variables on both sides (QML and Qt/C++) -- pass variant as parameter, and process it on Qt/C++ side as you wish.

您可以使用类似这样的内容:

You can use something like this:

您的C ++类已创建并传递给QML(例如,作为setContextProperty("TestObject", &tc)):

Your C++ class created and passed to QML (e.g. as setContextProperty("TestObject", &tc)):

public slots:
    Q_SLOT void insert(const int index, const QVariant &something) {
        qDebug() << __FUNCTION__;
        if (something.canConvert<QString>()) {
            insertOne(index, something.toString());
        } else if (something.canConvert<QStringList>()) {
            insertMany(index, something.toStringList());
        }
    }

private slots:
    void insertOne(int index, const QString &item) {
        qDebug() << __FUNCTION__ << index << item;
    }

    void insertMany(int index, const QStringList &items) {
        qDebug() << __FUNCTION__ << index << items;
    }

QML 中的某处:

Button {
    anchors.centerIn: parent
    text: "click me"
    onClicked: {
        // Next line will call insertOne
        TestObject.insert(1, "Only one string")
        // Next line will call insertMany
        TestObject.insert(2, ["Lots", "of", "strings"])
        // Next line will call insertOne
        TestObject.insert(3, "Item " + (3 + 1))
        // Next line will call insertOne with empty string
        TestObject.insert(4, "")
        // Next line will will warn about error on QML side:
        // Error: Insufficient arguments
        TestObject.insert(5)
    }
}

这篇关于Qt/Qml和方法重载的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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