Ein Bild mehrfach zeichnen

Programmierung für GNOME und GTK+, GUI-Erstellung mit Glade.
Antworten
majinv
User
Beiträge: 42
Registriert: Mittwoch 14. April 2010, 13:21

Aloah zusammen,

ich versuch mich gerade in PyGTK... allerdings mit ziemlichen schwierigkeiten... will sagen, es will nicht und ich komm auch nicht so wirklich damit klar...
daher erhoffe ich mir ein bisschen Hilfe ;-)
ich möchte ein Bild, mehrfach benutzen, sprich, ich möchte es mehrfach darstellen...
ich weiß aber vorher nicht wie oft ich es darstellen werde...
noch dazu scheint Python mich und das was ich geschrieben habe nicht zu würdigen...
denn es spuckt eine Warning aus:
GtkWarning: Can't set a parent on widget which has a parent
Das ist mein bisheriger Code:
(countPeople ist die Anzahl, wie oft ich die Figur zeichnen will, die wird mir aber später durch eine Methode vorgegeben)

Code: Alles auswählen

class CreateStickFigure(threading.Thread):
    
    def __init__(self):
        threading.Thread.__init__(self)
        self.countPeople = 5 #ScanEnv -> det_people 
        self.start()

    def init_gui(self):
        self.window = gtk.Window()
        self.window.set_default_size(700, 600)
        self.da = gtk.DrawingArea()

        #set bg color
        color = gtk.gdk.color_parse('white')
        self.window.modify_bg(gtk.STATE_NORMAL, color)
        
        #load image
        self.image = gtk.Image()
        self.image.set_from_file("stickFigure.png")
        self.image.show()

        #create a fixbox with warning!
        self.fixed = gtk.Fixed()
        self.fixed.add(self.image)
        self.window.add(self.fixed)
        self.fixed.put(self.image, 100, 100)
        self.fixed.show()

        self.window.show()
Freue mich über jegliche Anmerkungen =)
BlackJack

@majinv: Ein Widget hat genau ein `parent`, dementsprechend kann man ein Widget halt auch nur einmal in die Widgethierarchie einbauen.

Den Quelltext wo das Problem tatsächlich auftaucht, hast Du uns jetzt aber vorenthalten, oder? In welcher Zeile soll dass denn sein?
majinv
User
Beiträge: 42
Registriert: Mittwoch 14. April 2010, 13:21

Danke, für die schnelle Antwort :)
Das weiß ich nicht genau, mehr als die fehlermeldung kommt nicht...
und ich hab nur die imports und die aufrufe ausgelassen...

Code: Alles auswählen

    def run(self):
         self.init_gui()
         gtk.main()

CreateStickFigure()
denke nicht das da der Fehler liegt... mehr gibts nicht in dem Code...
prinzipiell kann ich mit der warnung leben, unschön aber okay...
meine größere Sorge ist es eben, dass ich nur ein Bild zeichnen kann...
und ich möchte nicht jedesmal n neues Objekt erstellen, wenn es sich nicht verhindern lässt...
BlackJack

@majinv: Du versuchst zweimal das selbe Widget (`self.image`) einem Containerwidget (`self.fixed`) als Kind hinzuzufügen. Das geht halt nicht. Da kannst Du Dir noch so sehr wünschen dass das ginge. Und die Warnung solltest Du auch nicht ignorieren. Wenn man bei GUI-Bibliotheken etwas macht was verboten ist, oder auch nur undefiniert, dann kann das zwar irgendwie funktionieren -- es kann aber auch genau so gut hart abstürzen. Und das auch noch nichtdeterministisch.

Ich weiss auch nicht so ganz wie Du auf die Idee kommst, das man mit einem Widget auskommen kann. Zu einem Widget gehört ja zum Beispiel eine Position. Und an der *einen* Position wird es dargestellt. Was sollte denn passieren wenn Du das gleiche Widget an einer anderen Position `put()`\test? Sollen dann "beide" an der neuen stehen? Wo ist dann der Sinn? Wenn Du das Widget nach seiner Position befragst, welche sollte dann zurückgegeben werden? Was sollte passieren wenn Du auf dem `Fixed`-Exemplar die `move()`-Methode für ein Widget aufrufst, das mehrfach hinzugefügt wurde? Mehrfachverwendung von den selben Widgets würde eine ganze Latte Probleme nach sich ziehen.
majinv
User
Beiträge: 42
Registriert: Mittwoch 14. April 2010, 13:21

