Search code examples
pythontkintertk-toolkittoplevel

Closing multiple toplevels in tkinter


I have created a tkinter application where the user can make multiple toplevel windows and have the option of closing them from inside the toplevel. I would like to make a button on the main window that closes all toplevel windows. How would I do this? Is there a way to do this without lists? If these toplevels are parts of classes is there also a way to call a function present in all of them?


Solution

  • Here's how to do the first part of your question about making a button in the main window to delete all the Toplevels without making a list of them. This works by using the universal winfo_children() widget method to find all the child widgets of the root (main) window.

    It's unclear to me what you meant about calling a function present in all of them — Toplevel widgets are instances of a predefined tkinter class which supports a predefined set of methods — and you can call them the same way the sample code below does with child.destroy().

    import tkinter as tk
    
    root = tk.Tk()
    root.title('Main')
    root.geometry('200x100')
    
    def close_all(master):
        for child in master.winfo_children():
            if isinstance(child, tk.Toplevel):
                child.destroy()  # Call method.
    
    button = tk.Button(root, text=f"Close Toplevels",
                       command=lambda master=root: close_all(master))
    button.pack()
    
    for i in reversed(range(4)):  # Create them bottom to top.
        toplevel = tk.Toplevel()
        toplevel.title(f'Toplevel {i+1}')
        toplevel.geometry('200x75')
        toplevel.lift()
    
        button = tk.Button(toplevel, text="Close me", command=toplevel.destroy)
        button.pack()
    
    root.mainloop()