为什么tkinter toplevel不能在Python3的循环内重复创建?

时间:2018-02-08 13:15:56

标签: python python-3.x tkinter toplevel

我希望程序能够:

  1. 使根窗口保持打开状态
  2. 当点击按钮时,它将打开一个顶层窗口
  3. 在下一个单击的顶层窗口中,它会破坏它 顶层窗口并创建另一个顶层窗口,这将是 直到列表的所有元素都将通过
  4. 进行迭代

    但它没有按预期工作。

    只出现一个顶层窗口,我无法进入下一个顶层

    我的代码是:

    from tkinter import *
    
    root = Tk()
    def go_cmd():
        list = [1,2,3,4,5]
        for i in list:
            win = Toplevel()
    
            def next_cmd():
                win.destroy()
    
            l = Label(text = i)
            l.grid(row=0,column=0)
            b = Button(text="Next",command=next_cmd)
            b.grid(row=1,column=0)
    
            win.mainloop()
    
    
    
    b1 = Button(root,text = " Go ",command = go_cmd)
    b1.grid(row=0,column=0)
    
    
    
    
    root.mainloop()
    

2 个答案:

答案 0 :(得分:0)

  

“为什么不能在Python3的循环内重复创建tkinter toplevel?”

可以在循环内重复创建:

    select id,max(assigneddate),startdate,enddate,userid,role
    from tablea
    where asssigneddate < startdate and 
    role = 'Red'
    group by id,startdate,enddate,userid,role;

在OP的代码中,try: # In order to be able to import tkinter for import tkinter as tk # either in python 2 or in python 3 except ImportError: import Tkinter as tk if __name__ == '__main__': root = tk.Tk() for _ in range(5): tk.Toplevel(root, bg='red') root.mainloop() 块在循环中进一步移动,因为它本身就是一个“win.mainloop”循环。

实现所需行为的一个好方法是创建while True的子类并逐个调用它们:

Toplevel

答案 1 :(得分:0)

您不应该使用循环来创建窗口。您设置功能的方式只是一次创建所有窗口。

以下代码将根据列表本身创建窗口,因此当您想要更改“下一步”按钮将转到的页面数时,您需要做的就是更新列表。

请记住,这种方式可能不是使用列表的最佳方法。为了获得更清晰的OOP方法,您可能希望在类中编写一些内容。下面的内容仅用于说明如何使用该列表来决定Toplevel接下来要创建的内容。

from tkinter import *

root = Tk()

mylist = [1,2,3,4,5]

current_toplevel = None

def go_cmd(x):
    # global is used to make variables that are outside of the function
    # in the global namespace accessible.
    global current_toplevel, mylist

    wx = root.winfo_x()
    wy = root.winfo_y()
    next_index = x + 1

    # This will check if the next_index variable will be within the available
    # index range and if next_index is outside the index range it will reset
    # to index zero. This will prevent the "outside index" error.
    if next_index not in list(range(len(mylist))):
        next_index = 0

    # if the variable current_toplevel is not set to none then destroy it
    # so we can create the next window.
    if current_toplevel != None:
        current_toplevel.destroy()

    current_toplevel = Toplevel()

    # set the location of the new top level window based off of the
    # root windows location. This can be changed to anything but
    # I wanted to use this as the example.
    current_toplevel.geometry("+{}+{}".format(wx, wy))

    Label(current_toplevel, width = 10, text = mylist[x]).grid(row=0,column=0)

    # because we need to prep the "Next" button for the next index
    # we will need to use a lambda command for getting the next window
    b = Button(current_toplevel, width = 10, text="Next",
               command = lambda a = next_index: go_cmd(a)).grid(row=1,column=0)

b1 = Button(root,text = "Go", width = 10,
            command = lambda: go_cmd(0)).grid(row=0,column=0)

root.mainloop()

这是没有所有教学评论的代码。

来自tkinter import *

root = Tk()

mylist = [1,2,3,4,5]

current_toplevel = None

def go_cmd(x):
    global current_toplevel, mylist

    wx = root.winfo_x()
    wy = root.winfo_y()
    next_index = x + 1

    if next_index not in list(range(len(mylist))):
        next_index = 0

    if current_toplevel != None:
        current_toplevel.destroy()

    current_toplevel = Toplevel()
    current_toplevel.geometry("+{}+{}".format(wx, wy))

    Label(current_toplevel, width = 10, text = mylist[x]).grid(row=0,column=0)

    b = Button(current_toplevel, width = 10, text="Next",
               command = lambda a = next_index: go_cmd(a)).grid(row=1,column=0)

b1 = Button(root,text = "Go", width = 10,
            command = lambda: go_cmd(0)).grid(row=0,column=0)

root.mainloop()