gpt4 book ai didi

Qt:Q_PROPERTY 带有指针和用于 QtScript 访问的前向声明

转载 作者:行者123 更新时间:2023-12-04 13:20:02 25 4
gpt4 key购买 nike

问题
我正在制作一个使用 Q_OBJECT 和 Q_PROPERTY 从脚本访问一些对象的项目。我有两个问题:

  • 使使用前向声明的类可编写脚本
  • 返回一个属性作为指针

  • 说明
    1. 为什么要提前申报?
    类 B 获得 A 的前向声明,因为由于模板,A 需要标题中的完整 B 类型。 B 在头中只需要一个不完整的类型 (A*),因此前向声明是有效的。
    2. 为什么要返回一个指针?
    我们无法返回副本,因为我们需要访问脚本中的实际对象。我们不能返回引用,如 Qt does not allow slots to return references - 它们的类型将被忽略,它们只会返回 void*。
    代码
    完整代码下载 on pastebin或作为 ZIP 存档或 as ZIP archive最小示例 可用,用于测试/播放:我需要拆分前向声明和 MOC 的文件。我添加了一个 Makefile 来测试它。制作 deps:g++、moc、Qt。
    重要部件
    class A; // forward declaration necessary, see explanation above

    class B : public QObject {
    Q_OBJECT
    Q_PROPERTY(A a READ GetA) // <-- ERROR HERE
    // ...

    public slots:
    A* GetA() {
    return mA;
    }

    private:
    A* mA;
    // ...
    }
    脚本中的错误行:
    print(bObj.GetA().GetName());
    编译错误
    当我注释掉上面的 Q_PROPERTY 时,此错误消失。
    tmp/B.moc.hpp:95:51: error: invalid use of incomplete type ‘struct A’
    tmp/../B.hpp:10:7: error: forward declaration of ‘struct A’
    脚本异常
    当省略 Q_PROPERTY 并从脚本中调用 GetA() 方法作为插槽时,我收到以下异常:
    Line 7: "TypeError: cannot call GetA(): unknown return type `A*' 
    (register the type with qScriptRegisterMetaType())"
    使用 qRegisterMetaType<A*>("A*"); 注册 A* 时这更改为:
    Line 7: "TypeError: Result of expression 'bObj.GetA().GetName' 
    [undefined] is not a function."
    这表明 GetA() 不返回 A 对象,或者以某种方式返回一个指针,但脚本无法取消引用它。 GetA() 然后实际上返回一个 QVariant(A*) ,这可以以某种方式使用吗?
    问题:
  • 我可以以某种方式从不完整的类型创建 Q_PROPERTY 吗,或者如何避免前向声明?
  • 我可以在插槽中返回一个引用吗(可能是一些技巧,例如一个包装指针并“覆盖”脚本的类 operator.,如果存在类似的东西)或
  • 我可以以某种方式在 QtScript 中将 QVariant(A*) 取消引用到 A 吗?
  • 最佳答案

  • 您的属性(property)类型是 A ,不是 A* ,这就是为什么你会得到非常合理的错误。
  • 您应该使用 QScriptValue .看看这个代码。它工作正常:
    class A; // forward declaration necessary, see explanation above

    class B : public QObject
    {
    Q_OBJECT

    // Using QScriptValue, made from A instead of A to allow script work correctly with an object
    Q_PROPERTY(QScriptValue a READ GetA)

    public slots:
    QScriptValue GetA() {
    //making QScriptValue from A. Type conversion in C style only due to limitation of incomplete type
    //In real app it's beter to put defenition of this slot after A's defenition
    return static_cast<QScriptEngine*>(parent())->newQObject((QObject*)mA);
    }

    private:
    A* mA;
    // ...
    public:
    //I decided my object will be a child of scriptEngine, but you can take a pointer to it in some other way
    B(QScriptEngine * parent);
    };

    class A: public QObject
    {
    Q_OBJECT
    public slots:
    QString GetName() const {return "a name";}
    public:
    A(QScriptEngine*parent):QObject(parent){}

    };

    B::B(QScriptEngine *parent):QObject(parent), mA(new A(parent)){}
  • 关于Qt:Q_PROPERTY 带有指针和用于 QtScript 访问的前向声明,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6959501/

    25 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com