Python 更新tkinter标签并使用条目选择参数

Python 更新tkinter标签并使用条目选择参数,python,python-3.x,tkinter,tkinter-label,Python,Python 3.x,Tkinter,Tkinter Label,我制作了一个小脚本来练习tkinter的使用。我希望程序打开一个窗口并显示一个标签。一旦我按下按钮,标签应显示一个介于0和100之间的随机数。我还希望标签每秒钟刷新一次,并显示另一个随机数 from tkinter import * import random import time root = Tk() def getrandint(): result = random.randint(0, 100) return result def go(): lab2['

我制作了一个小脚本来练习tkinter的使用。我希望程序打开一个窗口并显示一个标签。一旦我按下按钮,标签应显示一个介于0和100之间的随机数。我还希望标签每秒钟刷新一次,并显示另一个随机数

from tkinter import *
import random
import time
root = Tk()

def getrandint():
    result = random.randint(0, 100)
    return result


def go():
    lab2['text'] = 'Number: ' + str(getrandint())
    lab2.pack()

    root.geometry('300x200')
    root.mainloop()
    time.sleep(1)
    go()


lab1 = Label(root, text='Type in number')
lab2 = Label(root, text='Number:')
#ent = Entry(root, width=20)
#number = ent.get()
b = Button(root, text='Go', command=go())

b.pack()
lab1.pack()
lab2.pack()
#ent.pack()
这就是我走了多远。它会打开一个窗口并显示一个随机数,但不会刷新该数字。按钮甚至没有显示出来。另外,当我关闭窗口时,Python 3.8向我显示以下错误消息:

Traceback (most recent call last):
  File "C:/Users/chris/Desktop/WeatherLinkPy/testing.py", line 102, in <module>
    b = Button(root, text='Go', command=go())
  File "C:/Users/chris/Desktop/WeatherLinkPy/testing.py", line 95, in go
    go()
  File "C:/Users/chris/Desktop/WeatherLinkPy/testing.py", line 89, in go
    lab2['text'] = 'Number: ' + str(getrandint())
  File "C:\Users\chris\AppData\Local\Programs\Python\Python38\lib\tkinter\__init__.py", line 1660, in __setitem__
    self.configure({key: value})
  File "C:\Users\chris\AppData\Local\Programs\Python\Python38\lib\tkinter\__init__.py", line 1649, in configure
    return self._configure('configure', cnf, kw)
  File "C:\Users\chris\AppData\Local\Programs\Python\Python38\lib\tkinter\__init__.py", line 1639, in _configure
    self.tk.call(_flatten((self._w, cmd)) + self._options(cnf))
_tkinter.TclError: invalid command name ".!label2"
回溯(最近一次呼叫最后一次):
文件“C:/Users/chris/Desktop/WeatherLinkPy/testing.py”,第102行,在
b=按钮(根,text='Go',command=Go())
文件“C:/Users/chris/Desktop/WeatherLinkPy/testing.py”,第95行,在go中
go()
文件“C:/Users/chris/Desktop/WeatherLinkPy/testing.py”,第89行,在go中
lab2['text']='Number:'+str(getrandint())
文件“C:\Users\chris\AppData\Local\Programs\Python38\lib\tkinter\\ uuuuuu init\uuuuuu.py”,第1660行,在\uuuu setitem中__
self.configure({key:value})
文件“C:\Users\chris\AppData\Local\Programs\Python38\lib\tkinter\\uuuu init\uuuu.py”,第1649行,在configure中
返回自。_配置('configure',cnf,kw)
文件“C:\Users\chris\AppData\Local\Programs\Python\38\lib\tkinter\\ uuu init\uuu.py”,第1639行,在配置中
self.tk.call(_flatten((self._w,cmd))+self._选项(cnf))
_tkinter.TclError:无效的命令名“!label2”

最后,是否有一种方法可以更改random.randint(0,b)的第二个参数,该参数的开头有一个条目和一个按钮?

首先,当您将命令传递给按钮时,您需要将函数放在不带括号的位置:
command=go
。如果使用括号,则在声明按钮时(而不是按下按钮时)将调用该函数

其次,按下按钮后不应调用root.mainloop()。您应该在文件末尾运行它

mainloop
永远不会返回,因此将
sleep
和函数调用放在后面没有帮助。如果要在主循环期间运行代码,请创建一个调用
tk.update()
tk.update\u idletasks()
的循环

我不认为更新后的元素需要再次打包才能更新

最后,为什么要从内部调用
go

from tkinter import *
import random
import time
root = Tk()

def getrandint():
    result = random.randint(0, 100)
    return result


def go():
    lab2['text'] = 'Number: ' + str(getrandint())


lab1 = Label(root, text='Type in number')
lab2 = Label(root, text='Number:')
#ent = Entry(root, width=20)
#number = ent.get()
b = Button(root, text='Go', command=go)

b.pack()
lab1.pack()
lab2.pack()
#ent.pack()

root.geometry('300x200')
root.mainloop()
  • 让我们从基本错误开始,您对
    mainloop()
    的放置决定了所有小部件的显示方式(在编写良好的代码中)。在本例中,您希望将
    mainloop()
    放在末尾。在您的情况下,这甚至可以起作用,因为您使用的按钮具有包含
    mainloop()
    (有点难以用文字解释:P)的功能

  • 接下来,您不应该使用按钮的
    ()
    调用函数,因为它会自动启动函数,并且不会等待按钮按下:

  • 下一步是修复入口小部件和事件驱动编程。您不应该在代码开始时接受用户的输入,因为它在开始时是空的。在触发事件(函数等)后,您应该获取输入并将其存储在变量中,这意味着您的
    getrandint()
    将:
  • 接下来要避免使用
    time.sleep()
    ,因为它会延迟GUI。因此,您应该改为使用
    root.after(ms,func)
    ,它将在指定的
    ms
    之后调用
    func
所以您的最终代码是:

from tkinter import *
import random

root = Tk()
root.geometry('300x200')

def getrandint():
    try:
        result = random.randint(0, int(ent.get()))
        return result
    except TypeError:
        pass

def go():
    lab2['text'] = 'Number: ' + str(getrandint())
    root.after(1000,go)

lab1 = Label(root, text='Type in number')
lab2 = Label(root, text='Number:')
ent = Entry(root, width=20)
b = Button(root, text='Go', command=go)

b.pack()
lab1.pack()
lab2.pack()
ent.pack()

root.mainloop() # At the end of the code
另请注意:

from tkinter import *
import random

root = Tk()
root.geometry('300x200')

def getrandint():
    try:
        result = random.randint(0, int(ent.get()))
        return result
    except TypeError:
        pass

def go():
    lab2['text'] = 'Number: ' + str(getrandint())
    root.after(1000,go)

lab1 = Label(root, text='Type in number')
lab2 = Label(root, text='Number:')
ent = Entry(root, width=20)
b = Button(root, text='Go', command=go)

b.pack()
lab1.pack()
lab2.pack()
ent.pack()

root.mainloop() # At the end of the code
通过将您的
go()
更改为:

def go():
    try: # If not an integer is entered into entry widget
        lab2['text'] = 'Number: ' + str(random.randint(0,int(ent.get())))
        root.after(1000,go)
    except ValueError: # Ignore the error
        pass

尽管如此,您的错误是由于代码的流动方式造成的。经常练习,记住这些,你将永远不会再看到这些错误;)

