刚做完的一个项目,在测试时出现了一个问题:由于多线程的存在,当进行语音识别时:如果用户点击程序界面上的button或者其他接受点击事件后会发出信号的widget时,程序会crash ! 后来尝试着从多线程上去解决,但是比较困难;后来只能从另外一条路来解决,那就是:当语音识别进行时:禁掉一切用户操作!

所谓的禁掉一切UI操作,在手机等手持设备上,尤其是纯触摸屏的设备上,主要就是指的禁止mouse操作!当然了:也可能是禁止键盘操作等。那如何去做这一点呢?

方法:我们可以截获禁止操作的窗口的所有event事件,而后将他们全部抛掉而不进行处理,这样就可以了。那在Qt中要实现这一点有很多种方法,比较常用的方式就是使用eventFilter事件过滤器。

这其中不可避免要说到Qt中的事件传递顺序,其要经过很多层()对于我而言:我用的比较多的层次就是QApplication的eventFilter这一层 , 各个widget的eventFilter这一层 各个widget的event()这一层以及 各个widget里边的各个事件处理函数这一层(这四层的传递顺序是从前往后)

这里我们只需要使用各个widget的eventFilter即可! 可以如下写:

bool iEnableOperator = true;
myWidget::eventFilter(QObject *obj, QEvent *event)
{
if (iEnableOperator == true)
{
if(event->type() == QEvent::paint)
{
return false;
}
else
{
return true;
}
}
else
{
return QWidget::eventFilter(obj, event);
}
}

而后我们只需要改变iEnableOperator 这个变量的值 即可决定允许不允许进行UI操作!
//-------------------------------------------------------------------------------------------------------------------------------------------
这里有以下几点注意:
1:当禁止UI操作时:并不是要把所有event都要拦截掉,而是要把paint绘制事件给漏过去(正如上边所做的那样),因为我们仅仅是要禁止
UI操作,而不是不再更新绘制! 比如:在做语音识别的时候,我们再界面上显示一个进度条,其上边的值是逐渐增大的。 当禁止UI操作时:如果
我们同时拦截了paint绘制事件,那进度条也无法更新显示了! 基于以上理由,我们需要把paint事件给漏过去!
2:这里有一个特殊的空间:QTextEdit 。当我们后来对所有的窗口不见都做如上操作后发现:几乎所有窗口的UI操作都顺利禁掉了,唯独QTextEdit
的没有,导致程序还会发生crash! 后来追了一下这个问题发现:无论是在windows下还是symbian下,QTextEdit的事件传递过程都很另类!对于
所有的mouse事件,其在传递过程中不经过任何一个其注册的eventFilter事件过滤器,也不经过自身重写的event(),而是直接进入到了自己的
事件处理函数中(mousePressEvent()等等。。)!
对于这一点:我一直觉得没什么道理可言,因为别的空间,比如QPushButton都是经过的,唯独它不经过!Maybe这是QTextEdit的另外一个bug!!
后来我们用如下方法禁掉了QTextEdit的mouse事件:
①:首先准备一个标准的QWidget对象,将其透明度设为0.1,大小与QTextEdit相同,位置设置为QTextEdit对象的位置,亦即:让二者是一种前后
重叠的关系。初始时将这个窗口hide掉!
②: 当需要禁止QTextEdit的UI操作时(以我们的项目为例:就是当开始语音识别时),将前边创建的半透明窗口raise并show在QTextEdit
的前边来遮挡住QTextEdit本身。而当要允许QTextEdit的UI操作时则再将其hide掉!
其实道理也很简单:将QTextEdit挡住了,那事件就传递不到它上边,从而也就禁止掉了。由于我们将这个窗口透明度设置为0.1,几近全透明,
用户根本体验不到是我们在上边覆盖了一个窗口。

//-------------------------------------------------------------------------------------------------------------------------------------------
再补充一个关于QTextEdit的bug: QTextEdit这个控件在windows和symbian下的表现是很不一样的!
在windows下其表现很正常,但是在symbian下:其scrollBar上边的slider滑块长度大小永远不发生变化,按理说:其文字所占的屏数越多,
滑块的长度越短才对。 这一点就让用户无法通过滑动这个slider来达到翻屏的效果。
但是symbian下的QTextEdit却给出了几个菜单:当常按两个方向箭头时:其会跳出一个menu来,上边有几个选项:主要就是让滚动到
开头处,滚动到结尾处等。 它通过这种方式弥补了滑动块长度大小不变的问题。但是我觉得这个的用户体验度始终没有用slider好。

http://blog.csdn.net/nrc_douningbo/article/details/5646247

