从 C++ 更新 QML 对象的正确方法?
Proper way to update QML object from C++?
我找到了这个 How to modify a QML Text from C++ 但我听说从 C++ 更新 QML 对象不是线程安全的
这样做的正确方法是什么?
我认为最简单的例子(一个文本小部件)足以让我理解。
注意:我没有指出这段代码不是线程安全的,我已经指出你在中的代码不是线程安全的,因为您从与其所属线程不同的线程修改 GUI。
我已经指出 this answer 的代码是危险的,不推荐,因为 QML 元素的生命周期不由开发人员管理,QML 引擎可以在不通知我们的情况下删除它们,因此我建议创建 QObject 以在 C++ 和 QML 之间获取或发送信息。
main.cpp
#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>
class Helper: public QObject{
Q_OBJECT
Q_PROPERTY(QString text READ text WRITE setText NOTIFY textChanged)
QString m_text;
public:
using QObject::QObject;
QString text() const{
return m_text;
}
public slots:
void setText(QString text){
if (m_text == text)
return;
m_text = text;
emit textChanged(m_text);
}
signals:
void textChanged(QString text);
};
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
Helper helper;
QQmlApplicationEngine engine;
engine.rootContext()->setContextProperty("helper", &helper);
const QUrl url(QStringLiteral("qrc:/main.qml"));
QObject::connect(&engine, &QQmlApplicationEngine::objectCreated,
&app, [url](QObject *obj, const QUrl &objUrl) {
if (!obj && url == objUrl)
QCoreApplication::exit(-1);
}, Qt::QueuedConnection);
engine.load(url);
helper.setText("Change you text here...");
return app.exec();
}
#include "main.moc"
main.qml
Text {
id: text1
color: "red"
<b>text: helper.text</b>
font.pixelSize: 12
}
或
Text {
id: text1
color: "red"
text: "This text should change..."
font.pixelSize: 12
}
<b>Connections{
target: helper
onTextChanged: text1.text = text
}</b>
我找到了这个 How to modify a QML Text from C++ 但我听说从 C++ 更新 QML 对象不是线程安全的
这样做的正确方法是什么?
我认为最简单的例子(一个文本小部件)足以让我理解。
注意:我没有指出这段代码不是线程安全的,我已经指出你在
我已经指出 this answer 的代码是危险的,不推荐,因为 QML 元素的生命周期不由开发人员管理,QML 引擎可以在不通知我们的情况下删除它们,因此我建议创建 QObject 以在 C++ 和 QML 之间获取或发送信息。
main.cpp
#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>
class Helper: public QObject{
Q_OBJECT
Q_PROPERTY(QString text READ text WRITE setText NOTIFY textChanged)
QString m_text;
public:
using QObject::QObject;
QString text() const{
return m_text;
}
public slots:
void setText(QString text){
if (m_text == text)
return;
m_text = text;
emit textChanged(m_text);
}
signals:
void textChanged(QString text);
};
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
Helper helper;
QQmlApplicationEngine engine;
engine.rootContext()->setContextProperty("helper", &helper);
const QUrl url(QStringLiteral("qrc:/main.qml"));
QObject::connect(&engine, &QQmlApplicationEngine::objectCreated,
&app, [url](QObject *obj, const QUrl &objUrl) {
if (!obj && url == objUrl)
QCoreApplication::exit(-1);
}, Qt::QueuedConnection);
engine.load(url);
helper.setText("Change you text here...");
return app.exec();
}
#include "main.moc"
main.qml
Text {
id: text1
color: "red"
<b>text: helper.text</b>
font.pixelSize: 12
}
或
Text {
id: text1
color: "red"
text: "This text should change..."
font.pixelSize: 12
}
<b>Connections{
target: helper
onTextChanged: text1.text = text
}</b>