Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/301.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 使用PyGame时处理键盘中断_Python_Pygame - Fatal编程技术网

Python 使用PyGame时处理键盘中断

Python 使用PyGame时处理键盘中断,python,pygame,Python,Pygame,我已经编写了一个小型Python应用程序,其中我使用PyGame来显示一些简单的图形 我在应用程序的基础上有一个简单的PyGame循环,如下所示: stopEvent = Event() # Just imagine that this eventually sets the stopEvent # as soon as the program is finished with its task. disp = SortDisplay(algorithm, stopEvent) def up

我已经编写了一个小型Python应用程序,其中我使用PyGame来显示一些简单的图形

我在应用程序的基础上有一个简单的PyGame循环,如下所示:

stopEvent = Event()

# Just imagine that this eventually sets the stopEvent
# as soon as the program is finished with its task.
disp = SortDisplay(algorithm, stopEvent)

def update():
    """ Update loop; updates the screen every few seconds. """
    while True:
        stopEvent.wait(options.delay)
        disp.update()
        if stopEvent.isSet():
            break
        disp.step()

t = Thread(target=update)
t.start()

while not stopEvent.isSet():
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            stopEvent.set()
对于正常的程序终止,它工作得很好;如果PyGame窗口关闭,则应用程序关闭;如果应用程序完成其任务,应用程序将关闭

我遇到的问题是,如果在Python控制台中按住Ctrl-C键,应用程序会抛出一个
键盘中断
,但会继续运行


因此,问题是:我在更新循环中做错了什么,如何纠正它,使
键盘中断
导致应用程序终止?

如何将最终循环更改为…:

while not stopEvent.isSet():
    try:
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                stopEvent.set()
    except KeyboardInterrupt:
        stopEvent.set()

i、 例如,确保捕捉到键盘中断,并将其视为退出事件。

修改Alex的答案,请注意,您可能希望对所有异常执行此操作,以确保在主线程因任何原因而失败时关闭线程,而不仅仅是键盘中断

您还需要将异常处理程序移出,以避免竞争条件。例如,调用stopEvent.isSet()时可能会出现键盘中断

最后,在中这样做会更清楚:您可以立即知道,无论如何退出此代码块,事件都将始终被设置。(我假设设置两次事件是无害的。)


如果您不想在KeyboardError上显示堆栈跟踪,您应该捕获并吞下它,但请确保仅在最外层的代码中执行此操作,以确保异常被完全传播出去。

这似乎是可行的,只要我在线程本身内也执行同样的操作。我觉得有点奇怪,我必须显式地捕获键盘中断。@Sebastian,键盘中断总是转到主线程,所以我不确定为什么你也应该在次线程中捕获它。事实上,它看起来是这样的,似乎无法复制我之前得到的。也许我的文件不同步了。谢谢
try:
    t = Thread(target=update)
    t.start()

    while not stopEvent.isSet():
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                stopEvent.set()
finally:
    stopEvent.set()