Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

C++ signal to a QML file



  • Hello,

    I'm still learning about signals and slots. With a signal from C++ to QML , rather than calling a certain slot (function) in the QML file, is it possible to call and run all the code in a qml file?

    //.qml 
    
    function callCPP(key) {
         var value= myGlobalObject.readJson(key)
         return value
    }
    
    
            speedt.text:  callCPP("Engine_Spd")
            power.text:  callCPP("Engine_Power")
            .
            .
            .
    
    

    sparing all the details... I have a file watcher set up in my C++ and when a change is made I want to call the qml file, so that all of the text boxes get updated with the new correct data. The function calls are just statements in the qml file, so I'm wondering how I can run through them all when a signal is emitted from C++??
    Also, any tips on signals and slots are more than welcomed! thanks.



  • @texasRanger Hey,

    If you want to "run" a qml file, you have to create it dynamicly, not the best idea if all you want is to update labels..

    You can emit a signal(signalFromChanged();) from the slot you have connected the filewatchers fileChanged signal to, then receive the update through onSignalFromChanged: {} in qml. Then in onSignalFromChanged you can call the function from your qml file.

    To do this you must register the C++ file as a qml type in main.cpp with;
    -----------------FileWatcher.h--import statement, major, minor - qml type

    qmlRegisterType<FileWatcher>("libFileWatcher", 1, 0, "FileWatcherClass");
    

    Then in the QML file you can do:

    import libFileWatcher 1.0
    FileWatcherClass {
        id: fileWatcher
        onSignalFromChanged: {
            speedt.text=callCPP("Engine_Spd");
            power.text=callCPP("Engine_Power");
        }
    }
    

    The cpp file must have a Q_PROPERTY reading the json list, which makes you able to use the function callCPP to read a object from the QJsonObject Class with

    fileWatcher.readJson.find(key);
    

    Hope this helps you get started



  • @texasRanger said in C++ signal to a QML file:

    C++ to QML

    One way to react to c++ signal in QML is using QML Connection type.
    first expose the instance of your object to QML using Context Property

    //cpp
    signals: 
     void changeMade()
    
    //qml
    Connections {
        target: yourObject 
        onChangeMade {
             // js
        }
    }
    

  • Moderators

    It is also possible to connect a C++ signal to a QML "slot" from the C++ side: https://doc.qt.io/qt-5/signalsandslots-syntaxes.html#connecting-c-objects-to-qml-objects

    Note that any arguments must the QVariant type:

    class CppGui : public QWidget {
        Q_OBJECT
    
        QPushButton *button;
    
    signals:
        void cppSignal(const QVariant& sentMsg) const;
    
    public:
        CppGui(QWidget *parent = nullptr) : QWidget(parent) {
            button = new QPushButton("Click Me!", this);
            connect(button, &QPushButton::clicked, [=] {
                emit cppSignal("Hello from C++!");
            });
        }
    };
    
    // QmlGui.qml
    Rectangle {
        width: 100; height: 100
    
        function qmlSlot(receivedMsg) {
            console.log("QML received: " + receivedMsg)
        }
    }
    
    auto cppObj = new CppGui(this);
    auto quickWidget = new QQuickWidget(QUrl("QmlGui.qml"), this);
    auto qmlObj = quickWidget->rootObject();
    
    // Connect C++ signal to QML slot
    connect(cppObj, SIGNAL(cppSignal(QVariant)),
            qmlObj, SLOT(qmlSlot(QVariant)));
    

Log in to reply