在Qt里,一个事件是继承自QEvent的对象。事件通过调用QObject::event(),被发送到继承自 QObject 的对象。事件发送就是一个事件已经产生,由 QEvent正好去表达,且QObject 需要去回应。多数事件针对 QWidget和他的子类的,此外还有些不和图形相关的重要事件,比如,套接字激活,——某种被用于QSocketNotifier运作的事件。

某些事件来自窗口系统,如QMouseEvent,某些来自其他源头,如QTimerEvent,而某些来自应用程序。Qt一视同仁,因此像通常一样,你可以准确地发送事件,这和Qt自己的事件循环所作的方式一样。

多数事件类型具有特定的类,最常见的QResizeEvent、QPaintEvent、QMouseEvent、QKeyEvent和QCloseEvent。有很多别的,差不多40种左右,但大都是相当零碎。

每个类派生自QEvent且添加事件特定的函数;例如,QResizeEvent。在QResizeEvent中,就被加入了QResizeEvent::size()和QResizeEvent::oldSize()。

某些类支持多种事件类型。QMouseEvent支持鼠标移动、按压、粘滞按压、拖拽、点击、右按压,等等。

因为程序需要在多变且复杂的方式下作用,Qt的事件派发机制就是灵活的。QApplication::notify() 的文档扼要地叙述其整个来龙去脉,我们揭示在这里的内容满足99%的应用。

对于事件去被派发的正常的办法是调用一个虚拟函数。如,QPaintEvent通过调用QWidget::paintEvent()被使用。这个虚拟函数负责引起适当的响应,一般是重画窗口部件。

有时,并不存在一个特定事件函数,或者特定事件功能不足。最普通的例如按下tab键。正常情况下,被QWidget看成是去移动 键盘焦点,但少数窗口部件 需要自行解释。

这些对象能重新实现QObject::event(),按常规事件处理,以及要么在通常的处理之前,或之后处理,或完全重写。一个与众不同的的窗口部件,它解释了tab,也含有一个该应用特定的可能包含的自定制事件:

  bool MyClass:event( QEvent * e ) {
      if ( e->type() == QEvent::KeyPress ) {
          QKeyEvent * ke = (QKeyEvent*) e;
          if ( ke->key() == Key_Tab ) {
              // 这里是特定的tab处理
              k->accept();
              return TRUE;
          }
      } else if ( e->type() >= QEvent::User ) {
          QCustomEvent * c = (QCustomEvent*) e;
          // 这里是自定义事件处理
          return TRUE;
      }
      QWidget::event( e );
  }
更一般的,一个对象需要去考虑其它的事件。Qt用QObject::installEventFilter()支持这个目的(相应的有移除)。如,对话框通常要为某些窗口部件去过滤按键,比如,去修改Return键的处理。

一个事件过滤器在目标对象处理之前得以去处理事件。过滤器的QObject::eventFilter()实现被调用,它可以接受或丢弃过滤,也可容许或拒绝进一步去处理事件。如果所有的事件过滤器允许进一步的处理事件,事件自己就被送达目标对象。如果它们之一停止处理,目标和任何后面的事件过滤器根本就对该事件一无所知了。

整个应用程序中过滤所有的事件也是可能的,通过在QApplication上安装一个事件过滤器。这里有QToolTip为了处理全部鼠标和键盘行为的实作。这个功能相当强大,但其在整个应用中也拖慢了每单个事件的派送,因此最好避免这种应用方式。

全局事件过滤器在对象特定的过滤器前被调用。

许多应用程序都要创建和发送他们自己的事件。

创建一种内置类型的事件是非常简单的:创建一个相应的类型的对象,然后调用QApplication::sendEvent()或者QApplication::postEvent()。

sendEvent() 立即处理事件——当sendEvent() 返回,(事件过滤器和)对象已经处理过事件了。对于很多事件类,调用isAccepted()函数,他告知你该事件能否被目前调用的处理者所接受或者拒绝。

postEvent()投送事件于一个队列,以使能延迟派发。在下次Qt的主事件循环运行,他派发全部事件,带有些优化。举例,若有数个resize事件,它们就被压缩到一个。对于paint事件同样如此:QWidget::update()调用 postEvent(),最小化闪屏和避免多次重画,以增加速度。

postEvent()在对象初始化期间常常被使用,因为在对象完成初始化后,投送的消息会被很快派发。

去创建一个自定义类型的事件,你需要定义一个事件号,其必须大于QEvent::User,可能你也需要从QCustomEvent去派生,为了传递有关你的自定义事件的特性。看QCustomEvent的文档了解细节。

