Python - while循环挂起没有错误

时间:2013-07-16 05:45:27

标签: python while-loop tkinter hang

我正在尝试创建一个while循环,它将从列表中检查条目小部件e1和e2的正确答案,如果它是正确的,它会随机选择另一个图像放到画布上,如果它是错的那么它会将文字不正确地打印到屏幕上。 我目前拥有的while循环并没有给我任何错误,但它挂起了程序,我无法弄清楚导致问题的原因。

编辑:我现在能够在将这一行放到最后canvas.mainloop()之后加载游戏屏幕,但是while循环中的if语句不起作用,我也遇到了一个新的错误不会影响我在底部添加的程序。

这是更新的while循环:

def gamescreen():
    imagelist = ["1.gif","2.gif","3.gif","4.gif","5.gif","6.gif","7.gif","8.gif","9.gif","10.gif","11.gif","12.gif","13.gif","14.gif","15.gif","16.gif","17.gif","18.gif","19.gif","20.gif","21.gif","22.gif","23.gif","24.gif","25.gif","26.gif","27.gif","28.gif","29.gif","30.gif","31.gif","32.gif","33.gif","34.gif","35.gif","36.gif","37.gif","38.gif","39.gif","40.gif","41.gif","42.gif","43.gif","44.gif","45.gif","46.gif","47.gif","48.gif","49.gif","50.gif"]
    answerlistx = [-1, -3, 3, 4, -7, 8, 9, 10, -10, 2, -7, 7, -1, -5, -6, -9, -7, 10, -4, 8, 1, -8, -10, -1, -3, -7, -3, 7, 3, -4, 1, -8, -4, 9, -5, -10, 10, 2, 2, -10, 4, 9, -3, 6, 10, -6, 4, 9, -10, -10]
    answerlisty = [3, -6, -5, 3, -2, 4, -4, -3, 4, -6, 1, 2, 2, 3, 2, -1, -5, 1, -3, 1, -2, -2, -5, -3, -2, -6, -3, 6, 2, 0, -5, 6, -4, 4, 1, -6, 0, -6, 5, 2, 4, -4, -2, 0, -3, -6, -4, 1, -3, 1]

    canvas.bind("<Button-1>", buttonclick_gamescreen)
    canvas.pack(expand = YES, fill = BOTH)
    photo = PhotoImage(file="gamescreen.gif")
    canvas.create_image(1, 1, image = photo, anchor = NW)
    e1 = Entry(canvas, width = 11)
    e2 = Entry(canvas, width = 11)
    canvas.create_window(390, 501, window=e1, anchor = NW)
    canvas.create_window(551, 501, window=e2, anchor = NW)
    canvas.after(1, countdowntimer)
    while cdtimer > 0:
        print("start of while loop")
        randomimage = random.randrange(0,49+1)
        game = PhotoImage(file=imagelist[randomimage])
        images = canvas.create_image(30, 65, image = game, anchor = NW)
        if pressed == 8 and e1 == answerlistx[randomimage] and e2 == answerlisty[randomimage]:
            print("correct")
            canvas.delete(images)
            randomimage = random.randrange(0,49+1)
            scorecounter = scorecounter + 1
            game = PhotoImage(file=imagelist[randomimage])
            images = canvas.create_image(30, 65, image = game, anchor = NW)
            e1.delete(0, END)   
            e2.delete(0, END)
        elif pressed == 8 and e1 != answerlistx[randomimage] or pressed == 8 and e2 != answerlisty[randomimage]:
            print("incorrect")
            wronganswer = canvas.create_text(400, 200, text="Incorrect", font="Ubuntu 29 bold", fill='red', anchor=NW)
            e1.delete(0, END)   
            e2.delete(0, END)
            canvas.after(1500,(canvas.delete(wronganswer))) 
        canvas.mainloop()

这是压缩的== 8值来自:

def buttonclick_gamescreen(event):
    global pressed
    pressed = ""

    if event.x >853 and event.x <957 and event.y > 8 and event.y < 56 : pressed = 7 
    if event.x >666 and event.x <947 and event.y > 491 and event.y < 534 : pressed = 8 

    if pressed == 7 :
        window.destroy()
    if pressed == 8:
        print("next button")

当我按下gamescreen()或得分屏幕()中的退出按钮时,会出现此新错误

start of while loop
start of while loop
Exception in Tkinter callback
Traceback (most recent call last):
  File "/usr/lib/python3.2/tkinter/__init__.py", line 1402, in __call__
    return self.func(*args)
  File "/home/ppppwn3d/workspace/Python/JailBreakBob/JailBreakBob.py", line 114, in buttonclick_mainscreen
    gamescreen()
  File "/home/ppppwn3d/workspace/Python/JailBreakBob/JailBreakBob.py", line 60, in gamescreen
    game = PhotoImage(file=imagelist[randomimage])
  File "/usr/lib/python3.2/tkinter/__init__.py", line 3231, in __init__
    Image.__init__(self, 'photo', name, cnf, master, **kw)
  File "/usr/lib/python3.2/tkinter/__init__.py", line 3172, in __init__
    raise RuntimeError('Too early to create image')
RuntimeError: Too early to create image

如果有人能指出我正确的方向,那将会非常有帮助。 PS:这是完整的代码,因为我没有提供足够的信息Link to full code on pastebin

提前致谢!

1 个答案:

答案 0 :(得分:1)

你的while循环没有给主循环一个机会运行。因此,buttonclick_mainscreen调用gamescreen后,pressed仍然为1且永远不会更改其值。

从事件循环调用的任何回调必须立即返回到事件循环,否则程序将无响应。不要停留在while循环中,只需从gamescreen返回,然后从处理用户事件(canvas.bind)和超时(canvas.after)的回调中完成其余工作。当前循环的每次迭代都将是回调的一次调用。

以这种方式重写算法起初很困惑,但这就是事件循环的工作方式。