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

YACP (Yet Another Connect Problem)



  • I've read this:

    [http://doc.qt.io/qt-5/qobject.html](link url)

    and this:

    [http://doc.qt.io/qt-5/signalsandslots.html](link url)

    and numerous examples here and on the general web. It doesn't seem like it should be that difficult, but I can't get this working:

    Trying to connect a signal in one class to a slot in another class.

    MessageSorter.h

    #include <QObject>
    #include <QString>
    #include <QUdpSocket>
    #include <QtCore>
    #include <QtNetwork>
    #include <QHash>
    
    //class pcsMessageProcessor;
    
    class MessageSorter : public QObject
    {
        Q_OBJECT    
    
    public:
        explicit MessageSorter(QObject *parent = nullptr);
    
        QByteArray *buffer;
        QNetworkDatagram dataGram;
    
    public slots:
    
        void readyRead();
        void processDataGrams();
    
    signals:
    
        void PDSMessage(QString);
        void PCSMessage(QString &line);
        void N2KMessage(QString);
    
    private:
    
        QUdpSocket *socket;
        QHash<QString, int> hash;
    };
    
    #endif // MESSAGESORTER_H
    

    the function in messageSorter.cpp:

    void MessageSorter::processDataGrams() {
                QByteArray incomingData;
                QString line;
                QString testLine;
                int testKey;
                //int lineCount;
    
                do {
                    incomingData.resize(socket->pendingDatagramSize());
                    socket->readDatagram(incomingData.data(), incomingData.size());
                    line = incomingData;
                    testLine = line;
                    //lineCount = line.count();
                    testLine.remove(":");
                    testLine.remove(6, 24);
                    testKey = hash[testLine];
                    //qDebug()<< " Data: " << testLine;
                    if(testKey == 1){
                        emit PCSMessage(line);
                    }
                } while (socket->hasPendingDatagrams());
    
        }
    

    The receiving class - PCSMessageProcessor.h:

    #ifndef PCSMESSAGEPROCESSOR_H
    #define PCSMESSAGEPROCESSOR_H
    
    #include <QObject>
    #include <QDebug>
    
    //class messageSorter;
    
    class PCSMessageProcessor : public QObject
    {
        Q_OBJECT
    
    public:
        PCSMessageProcessor();
    
    public slots:
        void PCSIncomingMessage(QString message);
    };
    
    #endif // PCSMESSAGEPROCESSOR_H
    

    The function in the .cpp file:

    void PCSMessageProcessor::PCSIncomingMessage(QString message){
        qDebug()<< message;
    }
    

    And finally the connect statement in main.cpp:

    #include <QQmlApplicationEngine>
    #include <QGuiApplication>
    #include <QQmlComponent>
    #include <QQmlContext>
    #include <QObject>
    
    #include "backend.h"
    #include "messageRelay.h"
    #include "messageSorter.h"
    #include "pcsmessageprocessor.h"
    
    int main(int argc, char *argv[])
    {    
        QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
    
        QGuiApplication app(argc, argv);
    
        BackEnd backend;
        MessageSorter messageSorter;
        PCSMessageProcessor pcsMessageProcessor;
    
        QObject::connect(&messageSorter, SIGNAL(MessageSorter::PCSMessage(QString &)),
                 &pcsMessageProcessor, SLOT(pcsMessageProcessor::PCSIncomingMessage(QString &)));    
    
        MessageRelay messageRelay;
        QQmlApplicationEngine engine;    
        engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
    
        engine.rootContext()->setContextProperty("MessageRelay", &messageRelay);
    
        if (engine.rootObjects().isEmpty())
            return -1;
    
        return app.exec();
    }
    

    It compiles, but gives the error "QObject::connect: No such signal MessageSorter::MessageSorter::PCSMessage(QString &) in main.cpp"


  • Moderators

    @MScottM said in YACP (Yet Another Connect Problem):

    MessageSorter::PCSMessage(QString &)

    No need to add the class name there, and no need for reference sign after QString.

    If you want to see exactly what the expected connection string is, you can use QMetaObject class and print method signature.

    SLOT(pcsMessageProcessor::PCSIncomingMessage(QString &))

    Typo: should be PcsMessageProcessor. But, as mentioned above, class name is not needed at all.

    I strongly recommend using the new signal & slot syntax instead:

    QObject::connect(&messageSorter, &MessageSorter::PCSMessage,
                 &pcsMessageProcessor, &pcsMessageProcessor::PCSIncomingMessage);
    

    This will give you a clear compiler error if you provide any incorrect info.


  • Moderators

    @sierdzio said in YACP (Yet Another Connect Problem):

    I strongly recommend using the new signal & slot syntax instead:

    QObject::connect(&messageSorter, &MessageSorter::PCSMessage,
                 &pcsMessageProcessor, &pcsMessageProcessor::PCSIncomingMessage);
    

    This will give you a clear compiler error if you provide any incorrect info.

    +1

    Read more about the differences between the old and new connection syntaxes, see http://doc.qt.io/qt-5/signalsandslots-syntaxes.html



  • @sierdzio && @JKSH
    SOLVED!
    Thank you! Well, I have learned another lesson from this site: don't ignore the compiler. I swear I tried the new syntax, but could never get it to compile and the messages never made sense - probably too many little syntaxical errors that I have been slowly fixing (I'm still a noob). This time however, with one little change to @sierdzio's code (in bold below), that (as you said) the compiler clearly told me was a problem...it worked!!

    QObject::connect(&messageSorter, &MessageSorter::PCSMessage,
    &pcsMessageProcessor, &PCSMessageProcessor::PCSIncomingMessage);

    Thanks again for the help you guys provide on this forum - it helps keep noobies sane.


Log in to reply