Search code examples
pythonuser-interfacetkintermessagebox

Message Box Dialog at Exit using Tkinter in Python


I want to show a message box dialog when pressing the "X" button to close the GUI. I want to ask the user if he's sure he wants to exit the program with a Yes/No choice. I'm getting an error when I press "Yes" in the dialog and the GUI closes if I press "NO". This is the full code

This is the error I'm getting:

self.tk.call('destroy', self._w)

_tkinter.TclError: can't invoke "destroy" command: application has been destroyed

This is what I've done so far:

import atexit

def deleteme():
     result = messagebox.askquestion("Exit", "Are You Sure You Want to Exit?")
     if result == "yes":
        root.destroy()
     else:
        return None

atexit.register(deleteme)

Solution

  • You can use the protocol method to bind the window deletion with a function.

    from tkinter import *
    from tkinter import messagebox
    
    def on_close():
        response=messagebox.askyesno('Exit','Are you sure you want to exit?')
        if response:
            root.destroy()
    
    root=Tk()
    root.protocol('WM_DELETE_WINDOW',on_close)
    
    root.mainloop()
    

    UPDATE

    According to the docs of atexit module

    Functions thus registered are automatically executed upon normal interpreter termination.

    The function registered was called after the mainloop was destroyed (since nothing proceeds, it marks the end of program). The GUI element that the function tries to destroy doesn't exist anymore, as also stated by the error.

    This module is not meant for the use case you trying to achieve, it's usually used for "cleanup" functions that are supposed to perform a task after the program terminates.

    The callback registered via the WM_DELETE_WINDOW protocol gives you the control over what happens when the window is instructed to close.