Signal和slot的声明和连接

信号(SIGNAL)和槽(SLOT)是Qt编程的一个重要部分。这个机制可以在对象之间彼此并不了解的情况下将它们的行为联系起来。

Signal和slot的声明(一)

在Qt程序设计中,凡是包含signal和slot的类中都要加上Q_OBJECT的定义,下面的例子给出了如何定义在一个类中定义signal和slot

信号的定义:

siganls:

void mySignal();

void mySignal( int x );

void mySignal( int x, int y );

其中signals是Qt的关键字,而不是C/C++的关键字。此外信号与一般函数的区别是,它的所有返回值都是void,并且它没有函数实现体,它的函数体是moc自动生成的。

槽的定义:

public slots:

void mySlot();

void mySlot( int x );

不同类型的slot有不同的操作权限,具体看slot是public、protected还是private。

class Employee : public QObject

{

Q_OBJECT

public:

Employee() { mySalary = 0; }

int salary() const { return mySalary; }

public slots:

void setSalary(int newSalary);

signals:

void salaryChanged(int newSalary);

private:

int mySalary;

};

Signal和slot的声明(二)

Signal的发出一般在事件的处理函数中,利用emit发出signal,在下面的例子中在事件处理结束后发出signal

void Employee::setSalary(int newSalary)

{

if (newSalary != mySalary)

{

mySalary = newSalary;

emit salaryChanged(mySalary);

}

}

注意,只有newSalary != mySalary时才发出salary-Changed()信号,这样避免了死循环的出现。

槽和普通的c++成员函数很像。它们可以是虚函数(virtual),也可被重载(overload),可以是公有的(public),保护的 (protective),也可是私有的(private),它们可以象任何c++成员函数一样被调用,可以传递任何类型的参数。不同在于一个槽函数能和 一个信号相连接,只要信号发出了,这个槽函数就会自动被调用,这个任务是由connect函数来实现的。

connect函数语法如下:
connect(sender, SIGNAL(signal), receiver, SLOT(slot));
sender和receiver是QObject对象指针,signal和slot是不带参数的函数原型。SIGNALE()和SLOT()宏的作用是把他们转换成字符串。

信号和槽的一些使用规则:
1、一个信号可以连接到多个槽:
connect(slider, SIGNAL(valueChanged(int)),spinBox, SLOT(setValue(int)));
connect(slider, SIGNAL(valueChanged(int)),this, SLOT(updateStatusBarIndicator(int)));
当信号发出后,槽函数都会被调用,但是调用的顺序是随机的,不确定的。

2、多个信号可以连接到一个槽
connect(lcd, SIGNAL(overflow()), this, SLOT(handleMathError()));
connect(calculator, SIGNAL(divisionByZero()),this, SLOT(handleMathError()));
任何一个信号发出,槽函数都会执行。

3、一个信号可以和另一个信号相连
connect(lineEdit, SIGNAL(textChanged(const QString &)),this, SIGNAL(updateRecord(const QString &)));
 第一个信号发出后,第二个信号也同时发送。除此之外,信号与信号连接上和信号和槽连接相同。
 
4、连接可以被删除
disconnect(lcd, SIGNAL(overflow()),this, SLOT(handleMathError()));
这个函数很少使用,一个对象删除后,Qt自动删除这个对象的所有连接。

5、信号和槽函数必须有着相同的参数类型,这样信号和槽函数才能成功连接:
connect(ftp, SIGNAL(rawCommandReply(int, const QString &)),this, SLOT(processReply(int, const QString &)));
如果信号里的参数个数多于槽函数的参数,多余的参数被忽略:
connect(ftp, SIGNAL(rawCommandReply(int, const QString &)),this, SLOT(checkErrorCode(int)));
如果参数类型不匹配,或者信号和槽不存在,在debug状态时,Qt会在运行期间给出警告。如果信号和槽连接时包含了参数的名字,Qt将会给出警告。

时间: 2024-10-10 00:42:27

Signal和slot的声明和连接的相关文章

实现类似于Qt的Signal和Slot通讯机制

Signal和Slot机制 其实qt提供的对象间通讯机制. 实现细节 思路 实现类似与信号与槽的机制,无非就是做一些薄记工作,qt中通过虚函数和moc来实现.那我们怎么实现?我的思路是signal是一个对象,其他的slot将自己的回调注册进signal对象中,signal完成薄记工作.那么需要实现的细节归于一下几点. 1. 参数的提取与匹配. 2. slot容器的制作. 3. slot的调用. 参数处理 怎么处理参数是一大难题.我们必须推导出各类型,包括类的类型和参数类型,在此我们引入很多特性模

