vereinfachte Datumseingabe

Fragen zu Tkinter.
Antworten
sedi
User
Beiträge: 104
Registriert: Sonntag 9. Dezember 2007, 19:22

Hallo zusammen,

wollte eine Oberfläche zur einfachen Datumseingabe programmieren, so dass man das nicht immer wieder neu machen muss:

Also ganz simpel: Drei Eingabefelder für Jahr, Monat und Tag.

Das Ganze ist noch nicht fertig, insbesondere die Fehlerprüfung - wann sie einsetzen soll...

Aber generell soll nach der Eingabe geprüft werden, ob es sich um ein sinnvolles Datum handelt, wenn nicht, dann soll
das Eingabefeld mit dem fehlerhaften Eintrag farbig hinterlegt werden und gleichzeitig der Focus darauf gesetzt werden.
Nur bekomm ich das partout nicht hin... :(

Hier mein Code und das Problem in ``checkDate``:

Code: Alles auswählen

import datetime
import ttk  # enthaelt Tkinter als ttk.Tkinter
import tkMessageBox
from locale import getdefaultlocale, encodings
import logging
Logger = logging.getLogger(__name__)        # so Logger is unique
Logger.setLevel(logging.NOTSET)             # no level at develtime
Logger.addHandler(logging.NullHandler())    # no destination of ...


ENC = encodings.codecs.lookup(getdefaultlocale()[1]).name
HEUTE = datetime.datetime.now()
_tk = ttk.Tkinter


class Datumseingabe(object):
    def __init__(self, parent,
                       year=HEUTE.year,
                       month=HEUTE.month,
                       day=HEUTE.day):
        _c = "<%s>" % (self.__class__.__name__,)
        Logger.debug(_c)
        
        if parent == None or \
            not isinstance(parent, (_tk.Frame, ttk.Frame, _tk.Tk)):
            err = "Need ttk.Tkinter.Frame or ttk.Tkinter.Tk"
            raise ValueError(err)
        
        try:
            self.year = _tk.IntVar()
            self.year.set(int(year))
            Logger.debug("%s set year '%s'", _c, year)
        except:
            err = "Couldn't set year '%s'" % (year,)
            Logger.exception(err)
            raise ValueError(err)
        
        try:
            self.month = _tk.IntVar()
            self.month.set( int(month) )
            Logger.debug("%s set month '%s'", _c, month)
        except:
            err = "Couldn't set month '%s'" % (month,)
            Logger.exception(err)
            raise ValueError(err)
        
        try:
            self.day = _tk.IntVar()
            self.day.set( int(day) )
            Logger.debug("%s set day '%s'", _c, day)
        except:
            err = "Couldn't set day '%s'" % (day,)
            Logger.exception(err)
            raise ValueError(err)
        
        self.Datum = self.get()
        self.setupView(parent)
    
    def setupView(self, parent):
        """
        +----------------------------+
        |          Jahr  Monat  Tag  |
        |        +------++----++----+|
        | Datum: | 2013 || 09 || 28 ||
        |        +------++----++----+|
        +----------------------------+
        """
        _c = "<%s>" % (self.__class__.__name__,)
        Logger.debug(_c)
        
        f = self.frm = _tk.Frame(parent, bd=4, relief="groove")
        
        # 1. Zeile (Labels)
        lblJahr = _tk.Label(f, text="Jahr", anchor="c")
        lblJahr.grid(row=0, column=1)
        
        lblMonat = _tk.Label(f, text="Monat", anchor="c")
        lblMonat.grid(row=0, column=2)
        
        lblTag = _tk.Label(f, text="Tag", anchor="c")
        lblTag.grid(row=0, column=3)
        
        # 2. Zeile
        self.label = _tk.StringVar()
        self.label.set("Datum: ")
        lbl = _tk.Label(f, textvar=self.label, anchor="e")
        lbl.grid(row=1, column=0, sticky="w")
        
        self.entJahr = ttk.Entry(f, width=4, textvar=self.year)
        self.entJahr.grid(row=1, column=1)
        self.entJahr.bind("<FocusOut>", self.checkDate)
        
        self.entMonat = ttk.Entry(f, width=2, textvar=self.month)
        self.entMonat.grid(row=1, column=2)
        self.entMonat.bind("<FocusOut>", self.checkDate)
        
        self.entTag = ttk.Entry(f, width=2, textvar=self.day)
        self.entTag.grid(row=1, column=3)
        self.entTag.bind("<FocusOut>", self.checkDate)
        
        f.pack()
        Logger.debug("%s done", _c)
    
    def checkDate(self, event):
        _c = "<%s>" % (self.__class__.__name__,)
        
        jahr, monat, tag = self.year.get(), self.month.get(), self.day.get()
        try:
            if jahr and monat and date:
                d = datetime.date(jahr, monat, tag)
                Logger.debug("%s Date '%s-%s-%s' valid",
                             _c,d.year,d.month,d.day)
        except:
            tkMessageBox.showerror(
                u"Falsche Eingabe!",
                u"'%s-%s-%s' ist ein ungültiges Datum!" % (jahr, monat, tag),
                )
            
            # FIXME: Hintergrund hellrot und zurueck zu dem Entry...
            #~ event.widget.config(background="#A33")
            #~ event.widget.focus_set()
            
        Logger.info("%s done", _c)
    
    def __unicode__(self):
        d = self.get()
        return d.strftime(u"%Y-%m-%d")
    
    def __str__(self):
        return self.__unicode__().encode(ENC)
    
    def __repr__(self):
        return "<Datumseingabe %s>" % (self.__str__(),)
    
    def get(self):
        _c = "<%s>" % (self.__class__.__name__,)
        Logger.debug("%s try to create datetime.date object...", _c)
        d = datetime.date(self.year.get(),
                              self.month.get(),
                              self.day.get())
        Logger.debug("%s Return '%s'", _c, d)
        return d


if __name__ == "__main__":
    app = _tk.Tk()
    datum = Datumseingabe(app)
    datum.year.set(2012)
    app.mainloop()
CU sedi
----------------------------------------------------------
Python 3.5; Python 3.6
LinuxMint18
Antworten