Питер tkinter: ловить исключения - PullRequest
4 голосов
/ 12 июля 2011

Начиная программировать на python, я чувствовал себя как дома с его отчетами об ошибках. Теперь, когда я программирую с помощью Tkinter, я обнаружил, что часто в моей программе возникают ошибки, которые я не замечаю, даже если они генерируют исключение: я их ловлю (иногда) только потому, что иду к отладке. Step (я использую wingIDE) и, например, в данной строке я вижу сообщение об исключении. Но меня раздражает то, что программа не останавливается, но это происходит даже в блоках , а не внутри try / error.

Если то, что я сказал, имеет какой-либо смысл, знаете ли вы о каком-то общем подходе, чтобы хотя бы отобразить ошибки? Находясь в Tkinter, я мог бы создать окно ошибки и заполнить его любым генерируемым исключением, когда это происходит.

Ответы [ 3 ]

8 голосов
/ 12 июля 2011

См. Ответы на Как сделать громкие исключения громче в tkinter , которые показывают, как подключить обратный вызов к tkinter.Tk.report_callback_exception.

5 голосов
/ 14 октября 2014

Как сказал @ jochen-ritzel ( Должен ли я сделать громкие исключения громче в tkinter? ), есть tk.TK.report_callback_exception(), который вы можете переопределить:

import traceback
import tkMessageBox

# You would normally put that on the App class
def show_error(self, *args):
    err = traceback.format_exception(*args)
    tkMessageBox.showerror('Exception',err)
# but this works too
tk.Tk.report_callback_exception = show_error
0 голосов
/ 24 октября 2018

Я предпочитаю явный расширяющий виджет Toplevel Tk, который представляет собой главным образом главное окно приложения, а не внедряет хак:

import tkinter as tk
from tkinter import messagebox

class FaultTolerantTk(tk.Tk):
    def report_callback_exception(self, exc, val, tb):
        self.destroy_unmapped_children(self)
        messagebox.showerror('Error!', val)

    # NOTE: It's an optional method. Add one if you have multiple windows to open
    def destroy_unmapped_children(self, parent):
        """
        Destroys unmapped windows (empty gray ones which got an error during initialization)
        recursively from bottom (root window) to top (last opened window).
        """
        children = parent.children.copy()
        for index, child in children.items():
            if not child.winfo_ismapped():
                parent.children.pop(index).destroy()
            else:
                self.destroy_unmapped_children(child)

def main():
    root = FaultTolerantTk()
    ...
    root.mainloop()


if __name__ == '__main__':
    main()

ИМХО, это похоже на правильный путь.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...