verdammt, ich kapier es einfach nicht

Fragen zu Tkinter.
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 19:03

sagt mal, kann ich denn nicht auch grid nehmen ?

Kai
imac
20 Zoll
2,4 ghz
Benutzeravatar
numerix
User
Beiträge: 2696
Registriert: Montag 11. Juni 2007, 15:09

Beitragvon numerix » Montag 18. August 2008, 19:18

derkai hat geschrieben:sagt mal, kann ich denn nicht auch grid nehmen ?


Klar, kannst du. Aber einfacher wird es dadurch m.E. nicht.
Da du - bisher jedenfalls - auch keine Widgets hast, die gleiche Abmessungen bekommen sollen, musst du sehen, dass du durch geeignetes Zusammenfassen von Zellen entsprechende Megazellen bekommst. Ich persönlich finde das wesentlich unpraktischer als die Arbeit mit dem pack-Manager und ggf. einigen verschachtelten Frames. Wenn man denen ordentliche Namen gibt, dann behält man auch bei etwas Verschachtelung gut den Überblick.
yipyip
User
Beiträge: 418
Registriert: Samstag 12. Juli 2008, 01:18

Beitragvon yipyip » Montag 18. August 2008, 19:24

...musste auch erst einen Abend und einen Nachmittag
googeln und experimentieren bis ich's so hatte wie es sein soll:

Das Canvas-Scroll-Resizing Pattern

Code: Alles auswählen

import Tkinter as tk

class Scroller(object):
 
  def __init__(self, root):

    self.root = root
    self.frame = tk.Frame(self.root)
    self.canvas = tk.Canvas(self.frame, width=100, height=100, bg='white')

    xscroll = tk.Scrollbar(self.root, orient='horizontal')
    self.canvas.config(xscrollcommand=xscroll.set)
    xscroll.config(command=self.canvas.xview)

    yscroll = tk.Scrollbar(self.root, orient='vertical')
    self.canvas.config(yscrollcommand=yscroll.set)
    yscroll.config(command=self.canvas.yview)

    w = 999 
    self.canvas.config(scrollregion=(0, 0, w, w))
    self.canvas.pack(side=tk.LEFT, expand=1, fill=tk.BOTH)

    self.frame.grid(row=0, column=0, sticky=tk.N+tk.S+tk.E+tk.W)
    yscroll.grid(row=0, column=1, sticky=tk.N+tk.S)
    xscroll.grid(row=1, column=0, sticky=tk.E+tk.W)

    self.root.grid_columnconfigure(0, weight=1)
    self.root.grid_rowconfigure(0, weight=1)

    p0 = (0, 0)
    p1 = (w >> 1, w - 1)
    p2 = (w - 1, 0)
    self.canvas.create_line(p0, p1)
    self.canvas.create_line(p1, p2)


if __name__ == '__main__':
   
  root = tk.Tk()
  Scroller(root)
  root.mainloop()


Versuche das mal. :D

Bei Dir fehlte u.a. ein

Code: Alles auswählen

