python - 开始按钮在我的 tkinter 程序中不起作用
问题描述
在这个练习程序中,我创建了一个彩色游戏。在此我创建了一个名为 Start Game 的按钮。只有在我按下开始游戏按钮后,游戏才会开始。游戏开始时此按钮也会消失。它第一次完美运行。但是当倒计时结束或玩家输了时,开始游戏按钮应该重新出现在同一位置。开始按钮再次出现,但它正在调用应有的函数。请有人帮忙吗?
from tkinter import *
from random import *
doc = open("Highscore.txt", "r")
us = 0
hs = int(doc.read())
time_count = 5
colorlist = ["Red", "Yellow", "Blue", "Green", "Orange", "Purple"]
def add_uscore():
global us
us+= 1
score.config(text=(f"Score: {us}"))
def add_highscore():
global us
global hs
if us>hs:
hs = us
highscore.config(text=(f"Highscore: {hs}"))
doc2 = open("Highscore.txt","w")
doc2.write(str(hs))
doc2.close()
def start_game():
global colorlist
global textcolor
rancolor = choice(colorlist)
textcolor = choice(colorlist)
start_btn.grid_forget()
color.config(text=rancolor, fg=textcolor)
btn1.config(state=ACTIVE, bg="Indian Red")
btn2.config(state=ACTIVE, bg="Gold")
btn3.config(state=ACTIVE, bg="DodgerBlue3")
btn4.config(state=ACTIVE, bg="Sea Green")
btn5.config(state=ACTIVE, bg="Dark Orange")
btn6.config(state=ACTIVE, bg="Purple3")
timer.grid(row=4, column=0, columnspan=3)
def countdown():
global time_count
if time_count > 0:
time_count -= 1
timer.config(text=(f"Countdown: {time_count}"))
timer.after(1000, countdown)
elif time_count==0:
result.config(text="Time Over", fg="Indian Red")
finish_game()
def finish_game():
timer.grid_forget()
start_btn.grid(row=4, column=0, columnspan=3)
btn1.config(state=DISABLED)
btn2.config(state=DISABLED)
btn3.config(state=DISABLED)
btn4.config(state=DISABLED)
btn5.config(state=DISABLED)
btn6.config(state=DISABLED)
def new_game():
global us
us = 0
score.config(text=(f"Score: {us}"))
finish_game()
def reset_game():
global hs
hs = 0
doc2 = open("Highscore.txt","w")
doc2.write(str(hs))
doc2.close()
new_game()
def check(ucolor):
global textcolor
global time_count
if textcolor==ucolor:
result.config(text="Good", fg="Sea Green")
add_uscore()
add_highscore()
start_game()
time_count = 5
else:
result.config(text="You Lose", fg="Indian Red")
finish_game()
win = Tk()
win.title("Color Game")
#MENU
menu1 = Menu(win)
win.config(menu=menu1)
options = Menu(menu1)
menu1.add_cascade(label="Option", menu=options)
options.add_command(label="New Game", command=new_game)
options.add_command(label="Reset Game", command=reset_game)
options.add_command(label="Exit Game", command=quit)
#DISPLAY
color = Label(win, text="", font=("Comic Sans", 50), anchor=W)
color.grid(row=0, column=0, columnspan=4)
#BUTTON
btn1 = Button(win, text="Red", height=10, width=10, state=DISABLED, command=lambda:check("Red"))
btn1.grid(row=1, column=0)
btn2 = Button(win, text="Yellow", height=10, width=10,state=DISABLED, command=lambda:check("Yellow"))
btn2.grid(row=1, column=1)
btn3 = Button(win, text="Blue", height=10, width=10, state=DISABLED, command=lambda:check("Blue"))
btn3.grid(row=1, column=2)
btn4 = Button(win, text="Green", height=10, width=10, state=DISABLED, command=lambda:check("Green"))
btn4.grid(row=2, column=0)
btn5 = Button(win, text="Orange", height=10, width=10, state=DISABLED, command=lambda:check("Orange"))
btn5.grid(row=2, column=1)
btn6 = Button(win, text="Purple", height=10, width=10, state=DISABLED, command=lambda:check("Purple"))
btn6.grid(row=2, column=2)
#RESULT
result = Label(win, text="", font=("Ariel", 25))
result.grid(row=3, column=0, columnspan=3)
#COUNTDOWN
timer = Label(win, text="", fg="Dark Orange", font=("Ariel", 15))
#START BUTTON
start_btn = Button(win, text="START GAME", bg="Green", command= lambda: [start_game(), countdown()])
start_btn.grid(row=4, column=0, columnspan=3)
#SCORE
score = Label(win, text=(f"Score: {us}"), fg="Sea Green", font=("Ariel", 10))
score.grid(row=5, column=0, columnspan=3)
#HIGHSCORE
highscore = Label(win, text=(f"Highscore: {hs}"), font=("Ariel", 10), fg="firebrick4")
highscore.grid(row=6, column=0, columnspan=3)
win.mainloop()
解决方案
在您的代码中有一个变量time_count
在代码开头设置为5
...
hs = int(doc.read())
time_count = 5 # <-----------
colorlist = ["Red", "Yellow", "Blue", "Green", "Orange", "Purple"]
...
当你用完时间时,time_count
它的值为0。当你再次调用该start_game
函数时,它看到的time_count
是0,所以游戏必须结束。要解决此问题,您必须time_count
在每次游戏结束后重置。像这样的东西对我有用:
def finish_game():
global time_sleep
time_sleep = 5
timer.grid_forget()
start_btn.grid(row=4, column=0, columnspan=3)
btn1.config(state=DISABLED)
btn2.config(state=DISABLED)
btn3.config(state=DISABLED)
btn4.config(state=DISABLED)
btn5.config(state=DISABLED)
btn6.config(state=DISABLED)
编辑:
我设法通过添加一个变量来修复countdown
在后台自行执行的函数。gameover
游戏结束时设置为1
,游戏开始时再次设置为0
。倒计时功能检查gameover
并仅在设置为 时执行0
。我还让result
标签只在游戏结束时出现。
完整代码:
from tkinter import *
from random import *
doc = open("Highscore.txt", "r")
us = 0
hs = int(doc.read())
time_count = 5
colorlist = ["Red", "Yellow", "Blue", "Green", "Orange", "Purple"]
def add_uscore():
global us
us+= 1
score.config(text=(f"Score: {us}"))
def add_highscore():
global us
global hs
if us>hs:
hs = us
highscore.config(text=(f"Highscore: {hs}"))
doc2 = open("Highscore.txt","w")
doc2.write(str(hs))
doc2.close()
def start_game():
global gameover
global colorlist
global textcolor
gameover = 0
rancolor = choice(colorlist)
textcolor = choice(colorlist)
start_btn.grid_forget()
result.grid_forget()
color.config(text=rancolor, fg=textcolor)
btn1.config(state=ACTIVE, bg="Indian Red")
btn2.config(state=ACTIVE, bg="Gold")
btn3.config(state=ACTIVE, bg="DodgerBlue3")
btn4.config(state=ACTIVE, bg="Sea Green")
btn5.config(state=ACTIVE, bg="Dark Orange")
btn6.config(state=ACTIVE, bg="Purple3")
timer.grid(row=4, column=0, columnspan=3)
def countdown():
global time_count
if time_count > 0 and gameover != 1:
time_count -= 1
timer.config(text=(f"Countdown: {time_count}"))
timer.after(1000, countdown)
elif time_count==0:
result.config(text="Time Over", fg="Indian Red")
finish_game()
def finish_game():
global time_count
time_count = 5
timer.grid_forget()
result.grid(row=3, column=0, columnspan=3)
start_btn.grid(row=4, column=0, columnspan=3)
btn1.config(state=DISABLED)
btn2.config(state=DISABLED)
btn3.config(state=DISABLED)
btn4.config(state=DISABLED)
btn5.config(state=DISABLED)
btn6.config(state=DISABLED)
def new_game():
global us
us = 0
score.config(text=(f"Score: {us}"))
finish_game()
def reset_game():
global hs
hs = 0
doc2 = open("Highscore.txt","w")
doc2.write(str(hs))
doc2.close()
new_game()
def check(ucolor):
global textcolor
global time_count
global gameover
if textcolor==ucolor:
result.config(text="Good", fg="Sea Green")
add_uscore()
add_highscore()
start_game()
time_count = 5
else:
result.config(text="You Lose", fg="Indian Red")
gameover = 1
finish_game()
win = Tk()
win.title("Color Game")
#MENU
menu1 = Menu(win)
win.config(menu=menu1)
options = Menu(menu1)
menu1.add_cascade(label="Option", menu=options)
options.add_command(label="New Game", command=new_game)
options.add_command(label="Reset Game", command=reset_game)
options.add_command(label="Exit Game", command=quit)
#DISPLAY
color = Label(win, text="", font=("Comic Sans", 50), anchor=W)
color.grid(row=0, column=0, columnspan=4)
#BUTTON
btn1 = Button(win, text="Red", height=10, width=10, state=DISABLED, command=lambda:check("Red"))
btn1.grid(row=1, column=0)
btn2 = Button(win, text="Yellow", height=10, width=10,state=DISABLED, command=lambda:check("Yellow"))
btn2.grid(row=1, column=1)
btn3 = Button(win, text="Blue", height=10, width=10, state=DISABLED, command=lambda:check("Blue"))
btn3.grid(row=1, column=2)
btn4 = Button(win, text="Green", height=10, width=10, state=DISABLED, command=lambda:check("Green"))
btn4.grid(row=2, column=0)
btn5 = Button(win, text="Orange", height=10, width=10, state=DISABLED, command=lambda:check("Orange"))
btn5.grid(row=2, column=1)
btn6 = Button(win, text="Purple", height=10, width=10, state=DISABLED, command=lambda:check("Purple"))
btn6.grid(row=2, column=2)
#RESULT
result = Label(win, text="", font=("Ariel", 25))
#COUNTDOWN
timer = Label(win, text="", fg="Dark Orange", font=("Ariel", 15))
#START BUTTON
start_btn = Button(win, text="START GAME", bg="Green", command= lambda: [start_game(), countdown()])
start_btn.grid(row=4, column=0, columnspan=3)
#SCORE
score = Label(win, text=(f"Score: {us}"), fg="Sea Green", font=("Ariel", 10))
score.grid(row=5, column=0, columnspan=3)
#HIGHSCORE
highscore = Label(win, text=(f"Highscore: {hs}"), font=("Ariel", 10), fg="firebrick4")
highscore.grid(row=6, column=0, columnspan=3)
win.mainloop()
请注意result
标签如何仅在游戏结束时放置在网格管理器中,并且在游戏再次开始时将其移除:
游戏结束时放置result
标签.grid
def finish_game():
...
result.grid(row=3, column=0, columnspan=3)
...
游戏开始时移除result
标签.grid_forget
def start_game():
...
result.grid_forget()
...
推荐阅读
- java - 如何将textview放置在布局的随机位置的相对布局中?
- python - 使用池星图进行并行线程的输出序列
- java - Java - 在单独的线程上调用对象方法
- r - 如何分隔字符值以除以矩阵中的正则表达式
- java - 缓存执行器端点未显示
- spring - Spring IT 测试 - 不能子类化最终类
- kubernetes - 如何使用 ip 地址访问 grafana-istio 仪表板?
- python - 创建重复独立元素列表的 Pythonic 方法
- wso2 - WSO2 SCIM 用户未反映在 Carbon UI 用户列表中
- oracle - 如果 INSERTED 或 UPDATED 更新同一个表