来公司不久,当前主要任务就是看书,安排了一些进度,就当是复习和加深印象了,来吧,Qt中的信号和槽。
这里顺带说一下,信号和槽机制 = 观察者模式
(前两天看一篇英文文档,看的蛋疼,什么叫观察者模式。。。涨姿势了)
一 、信号
当对象改变其状态时,信号就被该对象emit出去。
在头文件(.h)中 Signal:关键字修饰信号,自己看吧。。。
class Test : public QObject
{
Q_OBJECT
signals:
void Signal();
void Signal(int x);
void Signal(int x, int y);
} ;
二、 槽
槽可以有参数,但槽的参数不能缺省(一般来说,信号的参数就会传入给槽,Qt底层已经实现了,但是我绝不会去看那些蛋疼的实现代码)
public slots:
void Slot();
void Slot(int x);
void Slot(int x, int y);
三 信号和槽的关联
通过QObject对象的connect函数来进行关联,关联方式如下:
connect(this, signal, this, slot);
//给看个原函数 bool QObject::connect ( const QObject * sender, const char * signal, const QObject * receiver, const char * member ) [static]
看一些例子吧
1.信号触发信号
class TestWidget : public QWidget
{
public:
TestWidget();
...
signals:
void TestSignal();
...
private:
...
QPushButton *TestButton;
};
TestWidget::TestWidget()
{
TestButton = new QPushButton( this );
connect( TestButton, SIGNAL(clicked()), this, SIGNAL(TestSignal()) );
}
必须注意的事情
1.这里第一点就想说说connect第5个参数
前面4个就不说了,说一下第五个参数;
第五个参数是一个enum Qt::Connection Type类型
一共有6种类型,这里就说说三种常用的吧。。。
Qt支持6种连接方式,其中3中最主要:
Qt::DirectConnection(直连方式)
当信号发出后,相应的槽函数将立即被调用。emit语句后的代码将在所有槽函数执行完毕后被执行。(信号与槽函数关系类似于函数调用,同步执行)
Qt::QueuedConnection(排队方式)
当信号发出后,排队到信号队列中,需等到接收对象所属线程的事件循环取得控制权时才取得该信号,调用相应的槽函数。emit语句后的代码将在发出信号后立即被执行,无需等待槽函数执行完毕。(此时信号被塞到信号队列里了,信号与槽函数关系类似于消息通信,异步执行)
Qt::AutoConnection(自动方式)
Qt的默认连接方式,如果信号的发出和接收这个信号的对象同属一个线程,那个工作方式与直连方式相同;否则工作方式与排队方式相同。
2.就说说信号和槽的一些不能问题、
1.宏定义不能用在signal和slot参数中
2.构造函数不能用在signals和slots声明中(是个正常人也不会这么做)
3.(重要)信号与槽不能有缺省参数
4.(重要) 函数指针不能为信号和槽的参数!!!!
但是问题来了,非常传函数指针怎么办?
public slots:
void apply( ApplyFunctionType, char *);
居然是定义别名。。。。