Dynamische Anzahl von Widgets (TKinter)

Fragen zu Tkinter.
Antworten
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Guten Abend,
in meiner GUI (TKinter) für eine SQLite-Datenbank benötige ich eine dynamische Anzahl von Widgets (z.B. Entry und Label). Die Anzahl der Widgets hängt von der Anzahl der Datenfelder in einer Tabelle ab. Wie kann ich so was generieren und wie werden sie angesprochen, um zum Beispiel auf die Werte in den Entry's zuzugreifen? Datenbankseitig habe ich nicht das Problem wie viele Spalten in einer Tabelle vorhanden sind.

Vielen Dank.

snowflake
Sirius3
User
Beiträge: 17711
Registriert: Sonntag 21. Oktober 2012, 17:20

@snowflake: dafür benutzt man Schleifen und Listen.
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Hallo Sirius3,

das hab ich mir schon so gedacht. Leider ist es damit nicht getan. Kannst Du etwas konkreter werden?

Vielen Dank.

snowflake
Sirius3
User
Beiträge: 17711
Registriert: Sonntag 21. Oktober 2012, 17:20

@snowflake: was weißt Du über Schleifen und Listen und was hast Du schon versucht?
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Hallo,

wie ich in TKinter Entries erstelle weiß ich. Ich weiß nur nicht wie ich das dynamisch hinbekomme und wie ich die Entries nach der Erstellung ansprechen kann. Ich finde keinen Ansatz.

Die Schleife könnte so aussehen:

Code: Alles auswählen

liste=[]
for i in range(0,10): #10 Anzahl der Spalten in der Datenbank, welche ich hier nur als Beispiel aufgeführt habe
	liste[i].append("entry"+str(i))
Die Liste mit den Namen der Entries kann ich erstellen, aber wie kann ich jetzt damit die Entries erzeugen und später ansprechen?

Vielen Dnak.

snowflake
Zuletzt geändert von Anonymous am Donnerstag 12. Januar 2017, 12:16, insgesamt 1-mal geändert.
Grund: Quelltext in Python-Codebox-Tags gesetzt.
BlackJack

@snowflake: Du brauchst keine Liste mit Zeichenketten sondern eine mit `Entry`-Objekten, denn Du willst ja später auf die `Entry`-Objekte zugreifen und nicht auf Zeichenketten mit einem ”Namen”.

Zudem funktioniert der Code auch mit den Zeichenketten so nicht wie er da steht. Führ ihn mal aus und überlege was Du falsch gemacht hast.
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Guten Morgen zusammen,

meinen Fehler hab ich gesehen. Das muss natürlich weg und dann funktioniert die Schleife, auch wenn nicht in Richtung meiner Problemstellung.
Ich finde einfach keinen Ansatz, wie ich das mit den Objekten machen muss. Vielleicht kann mir jemand da helfen?

Vielen Dank.

snowflake
BlackJack

@snowflake: Und ich verstehe nicht wie Du keinen ”Ansatz” finden kannst, wo Du doch schon die Lösung kennst. Du weisst wie man Objekte erstellt, sagst Du, und Du weisst wie man Objekte in eine Liste stecken kann, das zeigt Dein Code. Wieso Du das mit Zeichenketten kannst, aber mit `Entry`-Objekten nicht ist mir ein Rätsel, denn da gibt es keinen Unterschied. Ausser das es halt `Entry`-Objekte sind und keine Zeichenketten, aber das ist einer Liste herzlich egal *was* für Objekte man in ihr speichert. Das funktioniert immer gleich.
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Hallo BlackJack,

ich meinte nicht Objekte, sondern Widgets weiß ich wie ich die erstellen kann. Ich weiß auch wie ich Datenbankabfragen mit SQLite erstellen kann.

Ich weiß aber nicht wie ich dyn. Widgets erstellen kann und dann darauf Zugriff habe.

Vielen Dank.

snowflake
__deets__
User
Beiträge: 14493
Registriert: Mittwoch 14. Oktober 2015, 14:29

Was passiert denn deiner Meinung nach, wenn du ein Entry-Objekt (ein Widget IST EIN OBJEKT) in die List tust? Hast du das mal probiert?
BlackJack

@snowflake: In Python ist alles was man an einen Namen binden kann ein Objekt. Also jeder Wert ist ein Objekt. Und in Listen kann man ganz allgemein Objekte speichern. Also jeden Wert. Ob Du einen Ausdruck hast der eine Zeichenkette erstellt oder einen der ein `Entry`-Objekt erstellt (und damit ein `Widget`-Objekt, denn `Entry` ist eine Unterklasse von `Widget`) ist völlig unabhängig davon wie man diesen Wert in eine Liste steckt oder über so eine Liste iteriert. Das ist der Liste egal was konkret für Werte als Elemente in ihr gespeichert werden.
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Hallo Leute,

