Вопрос-Ответ

How can I schedule updates (f/e, to update a clock) in tkinter?

Как я могу планировать обновления (например, для обновления часов) в tkinter?

Я пишу программу с библиотекой tkinter на Python.

Моя основная проблема в том, что я не знаю, как создать таймер или часы, подобные hh:mm:ss.

Мне нужно, чтобы он обновился сам (это то, что я не знаю, как сделать); когда я использую time.sleep() в цикле, весь графический интерфейс зависает.

Переведено автоматически
Ответ 1

В корневых окнах Tkinter есть метод с именем after который можно использовать для планирования вызова функции через определенный промежуток времени. Если эта функция сама вызывается after, вы настроили автоматически повторяющееся событие.

Вот рабочий пример:

# for python 3.x use 'tkinter' rather than 'Tkinter'
import Tkinter as tk
import time

class App():
def __init__(self):
self.root = tk.Tk()
self.label = tk.Label(text="")
self.label.pack()
self.update_clock()
self.root.mainloop()

def update_clock(self):
now = time.strftime("%H:%M:%S")
self.label.configure(text=now)
self.root.after(1000, self.update_clock)

app=App()

Имейте в виду, что after это не гарантирует, что функция будет запущена точно в срок. Это только планирует выполнение задания через заданный промежуток времени. Если приложение занято, может возникнуть задержка перед его вызовом, поскольку Tkinter однопоточный. Задержка обычно измеряется в микросекундах.

Ответ 2

Пример синхронизации Python3 с использованием frame.after(), а не приложения верхнего уровня. Также показано обновление метки с помощью StringVar()

#!/usr/bin/env python3

# Display UTC.
# started with https://docs.python.org/3.4/library/tkinter.html#module-tkinter

import tkinter as tk
import time

def current_iso8601():
"""Get current date and time in ISO8601"""
# https://en.wikipedia.org/wiki/ISO_8601
# https://xkcd.com/1179/
return time.strftime("%Y%m%dT%H%M%SZ", time.gmtime())

class Application(tk.Frame):
def __init__(self, master=None):
tk.Frame.__init__(self, master)
self.pack()
self.createWidgets()

def createWidgets(self):
self.now = tk.StringVar()
self.time = tk.Label(self, font=('Helvetica', 24))
self.time.pack(side="top")
self.time["textvariable"] = self.now

self.QUIT = tk.Button(self, text="QUIT", fg="red",
command=root.destroy)
self.QUIT.pack(side="bottom")

# initial time display
self.onUpdate()

def onUpdate(self):
# update displayed time
self.now.set(current_iso8601())
# schedule timer to call myself after 1 second
self.after(1000, self.onUpdate)

root = tk.Tk()
app = Application(master=root)
root.mainloop()
Ответ 3
from tkinter import *
import time
tk=Tk()
def clock():
t=time.strftime('%I:%M:%S',time.localtime())
if t!='':
label1.config(text=t,font='times 25')
tk.after(100,clock)
label1=Label(tk,justify='center')
label1.pack()
clock()
tk.mainloop()
Ответ 4

Вы должны вызывать .after_idle(callback) перед mainloop и .after(ms, callback) в конце callback функции.

Пример:

import tkinter as tk
import time


def refresh_clock():
clock_label.config(
text=time.strftime("%H:%M:%S", time.localtime())
)
root.after(1000, refresh_clock) # <--


root = tk.Tk()

clock_label = tk.Label(root, font="Times 25", justify="center")
clock_label.pack()

root.after_idle(refresh_clock) # <--
root.mainloop()
2023-10-23 18:42 python tkinter