Gui freeze

Fragen zu Tkinter.
Antworten
andixx
User
Beiträge: 1
Registriert: Samstag 16. Februar 2013, 10:56

Hi.

Ich hab eine verständnissfrage wie ich ein Programm schreiben muss damit das gui responsible ist während das programm irgend was macht.

Man soll auf dem Gui start anklicken und das Programm soll daraufhin etwas machen. Während es das macht soll der START- zum STOP Button werden um die aktion zu stoppen. Während das progg arbeitet soll natürlich auch was auf dem gui ausgegeben werden. Ich hab es in meinemcodebeispiel jetzt überspitzt, ich weiß natürlich dass die gui eingefroren bleibt solange die methode läuft die der Button aufgerufen hat.

Muss ich jetzt dafür einen Thread starten damit das asynchron läuft oder kann ich das auch anders? Also dass ich mich irgendwie in die mainloop einklinke oder sowas?

Hier mal mein source der so natürlich nicht funktioniert:

Code: Alles auswählen

#!/usr/bin/python3.2

import sys

# Check what python version is used
if (sys.version[:1] != "3"):
    print("\n\nError: XXXXXXX needs Python version >= 3.2.x to be working correctly, but you are using "+sys.version[:5]+"\n\n")
    sys.exit(1)

from tkinter import *
import tkinter.ttk as ttk
import os, time, pickle, argparse
import urllib.request, urllib.error


# Define commandline arguments and parse them
arg_parser = argparse.ArgumentParser()
arg_parser.add_argument("-u", "--url", help="Target Url")
arg_parser.add_argument("-v", "--verbose", help="increase output verbosity", action="store_true")
args = arg_parser.parse_args()


class gui:
    
    def __init__(self):
        self.root = Tk()
        self.root.title('XXXXXXXXXXXX')
        self.root.geometry('1100x669+520+258')
        style = ttk.Style()
        theme = style.theme_use()
        default = style.lookup(theme, 'background')
        self.root.configure(background=default)
    
        #Frame1
        self.Frame1 = Frame (self.root)
        self.Frame1.place(relx=0.01,rely=0.01,relheight=0.16,relwidth=0.98)
        self.Frame1.configure(relief=GROOVE)
        self.Frame1.configure(borderwidth="2")
        self.Frame1.configure(relief="groove")
    
        #Label_url
        self.Label_url = Label (self.Frame1)
        self.Label_url.place(relx=0.01,rely=0.1,height=19,width=32)
        self.Label_url.configure(text='''URL:''')
    
        #Entry_url
        self.Entry_url = Entry (self.Frame1)
        self.Entry_url.place(relx=0.05,rely=0.1,relheight=0.2,relwidth=0.83)
        if (args.url): self.Entry_url.insert(0, args.url)
    
        #Start/Stop Button
        self.Button_start = Button (self.Frame1)
        self.Button_start.place(relx=0.89,rely=0.1,height=25,width=95)
        self.Button_start.configure(text='''START''')
        self.Button_start.configure(command=self.testlala)
        
        #Frame2
        self.Frame2 = Frame (self.root)
        self.Frame2.place(relx=0.01,rely=0.19,relheight=0.78,relwidth=0.98)
        self.Frame2.configure(relief=GROOVE)
        self.Frame2.configure(borderwidth="2")
        self.Frame2.configure(relief="groove")
 
        #Ausgabe
        self.Text_ausgabe = Text (self.Frame2)
        self.Text_ausgabe.place(relx=0.01,rely=0.02,relheight=0.91,relwidth=0.98)
        self.Text_ausgabe.configure(wrap="none")

        self.running = False

        self.root.mainloop()


    def testlala(self):
        if self.running == True:
            self.running = False
            self.Button_start.configure(text='''START''')
        else:
            self.running = True
            self.Button_start.configure(text='''STOP''')
            self.lala()
        self.Text_ausgabe.insert(END,"Button pressed\n")

    def lala(self):
        while self.running == True:
            print("blabla")
            time.sleep(2)
        print("fertig")


ui = gui()

BlackJack

@andixx: Üblicherweise wird das per Arbeitsthread und Queue zur Kommunikation mit dem GUI-Thread gelöst.

Edit: Du könntest mal einen Blick in den Style Guide for Python Code werfen was zum Beispiel die Namensschreibweisen angeht.

Sternchenimporte sollte man vermeiden, damit macht man Quelltexte schwerer nachvollziehbar, weil es nicht mehr so einfach ist zu sehen wo eigentlich welcher Name herkommt.

Kommentare sollten dem Leser einen Mehrwert zum Quelltext bieten und nicht das noch mal sagen was da eh schon sehr deutlich im Quelltext lesbar ist. Und wenn Kommentare dann sollten sie nicht sagen *was* da gemacht wird, sondern warum es gemacht wird und in einigen Fällen auch warum genau so und nicht anders. Von den vorhandenen Kommentaren ist IMHO kein einziger sinnvoll.

Feste Vorgabe der Fenstergrösse und `place()` ergeben keine gute GUI. Das Layout sollte man der GUI überlassen und relativ zu den tatsächlichen Gegebenheiten wie Bildschirm- und Schriftgrössen und Auflösungen machen lassen. Nur so bekommt man GUIs die grösstenteils unabhängig von diesen Faktoren sinnvoll und benutzbar präsentiert werden.

Um Bedingungen bei ``if`` und andere Schlüsselworte gehören keine Klammern.

Es werden mehr Objekte an das `gui`-Exemplar gebunden als nötig wäre. Wenn man etwas ausserhalb der Methode nicht benötigt, macht es keinen Sinn den Wert an das Objekt zu binden.
Antworten