fenster1.pack(side=tk.LEFT, ...

...mehr sage ich lieber nicht...
:roll:

Wichtigste Regel:
Tkinter-Funktionalitaet nie mit eigenem umfangreichen Code testen, sondern nur mit Minimalfunktionen.
:wink:
yipyip
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 19:26

ja, aber warum bekomme ich denn dann keinen Frame mehr RECHTS NEBEN die Spielfläche ?

Kai
imac

20 Zoll

2,4 ghz
yipyip
User
Beiträge: 418
Registriert: Samstag 12. Juli 2008, 01:18

Beitragvon yipyip » Montag 18. August 2008, 19:28

ups, war etwas zu spaet...
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 19:34

@yip yip

ne ne, nicht zu spät. ich gucke mir alles an
ich glaube aber inzwischen, dass die CANVAS bereits etwas
eingebaut haben, was die Funktion xview vereinfacht.

schönen Dank -
cih schaue es mir gleich mal an.
Ich habe aber gesehen, dass auch Du grid verwendet hast.

Davon raten ja leider alle ab.

Kai
imac

20 Zoll

2,4 ghz
Benutzeravatar
numerix
User
Beiträge: 2696
Registriert: Montag 11. Juni 2007, 15:09

Beitragvon numerix » Montag 18. August 2008, 19:51

derkai hat geschrieben:ja, aber warum bekomme ich denn dann keinen Frame mehr RECHTS NEBEN die Spielfläche ?


Weil du den pack()-Manager nicht richtig einsetzt ...

Guckst du hier:

Code: Alles auswählen

import Tkinter as tk

spiel = tk.Tk()
spiel.geometry("1024x768")
linkeseite = tk.Frame(spiel,bg="tomato",width=100)
linkeseite.pack(side=tk.LEFT,fill=tk.Y)
rechteseite = tk.Frame(spiel,bg="peachpuff",bd=3,relief=tk.SUNKEN)
rechteseite.pack(side=tk.LEFT,fill=tk.BOTH,expand=True)
spflaeche = tk.Canvas(rechteseite,bg="white")
spflaeche.pack(expand=True,fill=tk.BOTH,padx=25,pady=30)
rechtsnebencanvas = tk.Frame(spiel,bg="lightblue",width=100)
rechtsnebencanvas.pack(side=tk.LEFT,fill=tk.Y)
schieber = tk.Scrollbar(rechteseite,orient=tk.HORIZONTAL)
schieber.pack(fill=tk.X)
spiel.mainloop()
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 20:05

ok, aber wenn ich jetzt mal einen Teil aus deinem Code nehme :



Code: Alles auswählen

import Tkinter as tk

spiel = tk.Tk()
spiel.geometry("1024x768")

linkeseite = tk.Frame(spiel,bg="tomato",width=100)
linkeseite.pack(side=tk.LEFT,fill=tk.Y)

spiel.mainloop()


dann füllst Du nach oben auf : fill=tk.Y

lasse ich das jetzt weg und begrenze das Spielfeld auch in der Höhe,
dann komme ich mit side=tk.LEFT nicht weiter.

dann hilft nur :anchor=tk.nw



Code: Alles auswählen

import Tkinter as tk

spiel = tk.Tk()
spiel.geometry("1024x768")

linkeseite = tk.Frame(spiel,bg="tomato",width=100,height=100)
linkeseite.pack(side=tk.LEFT)

spiel.mainloop()
imac

20 Zoll

2,4 ghz
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 20:08

kommt jetzt die rechte seite dazu, dann baut der die aber nicht nach rechts, sondern drunter :

Code: Alles auswählen

import Tkinter as tk

spiel = tk.Tk()
spiel.geometry("1024x768")

linkeseite = tk.Frame(spiel,bg="tomato",width=100,height=100)
linkeseite.pack(anchor=tk.NW)

rechteseite = tk.Frame(spiel,bg="peachpuff",bd=3,relief=tk.SUNKEN)
rechteseite.pack(side=tk.LEFT,fill=tk.BOTH,expand=True)

spiel.mainloop()



auch anchor hilft dann nicht mehr weiter - ist immer noch drunter :

Code: Alles auswählen

rechteseite = tk.Frame(spiel,bg="peachpuff",bd=3,relief=tk.SUNKEN)
rechteseite.pack(anchor=tk.NE,fill=tk.BOTH,expand=True)

imac

20 Zoll

2,4 ghz
Benutzeravatar
numerix
User
Beiträge: 2696
Registriert: Montag 11. Juni 2007, 15:09

Beitragvon numerix » Montag 18. August 2008, 20:12

Das wird sich hier noch reichlich in die Länge ziehen, wenn du immer Scheibchenweise mit dem herausrückst, was deine GUI sonst noch für Features haben soll ...

Wenn ich etwas aufwändigere GUIs zu gestalten habe, dann nehme ich erstmal Papier und Stift (manchmal sogar Buntstifte und Geodreieck ...) und mache per Hand einen Entwurf. Meistens sieht es zwar am Ende dann doch (gewollt) anders aus, aber es hilft mir ungemein, mit einer Vorlage neben der Tastatur an dem zu bauen, was herauskommen soll.

In deinem Fall könntest du z.B. mit einem Zeichenprogramm mal einen Oberflächenentwurf aufbauen, der so ist, wie du es (am Ende veraussichtlich) gerne hättest - mit allem drum und dran. Und das zeigst du uns dann. Oder du beschreibst den vorgesehenen Endaufbau so präzise, dass man sich ein ausreichend genaues Bild davon machen kann.

Und dann sehen wir weiter ...
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 20:45

das ist jetzt aber nicht ganz fair.

Für mich soll das ein Test sein, ob die bisher programmierten
Zeilen auch in einer GUI funktionieren.

Ziel :

Linke Seite :
- einmal Canvas inkl. Scrollbalken mit vorgegener Spielfeldgröße
oben Luft und unten Luft
- einmal Canvas mittig drunter für eine Miniaturansicht der
gesamten Spielfäche

Rechte Seite - mit Luft rum herum :
- Frame mit drei Schaltflächen
oben, links und rechts.
Damit wird dann der Panzer übers Spielfeld bewegt.

das war es doch schon.

Ich habe das ja auch mit meinem Code gezeigt und gefragt,
warum ich nach Erstellung der Spielfläche links, einem Canvas darunter

DANN keinen Frame mehr auf die rechte Seite bekomme.

Kai
imac

20 Zoll

2,4 ghz
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 20:52

und mit "place" sähe das dann so aus :

Code: Alles auswählen

import Tkinter as tk
from funktionen import *

#Hauptfenster erzeugen
spiel = tk.Tk()
spiel.geometry("1024x768")
spiel.title("Kai s Battle Game")
spiel.config(bg="grey")

#Frame1 erzeugen
fenster1 = tk.Frame(master=spiel,bg="white",width=500,
                    height=500,bd=2,relief=tk.SUNKEN)
fenster1.place(x=10,y=20)

#Scrollbar erzeugen
xleiste = tk.Scrollbar(master=fenster1,orient=tk.HORIZONTAL)
yleiste = tk.Scrollbar(master=fenster1,orient=tk.VERTICAL)
xleiste.pack(side=tk.BOTTOM,pady=2,fill=tk.X)
yleiste.pack(side=tk.RIGHT,pady=2,fill=tk.Y)

#Canvas im Hauptfenster
spflaeche = tk.Canvas (master=fenster1,width=495,height=495)
erstelle_hexfeldobjekte (spielreihen, ungerade_spalten)

for x in hexdic.iterkeys() :
   
    spflaeche.create_polygon (hexdic[x][0],fill=hexdic[x][2],outline="black")

spflaeche.pack()


#Verknuepfung Scrollbar
xleiste.config(command=spflaeche.xview)
yleiste.config(command=spflaeche.yview)

#Frame2 erzeugen -> Miniaturansicht
fenster2 = tk.Frame(master=spiel,bg="white",width=200,height=200,
                   bd=2,relief=tk.SUNKEN)
fenster2.place(x=600,y=80)

#Frame3 erzeugen -> Miniaturansicht
fenster3 = tk.Frame(master=spiel,bg="white",width=200,height=200,
                   bd=2,relief=tk.SUNKEN)
fenster3.place(x=10,y=550)


spiel.mainloop()



Da dann aber gesagt wurde, dies besser mit Pack zu versuchen,
kam die Diskussion dann ins Rollen

Kai
imac

20 Zoll

2,4 ghz
Benutzeravatar
numerix
User
Beiträge: 2696
Registriert: Montag 11. Juni 2007, 15:09

Beitragvon numerix » Montag 18. August 2008, 21:24

Wenn ich deine verbale Beschreibung richtig verstehe, dann soll es so aussehen:

Code: Alles auswählen

import Tkinter as tk

spiel = tk.Tk()
spiel.geometry("1024x768")

linkeseite = tk.Frame(spiel)
linkeseite.pack(side=tk.LEFT,fill=tk.BOTH,expand=True)
spielfeld = tk.Canvas(linkeseite,bg="white",bd=2,relief=tk.SUNKEN)
spielfeld.pack(expand=True,fill=tk.BOTH,padx=25,pady=20)
schieber_x = tk.Scrollbar(spielfeld,orient=tk.HORIZONTAL)
schieber_x.pack(side=tk.BOTTOM,fill=tk.X)
schieber_y = tk.Scrollbar(spielfeld,orient=tk.VERTICAL)
schieber_y.pack(side=tk.RIGHT,fill=tk.Y)
vorschau = tk.Canvas(linkeseite,bg="white",bd=2,relief=tk.SUNKEN,width=180,height=120)
vorschau.pack(pady=20)

rechteseite = tk.Frame(spiel,bd=3,relief=tk.GROOVE)
rechteseite.pack(side=tk.RIGHT,anchor=tk.N,padx=20,pady=20)
knopfoben = tk.Button(rechteseite,text="oben")
knopfoben.pack(pady=10)
knopfbereich = tk.Frame(rechteseite)
knopfbereich.pack(padx=20,pady=10)
knopflinks = tk.Button(knopfbereich,text="links")
knopflinks.pack(side=tk.LEFT,padx=10)
knopfrechts = tk.Button(knopfbereich,text="rechts")
knopfrechts.pack(side=tk.LEFT,padx=10)
spiel.mainloop()


Dein letzter Code mit der pack/place-Mischung liefert bei mir aber nicht das, was deine verbale Beschreibung angibt.
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 22:35

ja, die Buttons fehlen !

ich wußte nicht, dass man SIDE und ANCHOR gleichzeitig
benutzen kann. Jetzt wird mir einiges klarer.

Du benutzt immer einen Frame, ohne eine Größe vorzugeben
und packst die Elemente einfach rein, richtig ?

ich habe es mal ergänzt um das Spielfeld + bewegliche Schieber :



Code: Alles auswählen

import Tkinter as tk
from funktionen import *

spiel = tk.Tk()
spiel.geometry("1024x768")

frame1 = tk.Frame(spiel)
frame1.pack(side=tk.LEFT,fill=tk.BOTH,expand=True)

spielfeld = tk.Canvas(frame1,bg="white",bd=2,relief=tk.SUNKEN)
erstelle_hexfeldobjekte ()

for x in hexdic.iterkeys() :
   
    spielfeld.create_polygon (hexdic[x][0],fill=hexdic[x][2],outline="black")

spielfeld.pack(expand=True,fill=tk.BOTH,padx=25,pady=20)


schieber_x = tk.Scrollbar(spielfeld,orient=tk.HORIZONTAL)
schieber_x.pack(side=tk.BOTTOM,fill=tk.X)

schieber_y = tk.Scrollbar(spielfeld,orient=tk.VERTICAL)
schieber_y.pack(side=tk.RIGHT,fill=tk.Y)

schieber_x.config(command=spielfeld.xview)
schieber_y.config(command=spielfeld.yview)

vorschau = tk.Canvas(frame1,bg="white",bd=2,relief=tk.SUNKEN,width=200,height=200)
vorschau.pack(pady=20)

frame2 = tk.Frame(spiel,bd=3,relief=tk.GROOVE)
frame2.pack(side=tk.RIGHT,anchor=tk.N,padx=20,pady=20)

knopfoben = tk.Button(frame2,text="oben")
knopfoben.pack(pady=10)
knopfbereich = tk.Frame(frame2)
knopfbereich.pack(padx=20,pady=10)
knopflinks = tk.Button(frame2,text="links")
knopflinks.pack(side=tk.LEFT,padx=10)
knopfrechts = tk.Button(frame2,text="rechts")
knopfrechts.pack(side=tk.LEFT,padx=10)


spiel.mainloop()


Vielen DANK für Deine unendliche Geduld

Kai
imac

20 Zoll

2,4 ghz
derkai
User
Beiträge: 169
Registriert: Montag 12. Mai 2008, 11:43

Beitragvon derkai » Montag 18. August 2008, 22:47

"vergrössert" sich quasi der Frame hier um das Widget Vorschau ?

Code: Alles auswählen

vorschau = tk.Canvas(frame1,bg="white",bd=2,relief=tk.SUNKEN,width=220,height=220)
vorschau.pack(anchor=tk.W,pady=10,padx=25)


Kai
imac

20 Zoll

2,4 ghz

Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder