QT #2 : Signals and Slots

In this section, we will sneak peak into one of the key concepts introduced by Qt – Signals and Slots. Qt uses Signals and slots for communicating between objects. Or to be more precise, all objects that derieved from QObjects (or one of its subclasses).

Objects often want to communicate with each other, particularly in GUI programming where different widgets would want to communicate and notify another widget about an event which the recieving widget might be interested in. In Qt, classes (which inherits from QObjects), emits a signal when a particular event occurs. Slots are functions which would be called when a signal is emitted, quite similar to callbacks. Most important fact to note here is that the signal emitting class has no clue on which classes/slots recieve the event, or in other words, they are loosely coupled.Furthermore, they are type-safe.

Let us go ahead and write some sample code. We will first define our Source class, which would emit the signal.

// source.h

#ifndef SOURCE_H
#define SOURCE_H

#include <QObject>
#include <QDebug>

class Source : public QObject
{
    Q_OBJECT
    QString _message;

public:
    explicit Source(QObject *parent = nullptr);
    void TriggerEvent();

public slots:

signals:
    void messageChanged(QString message);

};

#endif // SOURCE_H

As seen in our header definition, the Source class has a single signal, namely messageChanged, which accepts a QString parameter. We also have a public method named TriggerEvent(), which would use to emit the signal. Let us go ahead and define our TriggerEvent() method.

// source.cpp
#include "source.h"

Source::Source(QObject *parent)
    : QObject(parent)
{

}

void Source::TriggerEvent()
{
    QString message = "Say Hello !!!";
    qInfo() << "Emitting Signal with message "<<message;
    emit messageChanged(message);
}


As you can observe, the TriggerEvent doesn’t do anything fancy. It writes some debug message, before emitting the messageChanged signal using the emit call. We are also passing a QString as required by the method signature.

We will now go ahead define our Destination class, the one, which is interested in the signal, and contains slots to recieve them.

// Destination.h
#ifndef DESTINATION_H
#define DESTINATION_H

#include <QObject>
#include <QDebug>
class Destination : public QObject
{
    Q_OBJECT
public:
    explicit Destination(QObject *parent = nullptr);

public slots:
    void OnMessageRecieved(QString message);

signals:

};

#endif // DESTINATION_H

The Destination class has a slot, which has the same signature as the Source‘s signal messageChanged. For debugging purpose, let us log some useful information in the slot.

// Destination.cpp

#include "destination.h"

Destination::Destination(QObject *parent)
    : QObject{parent}
{

}

void Destination::OnMessageRecieved(QString message)
{
    qInfo() << "Recieved Message : " << message;
}


As observed in the above code, the slot merely prints the recieved message using qInfo.

So far, we have declared the Source which emits signal and Destination which declares the slots and recieves the emitted signal. But how does the Qt’s meta-object system know which slots to bind to a signal. This is done using the QObject::connect() method.

QCoreApplication app(argc, argv);
Source sourceObj(app);
Destination destinationObj(app);

QObject::connect(&sourceObj,&Source::messageChanged,&destinationObj,&Destination::OnMessageRecieved);
sourceObj.TriggerEvent();

The QObject::connect accepts 4 parameter – reference to the instance of Source class, the signal that is emitted, reference to the instance of Destination class, and the slot in Destination to which the signal needs to be binded.

We then use the Source.TriggerEvent() method to emit the signal. The Qt’s meta-object system then uses wiring defined by the connect() method to trigger the slots associated with the signal.

That’s all needed to get started with Signals and Slots. In the next part, we will look into Q_Property.

Advertisement

One thought on “QT #2 : Signals and Slots

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s