首页 > 解决方案 > 定时器在后台运行和调用文件

问题描述

试图在 tkinter 中设置一个小型日程管理器,我有一个带有计时器的控制台,它工作正常,但我似乎无法使用我存储在标签中的时间。

我想要做的是说当 timer() 是某个时间而不是这样做。

我对此很陌生,并且尽我所能去学习。我找到了一个 cget 函数,但是我认为它仅在作为文本存储在标签中时才会返回。如果有人能指出我正确的方向?

from tkinter import *
import sys
import time
from time import strftime


#function to close window when ESC is pressed
def close(event):
    sys.exit()

#function to get timer to calculate
def timer():
    timer_tick = strftime("%H:%M:%S")
    time_label.configure(text=timer_tick)
    time_label.after(1000, timer)

########## MAIN CONSOLE WINDOW
window = Tk()
ws=window.winfo_screenwidth()
hs=window.winfo_screenheight()
#with bar w=780
#with bar h=100
w=565
h=66
x=(ws/1)-(w/1)
y=(hs/1)-(h/1)

#window.state('zoomed')
window.configure(bg='#3a3a3a')
window.wm_attributes("-topmost", 1)
window.geometry('+%d+%d'%(x,y))
window.overrideredirect(1)

########## FRAMES
top_frame = Frame(window)
top_frame.pack(side=TOP)

########## LABELS
header_label = Label(top_frame, text="Automated Job Runner", width=30, height=1, borderwidth=3, anchor="w", background='#3a3a3a', fg='#ffffff', font=("calibri", 11))
header_label.pack(side=LEFT)

time_label = Label(top_frame, width=10, height=1, borderwidth=3, background='#3a3a3a', fg='#ffffff', font=("calibri", 11))
time_label.pack(side=LEFT) 

status_label = Label(top_frame, text="Status: ", width=10, height=1, borderwidth=3, anchor="e", background='#3a3a3a', fg='#ffffff', font=("calibri", 11))
status_label.pack(side=LEFT)

status_var = Label(top_frame, text="TBC", width=10, height=1, borderwidth=3, anchor="w", background='#3a3a3a', fg='#ffffff', font=("calibri", 11))
status_var.pack(side=LEFT)

panel_button = Button(top_frame, text ="Console", background='#3a3a3a', fg='#ffffff', font=("calibri", 10))
panel_button.pack(side=LEFT)

def schedules():
    while 1+1==2:
        time.sleep(1)
        if timer() == '20:00':
            'do this'


if __name__ == "__main__":
    timer()

#on press ESC window closes
window.bind('<Escape>', close)
schedules()
window.mainloop()

标签: pythontkintertimer

解决方案


一种方法是使用信号。您可以安装一个函数作为处理程序,然后设置一个警报,该警报将在设定的时间过去后调用该处理程序函数。你可以像这样使用它:

>>> import signal
>>> def foo(sig, frame):
...   print(f"got signal {sig} inside stack frame {frame}")
...
>>> signal.signal(signal.SIGALRM, foo)
<Handlers.SIG_DFL: 0>
>>> signal.alarm(5)
>>> # 5 seconds later...
>>>
0
got signal 14 inside stack frame None
>>>

您注册为信号处理程序的函数将自动传递 2 个参数:信号编号 (an int) 和被信号中断的帧的堆栈帧对象。您不需要对它们做任何事情,但必须声明该函数以接受 2 个参数。

这是真正的异步,因此控制流不会停止并等待信号发生(这意味着您可能需要使用事件循环来保持程序运行)。

如果您想知道signal.signal返回的是什么:

>>> signal.signal(signal.SIGALRM, foo) == foo
True

在这种情况下,它返回对处理函数的引用。一般来说:

SIG_IGN - 如果信号被忽略
SIG_DFL - 如果信号的默认操作有效
None - 如果未知处理程序有效
其他 - 用作处理程序的可调用 Python 对象


推荐阅读