繁体   English   中英

从C ++更改QML对象值

[英]Changing QML Object value from C++

我创建了一个QML类,例如

import QtQuick 2.2
import QtQuick.Controls 1.4
import QtQuick.Controls.Styles 1.4
import QtQuick.Extras 1.4

Rectangle {
    width: 80
    height: 200
    property double myVal: 15

    Timer {
        running: true
        repeat: true
        interval: 1
        onTriggered: gauge.value = myVal
    }

    Gauge {
        objectName: "gauge"
        id: gauge
        anchors.fill: parent
        anchors.margins: 10

        value: myVal
        Behavior on value {
            NumberAnimation {
                duration: 1000
            }
        }

        style: GaugeStyle {
            valueBar: Rectangle {
                implicitWidth: 16
                color: Qt.rgba(gauge.value / gauge.maximumValue, 0, 1 - gauge.value / gauge.maximumValue, 1)
            }
        }
    }
}

我想从我的c ++文件中更改值。 为此,我创建了一个setDataToGauge()方法,该方法类似于

void MainWindow::setDataToGauge(double newVal){

    QQmlApplicationEngine engine;
    QQmlComponent component(&engine, QUrl::fromLocalFile("gauge.qml"));
    QObject object = component.create();
    QObject *myGauge = object->findChild<QObject*>("gauge");

    if(myGauge){
        myGauge->setProperty("value",newVal);
        qDebug() << myGauge->property("value");

    }

}

这个。 但是,它不会更改仪表的值。 我尝试了不同的方法,但是找不到解决方案。 当我掉落

    Behavior on value {
        NumberAnimation {
            duration: 1000
        }
    }

来自QML文件值的这部分正在更改,但仪表视图未更改。 另外,我正在添加我的c ++文件的完整代码

#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QDebug>
#include <QDateTime>
#include <QtQuickWidgets/QQuickWidget>
#include <QtQml>
#include <QObject>

QObject *object;

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow),
    m_serial(new QSerialPort(this))
{
    ui->setupUi(this);

    ui->gaugeWidget->setSource(QUrl::fromLocalFile("gauge.qml"));
    ui->gaugeWidget->setUpdatesEnabled(true);

    QQmlApplicationEngine engine;
    QQmlComponent component(&engine, QUrl::fromLocalFile("gauge.qml"));
    object = component.create();

    setDataToGauge(60.0);
}

MainWindow::~MainWindow()
{
    delete ui;
}

void MainWindow::setDataToGauge(double newVal){

    QObject *myGauge = object->findChild<QObject*>("gauge");

    if(myGauge){
        QQmlProperty::write(myGauge, "value", newVal);
        qDebug() << myGauge->property("value");
}

}

那里有什么问题?

在尝试解决方案时,您正在创建另一个仪表,而该仪表没有显示,因为QQmlApplicationEngine是一个局部变量,在完成执行后将被删除,此外, QQmlApplicationEngine需要一个WindowApplicationWindow ,而不是Rectangle类的Item

另一方面,建议使用qresource存储.qml,因为否则,您每次编译可执行文件的那一面都必须复制它们。

还不建议从C ++访问QML对象,最好使用setContextProperty()将C ++对象导出到QML。

一个简单的解决方案是创建一个信号,该信号通过Connections :: Connections

*。H

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>

namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = nullptr);
    ~MainWindow();
    void setDataToGauge(double newVal);
signals:
    void dataGaugeChanged(double dataToGauge); // signal
private:
    Ui::MainWindow *ui;
};

#endif // MAINWINDOW_H

*的.cpp

#include "mainwindow.h"
#include "ui_mainwindow.h"

#include <QQmlEngine>
#include <QQmlContext>


MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    ui->gaugeWidget->engine()->rootContext()->setContextProperty("MainWindow", this);
    ui->gaugeWidget->setSource(QUrl("qrc:/gauge.qml"));
}

MainWindow::~MainWindow()
{
    delete ui;
}

void MainWindow::setDataToGauge(double newVal){
    emit dataGaugeChanged(newVal);
}

gauge.qml

import QtQuick 2.2
import QtQuick.Controls 1.4
import QtQuick.Controls.Styles 1.4
import QtQuick.Extras 1.4

Rectangle {
    width: 80
    height: 200

    Gauge {
        id: gauge
        anchors.fill: parent
        anchors.margins: 10

        Behavior on value {
            NumberAnimation {
                duration: 1000
            }
        }

        style: GaugeStyle {
            valueBar: Rectangle {
                implicitWidth: 16
                color: Qt.rgba(gauge.value / gauge.maximumValue, 0, 1 - gauge.value / gauge.maximumValue, 1)
            }
        }
    }
    Connections{
        target: MainWindow
        onDataGaugeChanged: gauge.value = dataToGauge
    }
}

另一种选择是创建一个Q_PROPERTY并进行绑定:

*。H

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>

namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT
    Q_PROPERTY(double dataGauge READ dataGauge WRITE setDataGauge NOTIFY dataGaugeChanged)

public:
    explicit MainWindow(QWidget *parent = nullptr);
    ~MainWindow();

    double dataGauge() const;
    void setDataGauge(double dataGauge);
signals:
    void dataGaugeChanged();
private:
    Ui::MainWindow *ui;
    double mDataGauge;
};

#endif // MAINWINDOW_H

*的.cpp

#include "mainwindow.h"
#include "ui_mainwindow.h"

#include <QQmlEngine>
#include <QQmlContext>

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    ui->gaugeWidget->engine()->rootContext()->setContextProperty("MainWindow", this);
    ui->gaugeWidget->setSource(QUrl("qrc:/gauge.qml"));
}

MainWindow::~MainWindow()
{
    delete ui;
}

double MainWindow::dataGauge() const
{
    return mDataGauge;
}

void MainWindow::setDataGauge(double dataGauge)
{
    if(mDataGauge == dataGauge)
        return;
    mDataGauge = dataGauge;
    emit dataGaugeChanged();
}

* .qml

import QtQuick 2.2
import QtQuick.Controls 1.4
import QtQuick.Controls.Styles 1.4
import QtQuick.Extras 1.4

Rectangle {
    width: 80
    height: 200

    Gauge {
        id: gauge
        anchors.fill: parent
        anchors.margins: 10
        value: MainWindow.dataGauge // binding

        Behavior on value {
            NumberAnimation {
                duration: 1000
            }
        }

        style: GaugeStyle {
            valueBar: Rectangle {
                implicitWidth: 16
                color: Qt.rgba(gauge.value / gauge.maximumValue, 0, 1 - gauge.value / gauge.maximumValue, 1)
            }
        }
    }
}

可以在以下链接中找到这两种解决方案。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM