DMarlon Studio

Lección 14 · 14 de 20

Diálogos de mensaje y de datos · tkinter

Use messagebox y simpledialog de tkinter: avisos, preguntas y peticiones de datos, y qué devuelve cada función al cerrarse.

tkinter · Diálogos de mensaje y de datos en DMarlon Studio: el código del ejemplo y la ventana que abre al ejecutarlo

Los diálogos son modales: la función abre la ventanita, espera a que el usuario la cierre y entonces devuelve un valor. Por eso nunca se abren al arrancar, sino desde un botón: cada botón del ejemplo llama a run, que ejecuta el diálogo y escribe lo que ha devuelto. Al empezar, la etiqueta enseña un resultado de ejemplo.

messagebox.showinfo, showwarning y showerror solo avisan, con el icono de información, aviso o error, y devuelven "ok". Reciben el título y el mensaje.

Las preguntas devuelven lo que se eligió: askyesno da True (sí) o False (no); askokcancel, True o False, y askyesnocancel, True, False o None si se cancela, justo lo que pide «¿Guardar los cambios?». También existen askquestion, que devuelve "yes" o "no", y askretrycancel.

simpledialog pide un dato: askstring devuelve el texto, askinteger un entero (con minvalue y maxvalue rechaza los que se salen) y askfloat un número decimal; initialvalue rellena el campo. Todos devuelven None si se pulsa Cancel, así que compruébelo antes de usar el valor.

El diccionario dialogs guarda una función sin argumentos (lambda) por diálogo, y el bucle crea un botón para cada una en una rejilla de tres columnas, con i // 3 como fila e i % 3 como columna. Estos diálogos no están en la paleta de DMarlon Studio, pero se llaman igual desde el código de cualquier ventana que diseñe.

Código · main.py

import tkinter as tkfrom tkinter import ttk, messagebox, simpledialogroot = tk.Tk()root.title("Dialogs")root.geometry("520x250")# Each function opens a modal dialog and returns when it is closed.dialogs = {    "showinfo": lambda: messagebox.showinfo("Info", "The file was saved."),    "showwarning": lambda: messagebox.showwarning("Warning", "The disk is almost full."),    "showerror": lambda: messagebox.showerror("Error", "File not found."),    "askyesno": lambda: messagebox.askyesno("Delete", "Delete the file?"),    "askokcancel": lambda: messagebox.askokcancel("Print", "Print 12 pages?"),    "askyesnocancel": lambda: messagebox.askyesnocancel("Close", "Save the changes?"),    "askstring": lambda: simpledialog.askstring("Name", "Your name:", initialvalue="Ana"),    "askinteger": lambda: simpledialog.askinteger("Age", "Your age:", minvalue=0, maxvalue=120),    "askfloat": lambda: simpledialog.askfloat("Price", "Price:", initialvalue=9.95),}result = tk.StringVar(value="askyesno() returned True")def run(name):  # call the dialog and show what it returned    value = dialogs[name]()    result.set(f"{name}() returned {value!r}")grid = ttk.Frame(root, padding=16)grid.pack()for i, name in enumerate(dialogs):    ttk.Button(grid, text=name, command=lambda n=name: run(n)).grid(        row=i // 3, column=i % 3, sticky="ew", padx=4, pady=4)ttk.Label(root, text="Last result:").pack()ttk.Label(root, textvariable=result, font=("Menlo", 13)).pack(pady=6)root.mainloop()

Para recordar

  • Los diálogos son modales: devuelven el valor al cerrarse.
  • Los show* devuelven "ok"; los ask*, la respuesta.
  • askyesnocancel y simpledialog devuelven None al cancelar.
  • Ábralos desde un botón, nunca al arrancar.

Ejercicio

Añada un botón que pida con askinteger un número de copias entre 1 y 10 y, si no se cancela, escriba «Printing N copies» en la etiqueta.