深入了解Qt(三)之元signal和slot

深入了解Qt主要内容来源于Inside Qt系列,本文做了部分删改,以便于理解.在此向原作者表示感谢! 在Qt 信号和槽函数这篇文章中已经详细地介绍了信号和槽的使用及注意事项.在这里对其使用方面的知识就不再做介绍,只做一些相应补充. 我们知道信号和槽是用来在对象间通信的一种机制,当一个特定的事件发生时,signal会被emit,slot调用时用来响应响应的signal.signal和slot机制是类型安全的,signal和slot必须互相匹配(实际上一个slot参数可以比对应的signal的参数

Signal和Slot是同步的还是异步的

signal和slot是异步调用还是同步调用,取决于对connect的设定.其实connect还有一个参数(Qt::ConnectionType),是它决定了是同步还是异步.以下是ConnectionType的定义 只不过,平常它有一个默认值Qt::AutoConnection,我们忽略了它.这时有道友问道,为何在AutoConnection模式下,有时是同步,有时是异步,莫非Auto就是人品代名词. 非也,其实Auto是这样规定的, 当sender和receiver在同一线程时,就是同步模式,

实现signal和slot机制(2)-跨线程投递

前言 在1中,我们实现了一个基础的signal+slot的模块件调用机制,不过那个direct调用,在这篇中,我们将支持夸线程调用,即在对象的线程上下文中,调用对象的函数. 对象线程绑定 在qt中,有一个很重要的概念,对象线程绑定,即在每个对象实例时候,其保存其线程上下文信息,其中就有一个事件循环,跨线程的信号就是将这个一个task丢到这个事件循环中,在对象绑定的线程中完成slot响应. 实现 对slot调用的打包-Task 我们需要将一个跨线程的slot调用打包成一个task,然后丢到想相应的

PyQt5信号-槽机制

signal -> emit -> slot signal.connect(slot) signal.disconnect(slot) 信号 (singal) 可以连接无数多个槽 (slot),或者没有连接槽也没有问题,信号也可以连接其他的信号. 连接的基本语句形式如下: who.singal.connect(slot) 信号是 QObject 的一个属性.只有通过 connect方法连接起来,信号-槽机制就建立起来了.类似的信号还有 disconnect 方法和emit 方法. discon

QT 中 关键字讲解(emit,signal,slot)

Qt中的类库有接近一半是从基类QObject上继承下来,信号与反应槽(signals/slot)机制就是用来在QObject类或其子类间通讯的方法.作为一种通用的处理机制,信号与反应槽非常灵活,可以携带任意数量的参数,参数的类型也由用户自定.同时其本身也是类型安全的,任何一个从QObject或其子类继承的用户类都可以使用信号与反应槽. 信号的作用如同Windows系统中的消息.在Qt中,对于发出信号的对象来说,它并不知道是谁接收了这个信号.这样的设计可能在某些地方会有些不便,但却杜绝了紧耦合,于

Qt 定时器signal/slot阻塞主线程界面

示例代码: <span style="font-size:18px;">class bicycle : public QMainWindow { public slots: void uploadDeviceStatus(); }; bicycle::bicycle(QWidget *parent) : QMainWindow(parent) { QTimer *timer = new QTimer(this); connect(timer, SIGNAL(timeout(

Signal &amp; Slot in QT

Try your best to provide an mechanism to implement what you want. 1. All is generated by QT Framework before compiling. 1 QObject.connect(sender,SIGNAL(signal()), reciver,SLOT(slot())); ==> QObject.connect(sender, “2signal( )”,reciver,”1slot()”); 1 c

Signal and Slots

Signal and Slots 用于对象之间通信. 它是 Qt 的核心特性之一, 并且也是Qt 与其它框架差别最大的部分. 概述 在GUI编程中, 如果我们改变了一个控件, 我们可能想其它控件知道: 换言之, 我们希望任何类型的 Object 能够彼此通信. 一些Tookits使用回调函数来实现通信,如果你想在一个函数中通告一些事件, 你需要在这个函数中使用一个函数指针. 但是这种做法有两个缺陷: 他们不是类型安全的, 我们在编译期无法获知这个指针是否正确. 这个回调函数把调用者和被调用者仅仅