Unable to connect signal to slot in another class

Sid411 picture Sid411 · Aug 7, 2013 · Viewed 19.9k times · Source

I have 2 classes. Class A and Class B. I am emitting a signal from class A which I want the B to recieve.

I am doing it following way

In Listener File

Header File:
  Class Listener:public DDSDataReaderListener
  {
     //Some code
    public:
       A m_objectSendData;
  }

Implementation File:

  void Listener::ondataavailable(DDSDataReader *reader)
 {
  m_objSendData.GetDDSData();
 }

In Class A

Header File:

Class A:public QObject
{
  Q_OBJECT
  public:
    void GetDDSData();
  signals:
    void Signal_Data();
}

.cpp File

 A::A(QWidget *parent):QObject(parent)
{
}

void A::GetDDSData()
 {
   emit Signal_Data();
 }   

In Class B

Header File:

  Class B:public QObject
  {
    Q_Object
    public:
    A objGetData;

    public slots:
    void getData();
  }

Implementation File:

 B::B(QWidget *parent):QObject(parent)
{
   //Some part of code

  connect(&objGetData,SIGNAL(Signal_Data()),this,SLOT(getData());
 }

 void B::getData()
 {
    //Watever is to be updated
  }

I tried debugging. It is going till emit part correctly. However it is not reaching the slot. Can someone please help me with this. Thank You.

Answer

TheDarkKnight picture TheDarkKnight · Aug 7, 2013

Without full code, it's quite difficult to identify the exact issue of the problem, so I'll outline a few important points to check.

To ensure you can use the signal and slots mechanism, you should ensure that your class is derived, from QObject or a class already derived from QObject in its hierarchy and your class must contain the Q_OBJECT macro, for example: -

class A : public QObject // derived from QObject
{
    Q_OBJECT // your class must have this macro for signals and slots

    public:
    A();
};

Omitting the macro is probably the most common of mistakes.

To specify a slot, you add it to either the public or private slot section of your class: -

class B : public QObject // derived from QObject
{
    Q_OBJECT // your class must have this macro for signals and slots

    public:
    B();

    public slots:
        void SlotB(); // slot declared public

    private slots:
        void SlotBPrivate(); // slot declared private.
}; 

Once a signal is declared in a class, a slot to receive the signal should match the arguments passed in and when you connect a signal to a slot, you must not add the function argument names.

Therefore: -

connect(&objectA, SIGNAL(SignalA(int in), this, SIGNAL(SlotA(int param)); //will fail due to the argument names

It should be: -

connect(&objectA, SIGNAL(SignalA(int), this, SIGNAL(SlotA(int));

Finally, if you're using Qt 5, you can use the new connection call, which doesn't require you to specify any argument, but instead takes the addresses of slot and signal functions.

connect(&objectA, &A::SignalA, this, &B::SlotA));

Since it references the address of a function, in actuality, the functions don't need to be classed as a slot and will still be called.

Hope that helps.