You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Guizero/TKinter计时器GUI冻结崩溃问题技术求助

嘿,这个问题我太熟了——你踩了GUI编程里最常见的坑之一:阻塞事件循环!

问题根源

当你点击Start按钮后,test_loopt里的while timeLoop循环加上time.sleep(1)会把GUI的主线程死死占住。GUI程序的核心是事件循环,它要处理按钮点击、界面更新这些事儿,结果你让它一直跑循环睡大觉,自然没法响应Stop按钮,系统一看GUI僵住了,就直接给你强制关闭了。

修复方案

我们需要用guizero内置的repeat方法来实现非阻塞的计时,这样GUI主线程能同时处理用户交互和计时任务。下面是修改后的完整代码:

修复后的代码

###import libraries ###
from guizero import *
import time

###Variables###
timeLoop = False
Sec = 0
Min = 0
Hour = 0
test_repeat_id = None  # 保存定时任务ID,用于停止计时

###Define Functions###
def verlaat_settings():
    window2.hide()
    window3.hide()
    window4.hide()
    window.show(wait=True)

def stop_test():
    global timeLoop, test_repeat_id
    if test_repeat_id is not None:
        app.cancel(test_repeat_id)  # 取消定时任务
        test_repeat_id = None
    info("test_result", f"Test stopped at {Hour} Hour {Min} Mins {Sec} Sec ")
    text_test.value = "Test Stopped..."
    timeLoop = False

def update_timer():
    global Sec, Min, Hour
    Sec += 1
    print(f"{Min} Mins {Sec} Sec ")
    # 实时更新GUI上的计时器显示
    timer_test.value = f"{Hour:02d}:{Min:02d}:{Sec:02d}"
    if Sec == 60:
        Sec = 0
        Min += 1
    if Min == 60:
        Min = 0
        Hour += 1

def test_loopt():
    global timeLoop, test_repeat_id
    if not timeLoop:
        text_test.value = "Test is running....."
        timeLoop = True
        # 每隔1000毫秒(1秒)触发一次计时更新
        test_repeat_id = app.repeat(1000, update_timer)

app= App(title="Profiberry", layout="", width=480, height=272)
window3 = Window(app, title="Profiberry-Tester", layout="grid", width=480, height=272)
window3.show()  # 补全括号,否则窗口不会显示

###Window3###
welkom_tester= Text(window3, text="Profibus Tester", grid=[2,0,1,1])
Plaatje_profi= Picture(window3, image="logoprofi.gif", grid=[2,1,1,1])
lege_ruimte1 = Text(window3, text="", grid=[2,2,1,1])
text_test= Text(window3, text=" Waiting for input..... ", grid=[2,3,1,1])
timer_test= Text(window3, text='', grid=[2,4,1,1] )
lege_ruimte2 = Text(window3, text="", grid=[2,5,1,1])
lege_ruimte2 = Text(window3, text="", grid=[1,6])
Start_knop= PushButton(window3, text="Start", command=test_loopt, padx=50, pady=10, grid=[1,6] )
Start_knop.tk.config(foreground="white", background="green")
Stop_knop= PushButton(window3, text="Stop", command=stop_test, padx=50, pady=10, grid=[3,6])
Stop_knop.tk.config(foreground="white", background="red")
Exit_setting = PushButton(window3, command=verlaat_settings, text="Exit to Main Menu(F2)", padx=30, pady=10, grid=[2,6])

app.display()

关键改动说明

  1. 移除阻塞循环:删掉了test_loopt里的while和time.sleep,改用app.repeat()定时触发计时更新,不会抢占GUI主线程。
  2. 定时任务管理:新增test_repeat_id变量保存定时任务的ID,点击Stop时可以用app.cancel()终止计时。
  3. 修复语法错误:把stop_test里的timeLoop: False改成正确的全局变量声明+赋值。
  4. 界面实时更新:在update_timer里同步更新GUI上的timer_test文本,让用户能直观看到计时进度。
  5. 补全方法调用:修复了window3.show漏写括号的问题,确保窗口正常显示。

这样修改后,点击Start按钮计时开始,GUI不会冻结,Stop按钮能正常响应,程序也不会被系统强制关闭了。

内容的提问来源于stack exchange,提问作者Robin46

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 10:10:33