PDA

View Full Version : Connect signal to slot from different class



Leutzig
10th December 2015, 20:28
Hi,

I have a signal that I want to connect to a slot found in a different class. How do I do that?
What I thought I could do:

Class A header:

#include "classB.h"

class ClassA
{

Q_Object

public:
ClassA();
...
...

signals:
void stuffChange( const QString & );

private:

ClassB classb
};

And in Class A constructor:

connect(this, SIGNAL( stuffChange( const QString & ) ), &classb, SLOT( setStuff( const QString & ) ) );


Class B header:



class ClassB
{

Q_Object

public:
ClassB();
...
...

public slots:
void setStuff( const QString & );

private:
QString stuff;

};

This gives me the error: LNK2019: unresolved external symbol "public: __ ...
What is the right way to do this?

anda_skoa
10th December 2015, 21:05
The connect looks ok.
Are both ClassA and ClassB derived from QObject?

Cheers,
_

Leutzig
10th December 2015, 21:16
Both classes look like this in the header (which was written by Qt when the project was made):



classA : public QWidget
{
Q_OBJECT

public:
...




classB : public QWidget
{
Q_OBJECT

public:
...


I'm not sure if that means that they are derived from Q_OBJECT.

Vikram.Saralaya
10th December 2015, 21:40
It looks fine. If you added Q_OBJECT later then you might want to try running qmake again.

May be showing a bit more of the actual code might be a better way to get more help..

Leutzig
10th December 2015, 22:05
I've tried running qmake many times and deleting build directory, Clean All, made a new project and inserted every class and function individually, but when I add the object of the other class and use it in the connect, I get that error.
The actual classes are these:

ColorSelect header (ClassA):


#ifndef COLORSELECT_H
#define COLORSELECT_H

#include "device.h"
#include "serialcom.h"

namespace Ui {
class ColorSelect;
}

class ColorSelect : public QWidget
{
Q_OBJECT
//Q_PROPERTY(QColor color READ color NOTIFY colorChanged)

public:
explicit ColorSelect(QWidget *parent = 0, SerialCom *cS = NULL);
QWidget * getColorWheelWidgetPtr() const;
QColor getRGBColor() const;
void setItemData(QString, QString);
~ColorSelect();

signals:
void colorChanged(QColor arg);
void houseChange(const QString &);
void unitChange(const QString &);

private slots:
void updatePalette( const QColor & );
void on_HouseAndUnitChanged( const QString & house, const QString & unit );
void on_ColorChanged();
void on_upButton_clicked();
void on_downButton_clicked();
void on_addDeviceButton_clicked();
void on_deleteDeviceButton_clicked();
void on_listWidget_itemDoubleClicked(QListWidgetItem *item);
void on_chooseButton_clicked();

private:
Ui::ColorSelect *ui;
QColor rgbColor;
SerialCom *serialCom;
Device device;
};

#endif // COLORSELECT_H


ColorSelect constructor from ColorSelect cpp:


#include "colorselect.h"
#include "ui_colorselect.h"
#include "devicedialog.h"
#include <qdebug.h>

ColorSelect::ColorSelect(QWidget *parent, SerialCom *serialCom) : QWidget(parent),
ui(new Ui::ColorSelect)
{
ui->setupUi(this);
connect(ui->redSlider, SIGNAL(sliderReleased()), SLOT(on_ColorChanged()));
connect(ui->greenSlider, SIGNAL(sliderReleased()), SLOT(on_ColorChanged()));
connect(ui->blueSlider, SIGNAL(sliderReleased()), SLOT(on_ColorChanged()));
ui->redLine->setReadOnly(true);
ui->greenLine->setReadOnly(true);
ui->blueLine->setReadOnly(true);
on_ColorChanged();
this->serialCom = serialCom;

// highlights default device
ui->listWidget->item(0)->setSelected(true);
ui->listWidget->setCurrentItem(ui->listWidget->item(0));

// sets default values for default device
ui->listWidget->item(0)->setData(Qt::UserRole, "A01");

connect( ui->colorWheelWidget, SIGNAL( colorChange( const QColor & ) ), this, SLOT( updatePalette( const QColor & ) ) );
connect(this, SIGNAL( houseChange( const QString & ) ), &device, SLOT( setHouse( const QString & ) ) );
connect(this, SIGNAL( unitChange( const QString & ) ), &device, SLOT( setUnit( const QString & ) ) );
}


And Device header (class B):


#ifndef DEVICE
#define DEVICE

#include "serialcom.h"

class Device : public QWidget
{
Q_OBJECT

public:
explicit Device(QWidget *parent = 0);
QString getHouse();
QString getUnit();

public slots:
void setHouse(const QString &);
void setUnit(const QString &);

protected:

private:
QString house;
QString unit;

private slots:

};

#endif // DEVICE


And Device cpp:


#include "device.h"

QString Device::getHouse()
{
return house;
}

QString Device::getUnit()
{
return unit;
}

void Device::setHouse(const QString & house_)
{
house = house_;
qDebug()<< "\nHouse value is:" << house;
}

void Device::setUnit(const QString & unit_)
{
unit = unit_;
qDebug()<< "Unit value is:" << unit;
}


The full error is:
colorselect.obj:-1: error: LNK2019: unresolved external symbol "public: __cdecl Device::Device(class QWidget *)" (??0Device@@QEAA@PEAVQWidget@@@Z) referenced in function "public: __cdecl ColorSelect::ColorSelect(class QWidget *,class SerialCom *)" (??0ColorSelect@@QEAA@PEAVQWidget@@PEAVSerialCom@@ @Z)

And another related error I get:
debug\colorselect.exe:-1: error: LNK1120: 1 unresolved externals

I can also attach the whole project if you want.

Vikram.Saralaya
10th December 2015, 22:26
Where is the Device(QWidget* parent) constructor definition? I can't see it in Device.cpp..

Leutzig
10th December 2015, 23:09
Yep, that was it. There wasn't supposed to be a constructor and I completely overlooked the one Qt made in the header. Thanks Vik!