报纸和订阅者的例子
newspaper.h
#ifndef NEWSPAPER_H
#define NEWSPAPER_H
#endif
#include <QObject>
class Newspaper : public QObject
{
Q_OBJECT
public:
Newspaper(const QString & name) : m_name(name){
}
void send(){
emit newPaper(m_name);
}
signals:
void newPaper(const QString &name);
private:
QString m_name;
};
reader.h
#ifndef READER_H
#define READER_H
#endif
#include <QObject>
#include <QDebug>
class Reader : public QObject{
Q_OBJECT
public:
Reader(){}
void receiveNewspaper(const QString & name){
qDebug()<<"Receives Newspaper:"<<name;
}
};
main.cpp
#include "mainwindow.h"
#include <QApplication>
#include "newspaper.h"
#include "reader.h"
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
Newspaper newspaper("Newspaper A");
Reader reader;
QObject::connect(&newspaper,&Newspaper::newPaper,&reader,&Reader::receiveNewspaper);
newspaper.send();
return app.exec();
}
总结
- 发送者和接收者都需是QObject的子类(槽函数是全局函数、Lambda表达式等无需接收者情况除外)
- 使用signals标记信号函数,信号是一个函数声明,返回void,不需要实现函数代码。但是槽函数需要具体的实现。
- 槽函数是普通的成员函数,作为成员函数,会受到public、private、protected的影响
- 使用emit在恰当位置发送信号
- 使用QObject::connect()函数连接信号和槽
- 任何成员函数、static函数、全局函数和Lambda表达式都可以作为槽函数。
扩展
- 信号可以和多个槽相连接,但是槽的调用顺序不确定
- 多个信号可以连接到一个槽,任意一个信号发出,这个槽就能被调用。
- 一个信号可以连接到另外一个信号:当第一个信号发出时,第二个信号被发出。
- 槽可以被取消连接