[Programación]GUI en python con TkInter...

Emiliano Gavilán emilianogavilan en gmail.com
Vie Mayo 21 21:47:50 ART 2010


On Fri, May 21, 2010 at 10:25:49AM -0700, Horacio Castellini wrote:
> Holas... como debo portar un código para que sea usado de manera simple
> en una máquina con WinXP (con perdón de la palabra) que tiene instalado
> ActivePython con el toolkit TkInter. Como la gente no está acostumbrada
> a trabajar en modo consola... me pidieron que haga una GUI (de lo cual
> manyo poco), he buscado varias plantillas para poder adaptar pero

Ojo que las GUI tienen una filosofía de diseño muy diferente a las
aplicaciones de consola, como que nunca tenes que bloquear la interfaz
(eso significa o nada de calculos intensivos largos o <<suspiro>> usar
threads, o un proceso externo) y jamas, repito JAMAS poner un exit()
que no sea en un botón que dice "Salir".

8<--------8<--------8<--------8<--------8<--------8<--------8<--------
from Tkinter import *
import tkFileDialog
# los demas imports

def definir_archivo():
    """Selecciona el archivo a procesar"""
    global fe
    fname = tkFileDialog.askopenfilename()
    if fname:
        fe.delete(0, END)
        fe.insert(0, fname)

def procesar():
    """Procesa el archivo e inserta los resultados en los campos"""
    global fe
    global res
    fname=fe.get()
    if not fname:
        return
    # Aca va el calculo
    # yo pondria asi :
    # (cum, suav, var, U) = procesarImagen(fname)
    # y procesarImagen deberia retornar una tupla con los valores.
    # Notar que si procesarImagen da un error, en el mundo de las
    # GUI es considerado buena practica hacer un cuadro de dialogo
    # explicando que fallo y permitir reintentar. Una forma seria
    # retornar (None,)*4 y comprobar esa condicion.
    # por ahora simulemos los resultados
    import random
    cum  = random.random()
    suav = random.random()
    var  = random.random()
    U    = random.random()
    # .... fin calculos
    for e, val in zip(res,[cum, suav, var, U]):
        e.configure(state="normal")
        e.delete(0,END)
        e.insert(END, val)
        e.configure(state="readonly")

def hacerGUI():
    global res
    global fe

    root=Tk()
    # frame superior con una etiqueta, una entrada de texto y un
    # boton para cargar el archivo
    ff=Frame(root)
    fl=Label(ff,text="Archivo a analizar:")
    fe=Entry(ff)
    fb=Button(ff,text="...", command=definir_archivo)
    # geometry management
    fb.grid(row=0, column=2, padx=3)
    fe.grid(row=0, column=1, padx=3, sticky=EW)
    fl.grid(row=0, column=0, padx=3)
    ff.grid_columnconfigure(1, weight=1)

    # Frame de resultados
    rf=Frame(root)
    res=[]
    for i,txt in enumerate(['Entro:','Suavidad:','Var:','U:']):
        l = Label(rf,text=txt)
        e = Entry(rf, state="readonly", readonlybackground="white",
            selectbackground="#4a6984")
        res.append(e)
        l.grid(column=0, row=i, sticky=E, pady=3, padx=12)
        e.grid(column=1, row=i, sticky=NSEW, pady=3)
    rf.grid_columnconfigure(1,weight=1)
    # frame de control/salida
    cf=Frame(root)
    cg=Button(cf, text="Procesar", width=12, command=procesar)
    ce=Button(cf, text="Salir", width=12, command=exit)
    # geometry management
    cg.grid(column=0, row=0, padx=12, sticky=E)
    ce.grid(column=1, row=0, padx=12, sticky=W)
    cf.grid_columnconfigure(0, weight=1)
    cf.grid_columnconfigure(1, weight=1)

    # finalmente le damos al geometry manager los tres frames
    ff.pack(fill=X, padx=3, pady=3)
    cf.pack(expand=1, fill=BOTH, side=BOTTOM, pady=3, padx=3)
    rf.pack(fill=BOTH, expand=1, padx=6, pady=6)
    # opciones de la ventana:
    # solo permitimos cambiar el tamanio horizontalmente
    root.wm_resizable(1,0)
    # titulo de la ventana
    root.wm_title("SuperProgramejo 1.0")

hacerGUI()
mainloop()
8<--------8<--------8<--------8<--------8<--------8<--------8<--------

Saludos
Emiliano


Más información sobre la lista de distribución Programacion