C++ 从C++;
我在Qt中更改QML窗口的文本时遇到一些问题。我有一个C++文件,它调用一个线程,从那里我试图改变文本标签的值。线程正在正确运行,但QML中的文本值没有更改。以下是我的代码的一部分: main.cpp:C++ 从C++;,c++,qt,qml,C++,Qt,Qml,我在Qt中更改QML窗口的文本时遇到一些问题。我有一个C++文件,它调用一个线程,从那里我试图改变文本标签的值。线程正在正确运行,但QML中的文本值没有更改。以下是我的代码的一部分: main.cpp: int main(int argc, char *argv[]) { QGuiApplication app(argc, argv); QQmlApplicationEngine engine; engine.load(QUrl(QStringLiteral("qrc:/
int main(int argc, char *argv[]) {
QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
engine.load(QUrl(QStringLiteral("qrc:///template.qml")));
QQuickItem *label = engine.rootObjects().at(0)->findChild<QQuickItem*>("myLabel");
thread2 thread(label);
thread.start();
}
thread2::thread2(QQuickItem *label) {
this->label = label;
}
void thread2::run() {
int test = 0;
char buffer[10];
int speed = 100;
while(1) {
speed++;
sprintf(buffer,"%d km/h",speed);
this->label->setProperty("text", QString(buffer));
QThread::msleep(1000);
qDebug()<<"tic: "<<buffer<<endl;
}
Window {
id: window
visible: true
width: 360
height: 360
Component {
id: fruitDelegate
Row {
spacing: 10
Text { text: name }
Text { text: '$' + cost }
}
}
Text {
width: 99
height: 19
text: qsTr("Speed: ")
anchors.verticalCenterOffset: 1
anchors.horizontalCenterOffset: 0
anchors.centerIn: parent
objectName: "lab"
}
Text {
width: 38
height: 19
text: qsTr(" 0 ")
anchors.verticalCenterOffset: 1
anchors.horizontalCenterOffset: 46
anchors.centerIn: parent
objectName: "myLabel"
}
}
有人能告诉我为什么不工作吗?我的错在哪里
谢谢 您不应该从其他线程修改UI。改用信号/插槽。 您也不应该从
QThread
创建子类(创建一个worker并将其移动到另一个线程中)
您有两个错误:
- 您不应该从另一个线程更新GUI,run方法是在另一个线程中执行的,因此Qt不能保证它正常工作
- 不要将QML元素导出到C++,因为它会带来很多问题,因为通过对象名多次获得对象是不可能的,另外一个不便之处是该项的生命周期由QML确定,所以在给定的时刻它可以被消除,这样标签可以指向一个未保留的内存,从而使用它。相反,它将C++对象输出到qML。
#ifndef THREAD_H
#define THREAD_H
#include <QThread>
class Thread : public QThread
{
Q_OBJECT
public:
Thread(QObject *parent=nullptr);
~Thread() override;
Q_SLOT void stop();
Q_SIGNAL void textChanged(const QString & text);
protected:
void run() override;
};
#endif // THREAD_H
欲了解更多信息,请阅读:
class Worker: public QObject
{
Q_OBJECT
public slots:
void run()
{
while(1) {
QThread::msleep(1000);
emit changed(QDateTime::currentDateTime().toString());
}
}
signals:
void changed(QString);
};
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
QThread* th = new QThread();
Worker* worker = new Worker();
worker->moveToThread(th);
QObject::connect(th, &QThread::started, worker, &Worker::run);
th->start();
QQuickView view(QStringLiteral("qrc:/Main.qml"));
QObject* o = view.rootObject();
QObject::connect(worker, SIGNAL(changed(QString)), o, SIGNAL(change(QString)));
view.showMaximized();
return app.exec();
}
#ifndef THREAD_H
#define THREAD_H
#include <QThread>
class Thread : public QThread
{
Q_OBJECT
public:
Thread(QObject *parent=nullptr);
~Thread() override;
Q_SLOT void stop();
Q_SIGNAL void textChanged(const QString & text);
protected:
void run() override;
};
#endif // THREAD_H
#include "thread.h"
#include <QDebug>
Thread::Thread(QObject *parent):
QThread(parent)
{
}
Thread::~Thread()
{
}
void Thread::stop()
{
requestInterruption();
wait();
}
void Thread::run()
{
int speed = 100;
QString text;
while(!isInterruptionRequested()) {
speed++;
text = QString("%1 km/h").arg(speed);
Q_EMIT textChanged(text);
QThread::msleep(1000);
qDebug()<<"tic: "<< text;
}
}
#include "thread.h"
#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
Thread thread;
QObject::connect(&app, &QGuiApplication::aboutToQuit, &thread, &Thread::stop);
thread.start();
QQmlApplicationEngine engine;
engine.rootContext()->setContextProperty("thread", &thread);
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
return -1;
return app.exec();
}
// ...
Text {
id: txt
width: 38
height: 19
text: qsTr(" 0 ")
anchors.verticalCenterOffset: 1
anchors.horizontalCenterOffset: 46
anchors.centerIn: parent
objectName: "myLabel"
}
Connections{
target: thread
onTextChanged: txt.text = text
}
// ...