Qt入门(8)——事件和事件过滤器的更多相关文章

  1. QT学习 之 事件与事件过滤器(分为五个层次)

    事件 在Qt中,事件是作为对象处理的,所有事件对象继承自抽象类QEvent.此类用来表示程序内部发生或者来自于外部但应用程序应该知道的动作.事件能够能过被 QObject 的子类接受或者处理,但是通常 ...

  2. Qt入门学习——Qt 5 帮助文档的使用

    Qt入门学习——Qt 5 帮助文档的使用 学习图形界面开发,肯定离不开帮助文档的使用,因为它不像 C 语言那样就那么几个函数接口,图形接口的接口可以用海量来形容,常用的我们可能能记住,其它的真的没有必 ...

  3. qt中的事件机制

    事件 1.QEvent -->类型 -> QKeyEvent QEvent::KeyRelease QEvent::MouseMove -> QMouseEvent 2.事件处理过程 ...

  4. Qt之键盘事件监听-实时响应大小写Capslock按键

    目录 一.开篇 二.效果展示 三.实现思路 1.重写QLlinEdit 2.全局应用程序事件 3.windows钩子 四.相关文章 原文链接:Qt之键盘事件监听-实时响应大小写Capslock按键 一 ...

  5. Qt中的事件

    1. 引自---http://blog.sina.com.cn/s/blog_6e80f1390100pro4.html 信号和事件的区别就在与,事件比信号更加底层,而且如果一个信号对应多个槽的话,信 ...

  6. easelJS入门、事件、spritesheet

    easelJS入门.事件.spritesheet <%@ page language="java" contentType="text/html; charset= ...

  7. Qt入门之基础篇 ( 二 ) :Qt项目建立、编译、运行和发布过程解析

    转载请注明出处:CN_Simo. 题解: 本篇内容主讲Qt应用从创建到发布的整个过程,旨在帮助读者能够快速走进Qt的世界. 本来计划是讲解Qt源码静态编译,如此的话读者可能并不能清楚地知道为何要静态编 ...

  8. Qt入门之基础篇(三):掌握Qt4的静态编译基本方法

    转载载请注明出处:CN_Simo. 导语: 前两章都提到过“静态编译”(Static Compilation),在Windows下一次静态编译差不多需要长达三个小时才能完成,而且还非常容易由于各种原因 ...

  9. 【转】Qt鼠标键盘事件

    http://blog.csdn.net/lovebird_27/article/details/50351336 Qt 程序需要在main()函数创建一个QCoreApplication对象,然后调 ...

随机推荐

  1. JAVA中的static修饰的方法不能被重写

    可以重写静态方法,但重写后的静态方法不支持多态. 其实static根本就没有重写之说.static方法引用的时候应该用类名来引用,而不是对象.同时static方法不参与继承,所以在继承体系里面也不存在 ...

  2. css(动画,过渡,转换)

    css3动画 @keyframes 规定动画,必须定义动画的名称,动画时长的百分比,一个或多个css样式属性 以百分比来规定改变发生的时间,或者通过关键词"from"和" ...

  3. youphp学习整理

    <?php //后台公共模块 // _list 数据显示 // add 添加/编辑 视图 // insert 添加处理函数 // edit 添加/编辑 视图 // update 更新处理函数 / ...

  4. Eclipse从数据库逆向生成Hibernate带注解的实体类

    http://www.2cto.com/database/201501/372023.html

  5. 八、C# 值类型

    结构.枚举.装箱.拆箱 自定义值类型 如何利用结构来定义新的值类型,并使之具有与大多数预定义 类型相似的行为,这里的关键在于,任何 新定义的值类型都有它们自己的数据和方法. 一般用枚举来定义常量值集合 ...

  6. javascript基础学习(四)

    javascript之流程控制语句 学习要点: 表达式语句含义 选择语句:if.if...else.switch 循环语句:while.do...while.for.for...in 跳转语句:bre ...

  7. angular的post提交

    用下来明显感觉jquery的post提交比ng的post提交好用很多 一开始,用angularjs的$http提交的数据,在php服务器端无法通过 因为jQuery会把作为JSON对象的data序列化 ...

  8. Jmeter软件测试2--http接口测试

    上次利用Jmeter进行了webservice接口的测试,本次利用Jmeter进行http接口的测试 1.新建线程组 2.新建配置文件 3.新建http请求 4.配置动态请求 4.查看测试结果

  9. 寒假挑战PythonTip(一人一python)总结——算法是程序的灵魂,程序员的心法

        2014年2月中旬,我上升到挑战python英雄榜第3名.这是我寒假修炼算法的成果之一.来一下总结吧! Linux的创始人Linus Torvalds在一次演讲中有一段涉及“什么才是优秀程序员 ...

  10. linux 监控服务器脚本

    #!/bin/bash ctime=`date +%x%T`monitor_dir=/home/jk/if [ ! -d $monitor_dir ]; then    mkdir $monitor_ ...