Seite 1 von 1

Name eines Frames von String nehmen

Verfasst: Freitag 28. Juli 2006, 16:21
von dh233
Ich möchte ein Frame erzeugen, wobei der Name des Frames in einem String steht. Ich hätte mir das wie folgt gedacht:

Code: Alles auswählen

for i in range(1, self.frames+1):
                """frameName contains name, eg: nav1, nav2,..."""
                self.frameName="nav" + str(i)
                print self.frameName
                
                """creating navigation frames"""
                self.frameName = Frame(self.root, relief=RIDGE, bd=2, bg="white", height=15)
                self.frameName.pack(anchor="n", fill=X)
Wenn ich den Frame dann verwenden will, gibt es aber eine Fehlermeldung:

Code: Alles auswählen

self.buttonCount=0    
            for i in range (1, self.frames+1):
                """count contains current Frame number"""
                self.count=i
                self.actualFrame="nav"+ str(i)
                
                
                
                #print self.actualFrame
                """getting 7 elements"""
                for i in range(6):
                    
                    """checking if list still contains elements"""
                    if len(self.modules) > 0:
                    
                        #TODO: dynamically setting command for button
                        self.buttonText=self.modules.pop()
                        print self.buttonText
                        
                        self.ButtonName="button"+str(self.buttonCount)
                        
                        self.buttonName=Button(self.actualFrame, text=self.buttonText, width=15, font=("Times New Roman", 11))
                        self.buttonName.pack(side="left", expand="yes", fill="x")
Was mache ich falsch, bzw. wie kann ich es richtig machen?

Danke, lG

Edit (Leonidas): Code in Python-Tags gesetzt.

Re: Name eines Frames von String nehmen

Verfasst: Freitag 28. Juli 2006, 21:19
von Joghurt
dh233 hat geschrieben:Was mache ich falsch
Du sagst uns nicht, worum es geht.

Ich vermute mal, es geht um ein GUI-Toolkit. Aber welches? Tkinter, WxWidgets, Gt???

Verfasst: Freitag 28. Juli 2006, 22:23
von dh233
Dabei handelt es sich um tkinter.

Das Problem ist eben, dass ich die Frames dynamisch generieren lassen möchte, wobei ein Frame 7 Buttons enthalten soll, ich aber vorher noch nicht weiß, wie viele Buttons es sein werden.

Das ganze ist so gedacht, dass die Anzahl der Buttons zur Laufzeit berechnet wird und dann je nach Anzahl der Buttons eben die entsprechende Anzahl an Frames generiert werden soll.

Re: Name eines Frames von String nehmen

Verfasst: Samstag 29. Juli 2006, 10:46
von CrackPod
dh233 hat geschrieben:Wenn ich den Frame dann verwenden will, gibt es aber eine Fehlermeldung:

Code: Alles auswählen

[...](Pythoncode)[...]
Wo is denn jetz genau die Fehlermeldung?

Verfasst: Samstag 29. Juli 2006, 23:28
von jAN
eine Möglichkeit:

Code: Alles auswählen

>>> from Tkinter import *
>>> root=Tk()
>>> a=locals()
>>> a["Frame1"]=Frame(root)
>>> a["Frame2"]=Frame(root)
>>> a["Frame1"].pack()
>>> a["Frame2"].pack()
>>> root.mainloop()
vllt eine bessere Möglichkeit:

Code: Alles auswählen

>>> from Tkinter import *
>>> root=Tk()
>>> frames=[]
>>> frames.append(Frame(root))
>>> frames.append(Frame(root))
>>> frames[0].pack()
>>> frames[1].pack()
>>> root.mainloop()

Verfasst: Sonntag 30. Juli 2006, 00:05
von HWK
Das ist doch ideal für setattr und getattr:

Code: Alles auswählen

for i in range(1, self.frames+1): 
    '''frameName contains name, eg: nav1, nav2,...''' 
    frameName = 'nav' + str(i) 
    print frameName 
    
    """creating navigation frames""" 
    setattr(self, frameName, Frame(self.root, relief=RIDGE, bd=2, bg="white",
                                   height=15)) 
    getattr(self, frameName).pack(anchor="n", fill=X)
MfG
HWK

Verfasst: Sonntag 30. Juli 2006, 07:53
von BlackJack
Warum sollte man in den `locals()` oder als Attribute Namen haben wollen, die auf diese Weise berechnet sind, sich also nie im Quelltext per "literalem" Namen benutzen lassen!? So etwas gehört in ein `dict()`. Oder halt eine Liste wenn man die Namen gar nicht braucht.

Verfasst: Sonntag 30. Juli 2006, 15:59
von jAN
es geht doch:

Code: Alles auswählen

>>> a=locals()
>>> a["antwort"]=21
>>> antwort*2
42
aber ich weiß was du meinst... deshalb ja auch die zweite favorisierte variante

Verfasst: Sonntag 30. Juli 2006, 21:29
von HWK
Das geht natürlich auch mit der getattr-, settattr-Variante. Die Frames sind auch unter ihrem Namen nav1, nav2 etc. ansprechbar.

Verfasst: Sonntag 30. Juli 2006, 21:33
von BlackJack
Es geht übrigens nicht! Versuch den Trick mal innerhalb einer Funktion oder Methode -- dann geht's nämlich nicht mehr weil `locals()` dort eine Kopie von der drunterliegenden Datenstruktur zurückgibt. Änderungen an dem Dictionary haben dann keinen Einfluss auf die lokalen Variablen.

Verfasst: Sonntag 30. Juli 2006, 22:05
von HWK
Hallo, BlackJack!

Deine Anmerkung betrifft aber doch nur die locals-Variante, nicht die getattr-, setattr-Variante, oder?
Übrigens eine durchaus nützliche Verwendung findet sich unter http://www.python-forum.de/viewtopic.php?p=40804.

MfG
HWK

Verfasst: Sonntag 30. Juli 2006, 22:16
von BlackJack
Das hat aber mit diesem "Fall" nichts zu tun. Dort wird auf Attribute zugegriffen, die bekannt sind und nicht auf berechnete.

Verfasst: Sonntag 30. Juli 2006, 22:32
von HWK
Hier erst einmal der Beweis, dass es funktioniert:

Code: Alles auswählen

class MyClass:
    def __init__(self):
        for i in range(4): 
            frameName = 'nav' + str(i + 1) 
            setattr(self, frameName, i * i)
        print self.nav1
        print self.nav2

class_test = MyClass()
print class_test.nav3
print class_test.nav4
Das Beispiel hat schon etwas mit diesem 'Fall' zu tun. Ich hätte die Buttonnamen auch einfach durch Durchnummerierung berechnen lassen können, um mir keine Namen 'aus den Fingern saugen zu müssen'. Desweiteren zeigt es die Verwendung von getattr.

Verfasst: Montag 31. Juli 2006, 06:47
von BlackJack
Wenn Du Dir keine Namen ausdenken willst, dann brauchst Du auch kein 'nav' vor Nummern setzen und kannst die Elemente gleich in eine Liste oder in ein Dictionary schmeissen mit den Zahlen als Index/Schlüssel.

Verfasst: Mittwoch 2. August 2006, 08:33
von dh233
Hallo!

Danke für eure Antworten. Ich hab das jetzt mit setattr() und getattr() gemacht, so wie es HWK beschrieben hat.



lG


dh233