-1

I am having trouble in accessing a property in QML.

QList is a property and i am able to access that but when i try to access the properties of classB in QML i am getting type error/Undefined. Following is the code:

[EDIT 1] - Changed the QList to QVariantList Based on the suggestion:

//ClassA.h

#include <QObject>
#include "classb.h"

Q_DECLARE_METATYPE(QList<ClassB*>)
class ClassA : public QObject
{
    Q_OBJECT
    Q_PROPERTY(QVariantList objList READ getClassBDetails) //[EDIT 1]

public:
    explicit ClassA(QObject *parent = nullptr);

    QVariantList getClassBDetails(); //[EDIT 1]

private:
    QVariantList  m_list; //[EDIT 1]
    ClassB m_Bobj;

};

//ClassA.cpp

#include "classa.h"

ClassA::ClassA(QObject *parent) : QObject(parent)
{
    m_list.append(QVariant::fromValue(&m_Bobj)); //** Appending to QvariantList
}

QVariantList  ClassA ::getClassBDetails() //[EDIT 1]
{
    return m_list;
}

//ClassB.h

#include <QObject>

class ClassB : public QObject
{
    Q_OBJECT
    Q_PROPERTY(int val READ getval WRITE setval NOTIFY valChanged)
public:
    explicit ClassB(QObject *parent = nullptr);

    int m_val = 10;

    int getval();
    void setval(int val);

signals:
    void valChanged();

public slots:
};

//ClassB.cpp

#include "classb.h"
ClassB::ClassB(QObject *parent) : QObject(parent)
{

}

int ClassB::getval()
{
    return m_val;
}

void ClassB::setval(int val)
{
    m_val = val;
    emit valChanged();
}

//Main.cpp

#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>
#include "classa.h"

int main(int argc, char *argv[])
{
    QGuiApplication app(argc, argv);

    ClassA aObj;
    QQmlApplicationEngine engine;
    engine.rootContext()->setContextProperty("classAObj",&aObj);
    engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
    if (engine.rootObjects().isEmpty())
        return -1;

    return app.exec();
}

//Main.qml

import QtQuick 2.6
import QtQuick.Window 2.2

Window {
    visible: true
    width: 640
    height: 480
    title: qsTr("Hello World")

    Component.onCompleted: {
        console.log("value========",classAObj.objList[0].val) //** Same error  
    }
}

If i try to access "classAObj.objList[0].val" i am getting TypeError: Cannot read property 'val' of undefined error. What is that i am doing wrong here ?

pra7
  • 834
  • 2
  • 21
  • 50

1 Answers1

1

What you are doing wrong is expecting the [] operator to work. It won't.

There is one way to get it to work, if you convert your QList to a QVariantList which QML will automatically convert to a JS array.

But what I actually recommend is to simply use accessory functions instead, implement a get(index) and if necessary a set(index) function and you are set.

You can also take a look at this generic object list model, which is very flexible, powerful and useful, supports any QObject children, including objects that are defined in QML, declarative and nested definitions and last but not least, it can be directly used as a model.

dtech
  • 47,916
  • 17
  • 112
  • 190
  • I actually tried with **QVariantList**, But I was not able to insert `ClassB` object to it .Can you please give an example? – pra7 Aug 19 '17 at 10:39
  • 1
    I am not sure how "editable" such implicitly converted lists are. I suggest you don't bother with that. If you want to insert from C++, you will obviously be inserting a `QVariant::fromValue(objPtr)`, and since it is just a `QList` you insert the same way you insert in any `QList`. – dtech Aug 19 '17 at 11:19
  • Thanks and i am able to pass now . After that can I access using `[ ]` operator ?? Because I did like this `var res = classAObj.objDetails` and later I tried to print it something like this `res[0]` ... And getting same error .. – pra7 Aug 19 '17 at 11:23
  • Did you change to `QVariantList`? It should work. It is possible that you may need to return from a `Q_INVOKABLE` function rather than use a property. As I already recommended - don't bother with that. Not exactly sure why you insist to make your live harder. – dtech Aug 19 '17 at 11:38
  • Yes i changed in `Q_PROPERTY` declaration and also return type of function `getClassBDetails` to QVariantList, it didn't work. I also changed `getClassBDetails` to `Q_INVOKABLE` and called directly from QML even that didn't work. I don't know why it is not working. – pra7 Aug 19 '17 at 11:53
  • I don't know why people are downvoting. it's a serious problem for me. @dtech I tried all possible ways. please help. – pra7 Aug 19 '17 at 14:03
  • I have already given you a better way. I don't know why it is not working. – dtech Aug 19 '17 at 14:08
  • I have edited the question by updated the code to use `QVariantList`. Can you please check? I am stuck here. – pra7 Aug 19 '17 at 14:18