gpt4 book ai didi

python - 如何让 QtGui 窗口在屏幕上显示时处理事件?

转载 作者:太空宇宙 更新时间:2023-11-04 03:21:57 26 4
gpt4 key购买 nike

我正在为 Python 使用 PyQt,并且正在构建一个图形用户界面。几周前我遇到了一个问题,我在 gui 模块之外有一个函数修改 gui 中的小部件(高级进度条、更新字符串等),并且这些修改没有反射(reflect)在 gui 中,直到函数更改完成运行。

对此的解决方案是在完成我想要的任何修改后简单地调用 app.processEvents(),这将立即更新窗口的图形。

但现在我想知道,有没有办法在每次提前窗口时都这样做?

假设我调用了一个函数来修改进度条,但是这个函数需要很长时间才能运行。在调用该函数和修改进度条之间,app 不处理任何事件。所以,在这段时间里,我拉出一个 Chrome 窗口(或其他任何东西),然后关闭它,我的 gui 窗口是空白的,只是灰色,直到 app.processEvents() 再次被调用。

PyQt 中的功能是否允许我检测窗口何时被带到所有当前窗口的前面?

最佳答案

你应该看看QThread .

线程允许您在worker 线程中运行长时间、复杂的任务,而background 线程保持 GUI 响应,例如更新 QProgressBar,确保它响​​应运动事件。

基本思路是这样的:

# load modules
import time

from PySide import QtCore, QtGui


# APPLICATION STUFF
# -----------------

APP = QtGui.QApplication([])


# THREADS
# -------


class WorkerThread(QtCore.QThread):
'''Does the work'''

def __init__(self):
super(WorkerThread, self).__init__()

self.running = True

def run(self):
'''This starts the thread on the start() call'''

# this goes over 1000 numbers, at 10 a second, will take
# 100 seconds to complete, over a minute
for i in range(1000):
print(i)
time.sleep(0.1)

self.running = False


class BackgroundThread(QtCore.QThread):
'''Keeps the main loop responsive'''

def __init__(self, worker):
super(BackgroundThread, self).__init__()

self.worker = worker

def run(self):
'''This starts the thread on the start() call'''

while self.worker.running:
APP.processEvents()
print("Updating the main loop")
time.sleep(0.1)


# MAIN
# ----


def main():
# make threads
worker = WorkerThread()
background = BackgroundThread(worker)

# start the threads
worker.start()
background.start()
# wait until done
worker.wait()

if __name__ == '__main__':
main()

你得到的输出是这样的,展示了它是如何轮流进行长计算和更新主循环的:

0
Updating the main loop
1
Updating the main loop
2
Updating the main loop
3
Updating the main loop
4
Updating the main loop
5
Updating the main loop
6
Updating the main loop
Updating the main loop7

8
Updating the main loop
9

这连同一个QFocusEvent覆盖应该允许你做任何你想做的事。但最好将更新 GUI 和运行所需的长线程分开。

至于重写 QFocusEvent,您可以执行以下操作:

def focusInEvent(self, event):
event.accept()

# insert your code here

如果您选择实现线程以避免 GUI 阻塞,您应该阅读 basics of threading (因为线程有很多细微差别,除非您知道它们的潜在陷阱)。

关于python - 如何让 QtGui 窗口在屏幕上显示时处理事件?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34419926/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com