QT study notes of QML and C++ (on)

QT study notes of QML and C++ (on)

 

table of Contents

QT study notes of QML and C++ (on)

C++ object registration to the meta object system

Register the C++ class to the Qml system

C++ create/get Qml object

Qml calls C++ object public functions

Qml access to C++ object properties (object member variables)

Qml calls C++ object slot functions

C++ object registration to the meta object system

  • Use Q_INVOKABLE to declare, this macro declares the function as a function callable by the meta-object system. QtQuick is also in the meta-object system, so this function can also be accessed.
class TestCpp : public QObject
{
    Q_OBJECT
public:
    explicit TestCpp(QObject *parent = nullptr);
    
    Q_INVOKABLE  void setNumber(int number);
    Q_INVOKABLE  void getNumber();
    
private:
    int m_iNumber{};    
    
signals:
    
};
  • achieve
void TestCpp::setNumber(int number)
{
    m_iNumber = number;
}

int TestCpp::getNumber()
{
    return  m_iNumber;
}
  • Register the TestCpp class in QML
  • ①Add header file (in main.cpp file)
#include <QQmlContext>
#include "testcpp.h"
  • ② Instantiate the object and register it (in the main.cpp file)
QQmlApplicationEngine engine;

//添加如下代码  
TestCpp testObj;
testObj.setNumber(12345);
engine.rootContext()->setContextProperty("testObj", &testObj);
  • ③ Use it in the Qml file (in the main.qml file)
import QtQuick 2.12
import QtQuick.Controls 2.5

ApplicationWindow {
    visible: true
    width: 640
    height: 480
    title: qsTr("QmlTest")


    Button{
        id: btn1
        width: 120
        height: 50
        anchors.centerIn: parent
        onClicked:
            text = testObj.getNumber();
    }

    Button{
        id: btn2
        width: 120
        height: 50
        anchors.top: btn1.bottom
        anchors.margins: 15
        anchors.horizontalCenter: btn1.horizontalCenter
        onClicked:
            text = testObj.setNumber(67890);
    }
}
  • effect

Register the C++ class to the Qml system

  • qmlRegisterType Registers C++ classes: When registering on the C++ side, the C++ classes are not instantiated, and the instantiation is done on the Qml side.
template<typename T>
int qmlRegisterType(const char *uri, int versionMajor, int versionMinor, const char *qmlName);

template<typename T, int metaObjectRevision>
int qmlRegisterType(const char *uri, int versionMajor, int versionMinor, const char *
qmlRegisterType<MySliderItem>("com.mycompany.qmlcomponents", 1, 0, "Slider");
  • use
import com.mycompany.qmlcomponents 1.0

Slider {
    // ...
}

【Exercise example】

  • main.qml file

C++ create/get Qml object

  • Code
import QtQuick 2.12
import QtQuick.Controls 2.5
import QtQuick.Window 2.2

Window {
    width: 300
    height: 300
    color: "pink"
}
  • ② main.cpp add
//添加头文件
#include <QQmlComponent>

//添加代码
/*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);*/

QQmlComponent qmlComponent(&engine);                            
qmlComponent.loadUrl(QUrl(QStringLiteral("qrc:/TestQml.qml"))); 

QObject* qmlTest = qmlComponent.create();                       
qmlTest->setParent(engine.rootObjects()[0]);    

engine.rootContext()->setContextProperty("qmlTest", qmlTest);   
  • ③ main.qml add
ApplicationWindow {
    visible: true
    width: 640
    height: 480
    title: qsTr("QmlTest")


    Button{
        id: btn1
        width: 120
        height: 50
        anchors.centerIn: parent
        onClicked: {
            qmlTest.visible = true;
            qmlTest.color  = "green"
        }
    }

    Button{
        id: btn2
        width: 120
        height: 50
        anchors.top: btn1.bottom
        anchors.margins: 15
        anchors.horizontalCenter: btn1.horizontalCenter
        onClicked:{
           qmlTest.color  = "blue"
           qmlTest.visible = true;
        }
    }
}
  • Modify TestQml.qml and add a rectangle inside the form

  • main.cpp, find the object of the child form through findChild
QObject *qmlRect = qmlTest->findChild<QObject*>("rectangle");
qmlRect->setProperty("color", "pink");                       
  • effect:

Qml calls C++ object public functions

  • C++ Q_INVOKABL registered function.

Qml access to C++ object properties (object member variables)

  • Use   Q_PROPERTY 
Q_PROPERTY(int number READ getNumber WRITE setNumber NOTIFY numberChanged)
  • In testcpp.h

  • Pay attention to the position of the code (the line below Q_OBJECT), and then add a signal, when the attribute change is triggered, the signal is numberChanged
  • Register in main.cpp
QQmlApplicationEngine engine;

//添加如下代码  
TestCpp testObj;
testObj.setNumber(12345);
engine.rootContext()->setContextProperty("testObj", &testObj);
  • main.qml add

Qml calls C++ object slot functions

public slots:  
     void setNumber(int number);
void TestCpp::setNumber(int number)
{
    m_iNumber += number;
}
  • Qml can directly call the slot function, because the slot function is originally in the meta-object system, and the C++ class has been registered in the meta-object system.

Guess you like

Origin blog.csdn.net/baidu_41388533/article/details/115219122