BlackJack hat geschrieben:@majinv: Du versuchst zweimal das selbe Widget (`self.image`) einem Containerwidget (`self.fixed`) als Kind hinzuzufügen. Das geht halt nicht [...]
oh man, jetzt hab ichs...
weil ich erst das bild "adde" und dann nochmal "putte", füge ich das zweimal hinzu...
ich bin davon ausgegangen, dass ich ein Bild erst adden muss, bevor ich ihm eine Position zuzweisen kann... ;-)
alles klar Fehler beseitigt...
BlackJack hat geschrieben: Ich weiss auch nicht so ganz wie Du auf die Idee kommst, das man mit einem Widget auskommen kann. Zu einem Widget gehört ja zum Beispiel eine Position. Und an der *einen* Position wird es dargestellt. Was sollte denn passieren wenn Du das gleiche Widget an einer anderen Position `put()`\test? Sollen dann "beide" an der neuen stehen? Wo ist dann der Sinn? Wenn Du das Widget nach seiner Position befragst, welche sollte dann zurückgegeben werden? Was sollte passieren wenn Du auf dem `Fixed`-Exemplar die `move()`-Methode für ein Widget aufrufst, das mehrfach hinzugefügt wurde? Mehrfachverwendung von den selben Widgets würde eine ganze Latte Probleme nach sich ziehen.
hmmm, ich ging jetzt davon aus, dass das widget sich über das ganze Fenster verteilt...
und ich dann soviel darauf rummalen kann wie ich will...
ich hab schon probiert mehere fixed widget mit dem bild zu füllen und an unterschiedliche positionen zu setzen...
allerdings nur mit dem erfolg, dass python noch mehr gemeckert hat... und mehrfach verwendung des einen widgets, hat nur zu der
Fehlermeldung vom anfang geführt...
jenes scheint also meine nächste baustelle...

ich muss also, wenn ich mehrere strichmännchen darstellen will, jedesmal ein neues widget erzeugen?
was aber laut dem compiler nicht geht, der sagte, dass ich immer nur ein widget des selben typs in einem fenster haben darf...
majinv
User
Beiträge: 42
Registriert: Mittwoch 14. April 2010, 13:21

naja, nicht schön aber selten...
es ist zumindest eine Lösung die tut was ich will und die keine warnings wirft...

Code: Alles auswählen

    def init_gui(self):
        self.window = gtk.Window()
        self.window.set_default_size(700, 600)

        #set bg color
        color = gtk.gdk.color_parse('white')
        self.window.modify_bg(gtk.STATE_NORMAL, color)
        
        self.image = []
        for i in range (0, self.countPeople):
            #load image
            self.image.append( gtk.Image() )
            self.image[i].set_from_file("stickFigure.png")
            self.image[i].show()
 
        #create a fixbox
        self.fixed = gtk.Fixed()
        for i in range (0, self.countPeople):
            self.fixed.put(self.image[i],( i * 100 ), ( i * 100 ))
        self.window.add(self.fixed)
        self.fixed.show()

        self.window.show()
auch hier nehme ich gern hinweise entgegen, wie man das besser machen könnte...
BlackJack

@majinv: `xrange()` statt `range()` (es sei denn Du verwendest Python 3.x) beziehungsweise `enumerate()` statt `xrange()`/`range()` bei der zweiten Schleife, und die unnötigen Indexzugriffe könnte man vermeiden.

`self.image` sollte besser `self.images` heissen.
majinv
User
Beiträge: 42
Registriert: Mittwoch 14. April 2010, 13:21

nein... 2.6 ;-)

Code: Alles auswählen

        for i, image in enumerate (self.images):
            self.fixed.put(image,( i * 100 ), ( i * 100 ))
danke... kannte ich vorher noch nicht... :-)
Antworten