有时我的QProgressDialog显示,有时它根本不会显示(好像没有调用processEvents)。是否有任何processEvents()命令的工件可能导致QProgressDialog在某些情况下不显示?
我的问题很笼统,因为我还没有能够在我的代码中找出问题所在。但是,我注意到当我使用配置解析器访问文本文件时,我的QProgressDialog没有显示它。解决方法是在文件关闭后执行time.sleep()(可能是为了确保进程完成,然后processEvents将开始显示QProgressDialog)。
如果有帮助,这是我将QProgressDialog作为生成器运行的代码:
def progress_dialog(self, data, label, window_title, stop_label, capture_bar=False):
bar = QProgressDialog(label, stop_label, 0, len(data))
if capture_bar: self.prog_bar = bar
bar.setWindowTitle(window_title)
for k, d in enumerate(data):
QCoreApplication.instance().processEvents()
if bar.wasCanceled():
raise GeneratorExit
# set the next value beyond the start of 0
bar.setValue(k+1)
# again process events to draw the new label and value
QCoreApplication.instance().processEvents()
yield(d)
raise StopIteration
再次,抱歉,我没有孤立问题的完整代码片段(并且完整代码太大了)。我想我正在寻找的是检查processEvents()命令是否正在执行其工作的原因(因为我正在调用它,但它挂起在其他进程而不是显示对话框)。
编辑:
根据此支持请求执行“bar.show()”命令将强制显示进度条。
http://redmine.smar.fi/issues/265
我要等几周,确保这是一个有保障的修复方法,然后再将其作为答案发布。
答案 0 :(得分:3)
如果您需要显示QProgessDialog
而不管进程的持续时间,请使用其setMinimumDuration方法,其值为0.根据文档,默认最小值为4000毫秒。
答案 1 :(得分:1)
根据此支持请求,执行bar.show()
命令将强制进度条显示:
http://redmine.smar.fi/issues/265
在每次show()
调用之前和首次构建进度条之后,只需调用process events
方法。
我已经等了将近4个月了,这个解决方案还没有失败。似乎是一个充分的答案。
答案 2 :(得分:1)
这可能是一个旧线程,但我有一个类似的问题,show()使对话框出现,但是空。所以,我想出了这个装饰器,我应用于我想要运行阻塞的函数,同时允许GUI线程处理事件。
def nongui(fun):
"""Decorator running the function in non-gui thread while
processing the gui events."""
from multiprocessing.pool import ThreadPool
from PyQt4.QtGui import QApplication
def wrap(*args, **kwargs):
pool = ThreadPool(processes=1)
async = pool.apply_async(fun, args, kwargs)
while not async.ready():
async.wait(0.01)
QApplication.processEvents()
return async.get()
return wrap
然后,通过装饰器正常编写计算函数很容易:
@nongui
def work(input):
# Here you calculate the output and set the
# progress dialog value
return out
然后像往常一样运行它:
out = work(input)