基于您的说明的程序应如下所示(类似):


Lambda
函数允许您正确调用函数。我建议为tkinter寻找一些好的教程。试试。

一个问题是,您通过调用函数来传递按钮命令,而不是传递函数。使用
command=go
代替
command=go()
。此外,您应该在最后运行root.mainloop()。这里有很多错误,我建议您先学习
tkinter
教程。此外,我建议使用
after
方法代替
sleep
from tkinter import *
import random

root = Tk()
root.geometry('300x200')

def getrandint():
    try:
        result = random.randint(0, int(ent.get()))
        return result
    except TypeError:
        pass

def go():
    lab2['text'] = 'Number: ' + str(getrandint())
    root.after(1000,go)

lab1 = Label(root, text='Type in number')
lab2 = Label(root, text='Number:')
ent = Entry(root, width=20)
b = Button(root, text='Go', command=go)

b.pack()
lab1.pack()
lab2.pack()
ent.pack()

root.mainloop() # At the end of the code
def go():
    try: # If not an integer is entered into entry widget
        lab2['text'] = 'Number: ' + str(random.randint(0,int(ent.get())))
        root.after(1000,go)
    except ValueError: # Ignore the error
        pass
from tkinter import *
import random
import time

# Create function, which generates random number and update label
def set_random_num():
    num = random.randint(0,100)
    lab2.config(text=num)

# Initialize tkinter window
root = Tk()

# Create labels and button
lab1 = Label(root, text='Type in number')
lab1.pack()

lab2 = Label(root, text='Number:')
lab2.pack()

b = Button(root, text='Go', command=lambda: set_random_num()) 
b.pack()

# Keep it at the end of program
root.mainloop()