so weit bin ich jetzt. Ich komme wirklich nicht mehr weiter.

Code: Alles auswählen

from tkinter import *

class MyObject(Frame):
    def __init__(self, NameEntry):
        super().__init__(master=fenster)
        self.NameEntry=NameEntry
        self.pack()
        self.createwidgets()
    def createwidgets(self):
        self.NameEntry=Entry(self)
        self.NameEntry.pack()
    def inhalteinf(self):
        pass
    
def Entries_erstellen():
    anzahl=10#Anzahl der Spalten in SQLite
    ListeName=[]
    ListeEntry=[]
    for i in range(0,anzahl):
        ListeName.append("Entry"+str(i))
    for i in range(0,anzahl):
        ListeEntry=MyObject(ListeName[i])

def Wert_eintragen():
    ListeEntry[1].insert(0,"test")

#Fenster
fenster = Tk()
fenster.title("Entries dynamisch erzeugen")

#Widgets
button = Button(fenster,text='Entries erstellen',command=Entries_erstellen)
button.pack()
aufruf = Button(fenster,text='Wert Eintragen',command=Wert_eintragen)
aufruf.pack()

fenster.mainloop()
Das Erzeugen der Entries scheint zu funktionieren. Ich habe aber anscheinend mit der Funktion Wert_eintragen keinen Zugriff auf das Entry.

snowflake
Zuletzt geändert von Anonymous am Freitag 13. Januar 2017, 15:41, insgesamt 1-mal geändert.
Grund: Quelltext in Python-Codebox-Tags gesetzt.
BlackJack

@snowflake: Du erstellst immer noch eine Liste mit Zeichenketten was unsinnig ist weil die nirgends gebraucht werden. Und die `Entry`-Objekte die Du erzeugst steckst Du *nicht* in eine Liste.

Und natürlich sind lokale Namen in einer Funktion nicht auf magische Weise irgendwo ausserhalb der Funktion sicht- und verfügbar. Das ist ja gerade der Sinn von Funktionen, das man da in sich geschlossene Sachen machen kann, die keinen Einfluss auf die Umgebung haben und auch von ihr nicht beeinflusst werden. Selbst wenn `ListeEntry` einfach so nach dem Aufruf der Funktion in anderen Funktionen sichtbar wäre: Da würde dann ein `Entry`-Objekt dran gebunden sein, nämlich das letzte welches in der `Entries_erstellen()`-Funktion erstellt und an den Namen gebunden wurde.

Dir fehlen absolute Grundlagen zu Datentypen, Datenstrukturen, Funktionen, und dann sicher auch objektorientierter Programmierung. Das ist zu viel um das mal eben in einem Forenbeitrag zu erklären, zumal es solche Erklärungen ja bereits in Form von Tutorials gibt. In der Python-Dokumentation befindet sich beispielsweise eines.
snowflake
User
Beiträge: 93
Registriert: Mittwoch 9. November 2016, 15:46

Ich habe noch nie objektorientiert programmiert und bin auch kein Informatiker. Ich möchte lediglich meine Daten etwas komfortabler verwalten, als es bisher der Fall ist (den Fehler mit der Variable habe ich jetzt auch gesehen)....

snowflake
BlackJack

@snowflake: Objektorientierte Programmierung (OOP) ist Grundlage für GUI-Programmierung, zum einen weil sie eines *der* Paradebeispiele für deren sinnvolle Anwendung ist, und GUI-Rahmenwerke davon regen gebrauch machen, als auch das man sich dabei nicht auf das reine verwenden beschränken kann, sondern auch selbst Klassen schreiben muss. Python ist halt eine objektorientierte Programmiersprache. Informatiker muss man dafür nicht sein. OOP ist fester Bestandteil der Grundlagen die man heute zum allgemeinen Programmieren braucht. Und ich würde sogar sagen funktionale Programmierung gehört da mittlerweile auch schon dazu, auch wenn dieser Trend etwas neuer ist.
Benutzeravatar
Goswin
User
Beiträge: 363
Registriert: Freitag 8. Dezember 2006, 11:47
Wohnort: Ulm-Böfingen
Kontaktdaten:

:wink:

Code: Alles auswählen

#[...]
    ListeName=[]
    ListeEntry=[]
    for i in range(0,anzahl):
        ListeName.append("Entry"+str(i))
        ListeEntry.append(MyObject(ListeName[i]))
#[...]
Antworten