Почему я не могу прочитать открытые данные C ++ из QML? - PullRequest
0 голосов
/ 22 января 2019

Я создал этот класс, чтобы использовать его в качестве контейнера данных. Я читаю из json некоторые данные (в c ++) и заполняю список GUIArea, который я храню в списке m_guiAreas в dataHandler. В определенный момент из QML я запрашиваю серию выделенных областей для dataHandler. DataHandler заполняет QList m_selectedGuiAreas и испускает сигнал selectedAreasChanged (). Теперь я ожидаю увидеть сетку прямоугольника, заполненного выбранными данными, но ничего не вижу. На уровне C ++, когда выбрана selectedAreasChanged (), результат m_selectedGuiAreas заполнен правильными данными, но на уровне QML он кажется пустым или, возможно, данные считываются неправильно.

Вот класс, который я использую в качестве оболочки для переноса данных на уровень QML:

class GUIArea : public QObject
    {
        Q_OBJECT
        Q_PROPERTY(QString id READ id )
        Q_PROPERTY(QString configurations READ configurations )

        ...

    public:
        explicit GUIArea(QObject *parent = nullptr): QObject (parent) {}

        QString id() {return m_id;}
        void id(QString newId) {m_id = newId;}

        QString configurations() {return m_configuration; }
        void configurations(QString newConfiguration) {m_configuration = newConfiguration;}

        ...

    private:
        QString m_id;
        QString m_configuration;
    };

здесь ниже - класс dataHandler, где я объявляю списки данных, считанных из Json, и которые я конвертирую из Qlist в QQmlPropertyList (я вижу это в некоторых руководствах по QML для предоставления свойств c ++ для QML). Метод initializeDatas считывает данные, хранящие их в m_GUIAreas, а затем выбирает данные для отправки в QML в m_selectedGUIAreas, испуская в конце сигнал selectedGUIAsChanged ().

class dataHandler : public QObject
    {
        Q_OBJECT
        Q_PROPERTY(QQmlListProperty<GUIArea> selectedGuiAreas READ selectedGuiAreas NOTIFY selectedAreasChanged)

public:
    explicit dataHandler(QObject *parent = nullptr);
    static dataHandler* instance();

    QQmlListProperty<GUIArea> selectedGuiAreas();
    ...

public slots:
        void initializeDatas(const json& blocksList);
    ... 

signals:
    ...
    void selectedAreasChanged();
    ...
private:   
    ... 
    QList<GUIArea *> m_guiAreas;
    QList<GUIArea *> m_selectedGuiAreas;
};

в основном файле, тогда dataHandler объявляется как свойство: вот код:

  QQuickView view;
  ...
  view.engine()->rootContext()->setContextProperty("dataHandler", dataHandler::instance());
  ...
  view.show();

часть страницы, которую я хочу визуализировать в QML, находится ниже. AreaButton - это прямоугольник внутри текста и псевдоним текста свойства.

Grid {
    id: areasButtonsGrid
    columns: 4
    anchors.fill: parent

    Repeater {
        model: dataHandler.selectedGuiAreas
        delegate:
            AreaButton {
                text: qsTr(model.modelData.programName)
            }
    }
}

1 Ответ

0 голосов
/ 23 января 2019

Код не может быть проанализирован, так как он неполный, поэтому я просто предоставлю рабочий код, чтобы вы могли проанализировать, где проблема:

main.cpp

#include <QGuiApplication>
#include <QQmlContext>
#include <QQuickView>
#include <QTimer>

class GUIArea : public QObject
{
    Q_OBJECT
    Q_PROPERTY(QString id READ id  CONSTANT)
    Q_PROPERTY(QString configurations READ configurations CONSTANT)
public:
    GUIArea(const QString & id="", const QString & configurations="", QObject *parent=nullptr):
        QObject(parent), m_id(id), m_configurations(configurations)
    {}
    QString id() const{return m_id;}
    QString configurations() const{return m_configurations;}
    void setId(const QString &id){
        m_id = id;
    }
    void setConfigurations(const QString &configurations){
        m_configurations = configurations;
    }
private:
    QString m_id;
    QString m_configurations;
};

class DataHandler: public QObject
{
    Q_OBJECT
    Q_PROPERTY(QQmlListProperty<GUIArea> selectedGuiAreas READ selectedGuiAreas NOTIFY selectedAreasChanged)
    using QObject::QObject;
public:
    static DataHandler& instance(){
        static DataHandler handler;
        return handler;
    }
    QQmlListProperty<GUIArea> selectedGuiAreas(){
        return QQmlListProperty<GUIArea>(this, m_selectedGuiAreas);
    }
    void append(GUIArea *area){
        if(area){
            m_selectedGuiAreas << area;
            emit selectedAreasChanged();
        }
    }
signals:
    void selectedAreasChanged();
private:
    QList<GUIArea *> m_selectedGuiAreas;
};

int main(int argc, char *argv[])
{
    QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
    QGuiApplication app(argc, argv);
    qmlRegisterType<GUIArea>();
    QQuickView view;
    view.rootContext()->setContextProperty("dataHandler", &DataHandler::instance());
    view.setSource(QUrl(QStringLiteral("qrc:/main.qml")));
    view.show();
    QTimer timer;
    static int counter =0;
    QObject::connect(&timer, &QTimer::timeout, [](){
        GUIArea *area = new GUIArea(QString::number(counter),
                                    QString("configuratio-%1").arg(counter),
                                    &DataHandler::instance());
        DataHandler::instance().append(area);
        counter++;
    });
    timer.start(1000);
    return app.exec();
}
#include "main.moc"

main.qml

import QtQuick 2.12

Grid {
    id: areasButtonsGrid
    columns: 5
    width: 640
    height: 480
    spacing: 20
    Repeater {
        model: dataHandler.selectedGuiAreas
        delegate:
            Rectangle{
            width: 100
            height: 100
            color: "blue"
            Text {
                anchors.fill: parent
                text: qsTr(model.modelData.configurations)
                verticalAlignment: Text.AlignVCenter
                horizontalAlignment: Text.AlignHCenter
            }
        }
    }
}
...