Progressbar.step funktioniert nicht unter .grid !!!!!!!

Fragen zu Tkinter.
Antworten
mexxwell
User
Beiträge: 6
Registriert: Sonntag 24. Februar 2013, 14:55

Hallo Zusammen!

Vielleicht kann mir jemand helfen bevor ich die letzten Haare verliere!!! :evil:
Ich versuche für den Raspberry Pi eine Temperaturanzeige zu programmieren.
Mittels .grid habe ich bereits das Layout erstellt und es wird auch korrekt angezeigt.
Nur:
Ich habe als Temp-Anzeige zwei Progressbar, welche ich auch mittels .step ansteuern kann.
Nur, funktioniert das nur, wenn ich den .pack Manager verwende - mit der Methode .grid zum anordnen der Widgets bekomme
ich Fehlermeldungen!

Hat jemand eine Idee???? :K

Hier mein Code:

Code: Alles auswählen

import Tkinter as tk
import ttk
from Tkinter import * 
import Image as PIL
import ImageTk

def click():
	pbar.step(10)

main= Tk();
main.title('Main')

##########################################################
# Definition der oberen Umgebungstemperatur Widgets      

Label(main,text='Umgebungstemperatur').grid(row=1,column=1)
Umg_temp_text = Label(main,text='12').grid(row=1,column=2)

image = PIL.open('wr1.png')
photo = ImageTk.PhotoImage(image)
Label(main,image=photo).grid(row=2,column=0)

pbar = ttk.Progressbar(main, length=300).grid(row=2,column=1)

image2 = PIL.open('wr2.png')
photo2 = ImageTk.PhotoImage(image2)
Label(main,image=photo2).grid(row=2,column=2)

Umg_temp_scale = Label(main,text="-25  -10   0   5   10   15   20   25   30   35   40").grid(row=3,column=1)

##########################################################
# Definiton des Abstandbalkens 

canvas=Canvas(main, width=200, height=10).grid(row=4,column=1)

##########################################################
# Definition der unteren Innenraumtemperatur Widgets    

Label(main,text='Innenraumtemperatur').grid(row=5,column=1)
Inn_temp_text = Label(main,text='12').grid(row=5,column=2)

image3 = PIL.open('wr1.png')
photo3 = ImageTk.PhotoImage(image3)
Label(main,image=photo3).grid(row=6,column=0)

Inn_temp_bar = ttk.Progressbar(main, length=300).grid(row=6,column=1)

image4 = PIL.open('wr2.png')
photo4 = ImageTk.PhotoImage(image4)
Label(main,image=photo4).grid(row=6,column=2)

Inn_temp_scale = Label(main,text="-25  -10   0   5   10   15   20   25   30   35   40").grid(row=7,column=1)

#############################################################
# Testbuttons zum auffuellen und loeschen der Temperaturbalken sowie zum aendern des TempLabels

Umg_temp_vor = ttk.Button(text="Vor", command=click).grid(row=8,column=1)

main.mainloop()

LG aus Wien
Zuletzt geändert von Anonymous am Sonntag 24. Februar 2013, 15:15, insgesamt 1-mal geändert.
Grund: Code-Formatierung korrigiert
Benutzeravatar
vegaseat
User
Beiträge: 6
Registriert: Montag 28. Januar 2013, 22:53
Wohnort: Las Vegas Nevada USA

pbar = ttk.Progressbar(main, length=300).grid(row=2,column=1)

hier pbar gibt Dir nicht das object sondern wo es ist im grid()

Du musst es so schreiben ...

Code: Alles auswählen

pbar = ttk.Progressbar(main, length=300)
pbar.grid(row=2,column=1)
mexxwell
User
Beiträge: 6
Registriert: Sonntag 24. Februar 2013, 14:55

Super funktioniert jetzt dank deinem schnellen Tip!!

Vielen lieben Dank, LG aus Wien
BlackJack

@mexxwell: Das hat überhaupt nichts mit `grid()` oder `pack()` zu tun.

Wenn Du Fehlermeldungen bekommst, wäre es nett diese auch zu verraten, dann muss man das nicht selbst heraus finden, beziehungsweise kann es ja sogar sein, dass man andere oder gar keine Fehlermeldung bekommt. Die Meldung hier jedenfalls lautet:

Code: Alles auswählen

Exception in Tkinter callback
Traceback (most recent call last):
  File "/usr/lib/python2.7/lib-tk/Tkinter.py", line 1413, in __call__
    return self.func(*args)
  File "./forum3.py", line 10, in click
    pbar.step(10)
AttributeError: 'NoneType' object has no attribute 'step'
Also ist `pbar` anscheinend nicht was Du denkst was es ist. Es ist ein Objekt vom Typ `None` und die haben keine `step()`-Methode. Also schauen wir mal wo `pbar` an `None` gebunden wird:

Code: Alles auswählen

pbar = ttk.Progressbar(main, length=300).grid(row=2,column=1)
Die `grid()`-Methode gibt `None` zurück. So kannst Du das also nicht schreiben. Und hier wird auch klar, dass es nichts mit `grid()` versus `pack()` zu tun hat, denn die `pack()`-Methode gibt ebenfalls `None` zurück, damit hätte man also exakt das gleiche Problem. Da Du das anscheinend nicht hattest als Du `pack()` verwendet hast, musst Du da etwas *anders* gemacht haben. Womit Du im Grunde auch schon wissen müsstest wie man das mit `grid()` anders machen muss, damit es funktioniert.

Du sollest dabei dann mal über den Quelltext gehen und überall wo Du `None` auf diese Weise an Namen bindest, das ändern oder einfach den Namen weglassen. Denn da wo das nicht zu fehlern führt, bedeutet es ja, dass der Name nie gebraucht wird. Beziehungsweise generell nur an Namen binden was auch tatsächlich benötigt wird und einige Zwischenergebnisse direkt verwenden.

Ansonsten wäre zu dem Programm noch zu sagen, das Sternchenimporte, vor allem bei Modulen die so viele Namen enthalten wie das `Tkinter`-Modul (ca. 200) keine gute Idee sind. Du hast es ja sogar *auch* unter dem Namen `tk` importiert — dann nutze das doch auch.

Code-Wiederholungen sind etwas was man als Programmierer vermeiden sollte. Für die beiden Temperaturanzeigen steht da zweimal fast identischer Quelltext. So etwas gehört in eine Funktion. Beziehungsweise bei GUIs sollte man IMHO schon objektorientierte Programmierung halbwegs drauf haben *bevor* man mit der GUI-Programmierung beginnt. Denn nur dann kann man saubere Programme schreiben, die etwas komplexer als ein „Hallo, Welt!”-Programm sind. So eine komplette Temperaturanzeige könnte man prima in einer eigenen Widget-Klasse zusammenfassen.

Bezüglich der Namensgebung sei Dir noch der Style Guide for Python Code ans Herz gelegt. Man sollte ausserdem Abkürzungen bei Namen vermeiden wenn die nicht allgemein geläufig sind. Bei `pbar` darf man raten, bei `progress_bar` ist sogar ohne Kontext den meisten klar was sich hinter dem Namen verbirgt. Ich finde ausserdem Denglish schrecklich. `Umg_temp_scale`, hä?
Antworten