Qt学习笔记-----事件
2017-02-17 00:02
176 查看
除了信号槽,Qt也使用了另一种手段来响应对象,即事件。比如鼠标左键按下事件,键盘某一个按键按下事件。
Qt的主循环QCoreApplication::exec()就是一个事件循环,这个循环捕获本地计算机产生的各种事件然后将这些事件存放到事件队列中,按照FIFO的顺序将每一个事件传递给相应的对象(QObject)。
事件队列中的事件被传递给QObject::event()函数,这个函数是一个集中分配营,它判断参数是哪种类型的事件,然后将该事件传递给相应的事件处理函数进行处理。而event本身并不对事件进行处理 。
事件的传播顺序:
1. 在QCoreApplication::exec()主循环中,Qt捕获计算机产生的各种事件,如果在此之前还有其他事件没有分配,就暂时将该事件放到事件队列中,随后再按照FIFO顺序一个个传播。
2. 事件经过一系列传播后到达该类的事件过滤器eventFilter(),这个函数对该事件进行过滤,如果返回true则传播终止。返回false则告诉Qt不过滤这个事件,继续传播。
3. 如果没有过滤掉,则随后会传播到该类的event()函数(或其父类),在这个函数中会根据事件的所属类型进行分配,调用相应的事件处理函数。如果不需要再向它的父类传播这个事件,则返回true告诉Qt应该处理完这个事件了。否则,调用父类的event函数来保证由父类来处理这个事件,防止其他类型的事件被忽略掉。
4. 特定的事件处理函数进行处理。
接下来我们逐个讨论这几个函数:
eventFilter
事件过滤函数,会在event函数之前被调用。返回true则告诉Qt事件被过滤掉,反之继续传播给event函数。通常的实现形式为:
event
如果成功分配掉事件则返回true;否则,调用父类的event函数防止其他类型事件被忽略掉。通常的实现形式为:
然后就是特定的事件处理函数,举个例子,如果我们需要对鼠标点击事件进行自定义的处理,那么我们就需要在自定义类中重新实现mousePressEvent()函数。又因为这个函数是父类的虚函数,我们无需重新实现event()函数,所以可以像这样:
Qt的主循环QCoreApplication::exec()就是一个事件循环,这个循环捕获本地计算机产生的各种事件然后将这些事件存放到事件队列中,按照FIFO的顺序将每一个事件传递给相应的对象(QObject)。
事件队列中的事件被传递给QObject::event()函数,这个函数是一个集中分配营,它判断参数是哪种类型的事件,然后将该事件传递给相应的事件处理函数进行处理。而event本身并不对事件进行处理 。
事件的传播顺序:
1. 在QCoreApplication::exec()主循环中,Qt捕获计算机产生的各种事件,如果在此之前还有其他事件没有分配,就暂时将该事件放到事件队列中,随后再按照FIFO顺序一个个传播。
2. 事件经过一系列传播后到达该类的事件过滤器eventFilter(),这个函数对该事件进行过滤,如果返回true则传播终止。返回false则告诉Qt不过滤这个事件,继续传播。
3. 如果没有过滤掉,则随后会传播到该类的event()函数(或其父类),在这个函数中会根据事件的所属类型进行分配,调用相应的事件处理函数。如果不需要再向它的父类传播这个事件,则返回true告诉Qt应该处理完这个事件了。否则,调用父类的event函数来保证由父类来处理这个事件,防止其他类型的事件被忽略掉。
4. 特定的事件处理函数进行处理。
接下来我们逐个讨论这几个函数:
eventFilter
bool QObject::eventFilter(QObject *watched, QEvent *event)
事件过滤函数,会在event函数之前被调用。返回true则告诉Qt事件被过滤掉,反之继续传播给event函数。通常的实现形式为:
/*判断对象指针watched是否是需要过滤掉事件的那个对象*/ /*通常和this比较或者和该类的某个成员变量比较*/ if(watched == this) //或 if(watched == m_watched) { /*判断事件类型是否是需要过滤的事件*/ if(event->type() == /*某个事件类型*/ ) { return true; } } return false;
event
bool QObject::event(QEvent *e)
如果成功分配掉事件则返回true;否则,调用父类的event函数防止其他类型事件被忽略掉。通常的实现形式为:
if(e->type() == /*event 1*/) { doThings1(); return true; } else if(e->type() == /*event 2*/) { doThings2(); return true; } //...关心的几个类型的事件分配 return QWidget::event(e); //调用父类的函数
然后就是特定的事件处理函数,举个例子,如果我们需要对鼠标点击事件进行自定义的处理,那么我们就需要在自定义类中重新实现mousePressEvent()函数。又因为这个函数是父类的虚函数,我们无需重新实现event()函数,所以可以像这样:
//.h #include <QWidget> #include <QLabel> class MyClass : public QWidget { Q_OBJECT public: MyClass(QWidget *parent = 0); protected: void mousePressEvent(QMouseEvent *event); private: QLabel *label; }; //.cpp MyClass::MyClass(QWidget *parent) :QWidget(parent) { label = new QLabel(); setCentralWidget(label); } void MyClass::mousePressEvent(QMouseEvent *event) { label->setText(QString("[%1, %2]") .arg(event->x(), event->y())); }
相关文章推荐
- Qt学习笔记(三)鼠标事件
- Qt学习笔记(1)---QT5利用事件过滤器实现在控件上绘图
- Qt学习笔记(六) 事件处理
- Qt学习笔记(三)事件处理
- 在事件查看器里有时会看到:KCC warnings
- 深入浅出话窗体(一)——窗体事件模型(上)
- c#中委托、事件之我见(二)
- 又一灵异事件--iBatis不支持枚举类型
- javascript 触发事件汇总
- 使用MFC 发送消息模拟按钮按下事件
- javascript事件集锦
- IOS控件:长度单位换算(UITextField,IBAction,委托事件touchesBegan)
- QT 模拟鼠标事件
- qt学习笔记(二) QString
- cocos2d-x (四):触摸事件处理机制
- 第12章 事件
- 秒杀多线程第六篇 经典线程同步 事件Event
- 微信学习_04_关注事件,关键字回复
- 事件分发与拦截
- java事件机制之通过上下左右键来控制小球为位置的移动演示