Qt中如何禁掉所有UI操作以及注意事项(处理各个widget的eventFilter这一层,但是感觉不好,为什么不使用QApplication呢)的更多相关文章

  1. Qt中forward declaration of struct Ui::xxx的解决

    每当你新键一个 QT设计界面, QT会自动生成yyy.ui文件,如 <?xml version="1.0" encoding="UTF-8"?> & ...

  2. Android之线程回掉更新ui

    一:工作线程中的回掉更新UI public class MainActivity extends AppCompatActivity { private int i; private Callback ...

  3. QT中几个函数的使用方法

    一.把字符串转换成整形demo1:QString str = "FF";bool ok;int hex = str.toInt(&ok, 16); // hex == 25 ...

  4. Qt中通过ui怎么引用不了pushbutton呢? 原来是这样…

    在Qt中打开一个项目在做, 突然想到要测量一下其中一个子系统,于是在当前环境下新建了一个项目并用qt designer 简单设计了一下ui,其中添加了pushbutton并命名为OpensourceB ...

  5. 主线程中也不绝对安全的 UI 操作

    从最初开始学习 iOS 的时候,我们就被告知 UI 操作一定要放在主线程进行.这是因为 UIKit 的方法不是线程安全的,保证线程安全需要极大的开销.那么问题来了,在主线程中进行 UI 操作一定是安全 ...

  6. qt中ui的 使用介绍

    1.什么是ui?ui通常是用Qt 设计师设计出来的界面文件的后缀.通常情况下ui是一个指向这个界面类的指针.ui-> 一般就是用来访问这个界面类里面的控件.例如你的ui文件里有一个叫okButt ...

  7. 第32课 Qt中的文件操作

    1. Qt的中IO操作 (1)Qt中IO操作的处理方式 ①Qt通过统一的接口简化了文件和外部设备的操作方式 ②Qt中的文件被看作一种特殊的外部设备 ③Qt中的文件操作与外部设备的操作相同 (2)IO操 ...

  8. 在多线程中进行UI操作

    那么在子线程中的UI操作如何处理呢?有两种方法: 一:在子线程,你需要进行的UI操作前添加dispatch_async函数,即可将代码块中的工作转回到主线程 dispatch_async(dispat ...

  9. Android 子线程中进行UI操作遇到的小问题

    今天在学习<第一行Android代码>第9章-子线程进行UI操作时遇到了一些问题. 代码是这样的: ... import java.util.logging.Handler; ... pu ...

随机推荐

  1. 给Extjs的GridPanel增加“合计”行(转)

    再Google,找到一个看似写的比较好的 http://www.cnblogs.com/over140/archive/2009/05/06/1449892.html 期间主要部分也是借鉴官方论坛上的 ...

  2. Android 混淆文件project.properties和proguard-project.txt

    参考文档:http://blog.csdn.net/xueyepiaoling/article/details/8202359 http://glblong.blog.51cto.com/305861 ...

  3. Java Notes 00 - Singleton Pattern(单例总结)

    转:http://hukai.me/java-notes-singleton-pattern/ 这里不赘述单例模式的概念了,直接演示几种不同的实现方式. 0)Eager initialization ...

  4. Nlog、elasticsearch、Kibana以及logstash

    Nlog.elasticsearch.Kibana以及logstash 前言 最近在做文档管理中,需要记录每个管理员以及用户在使用过程中的所有操作记录,本来是通过EF直接将操作数据记录在数据库中,在查 ...

  5. Topo软件

    http://jung.sourceforge.net/#! http://www.netdisco.org/ http://sourceforge.net/projects/toponet/ htt ...

  6. 没有产品,没有用户的,绝对不要浪费时间去联系风投——没有过home run的创业人,想办法先做出产品,找到少量用户,没有任何销售成本

    著作权归作者所有.商业转载请联系作者获得授权,非商业转载请注明出处.作者:Kuan Huang链接:http://www.zhihu.com/question/19641135/answer/1353 ...

  7. WebMatrix安装和使用

    官网:http://www.microsoft.com/web/webmatrix/ 一直觉得dreamweaver已经过时了,很多新的库都不支持.而且,启动慢,占用内存多,是时候换一个ide了. h ...

  8. Unix/Linux环境C编程入门教程(20) 搭建基于Mac的 Xcode 与 QT 开发环境

    1.启动 Vmware,如果没有 VMware 的同学,请看前面我们搭建 VMware 的视频 2.打开虚拟机以后,出现虚拟机界面 3 新建一个虚拟机 4 选择自定义,单击下一步 5 选择默认的 VM ...

  9. java的几个版本以及jre,jdk等概念——【转载】JDK、Java SE、Java EE、Java ME我该选

    我们平时使用的一些软件,有一部分需要Java环境的支持,但是SUN那么多的产品,让人眼花缭乱的版本号,前看后看都差不多的缩写,让我们选择起来的时候常常望而却步,只好跟着感觉走.所以下面我要介绍的就是那 ...

  10. 多项式ADT的数组实现

    /*删除表的正确方法*/ /*assume header*/ void DeleteList(List L) { Position p,Tmp; p=L->Next; while(p != NU ...