PYSIMPLEGUI Daten beim Öffnen eintragen

Hier werden alle anderen GUI-Toolkits sowie Spezial-Toolkits wie Spiele-Engines behandelt.
Antworten
tmessers
User
Beiträge: 28
Registriert: Dienstag 30. Oktober 2018, 21:08

Montag 3. Mai 2021, 20:26

Hallo zusammen,

ich benötige Euren Rat.
Ich lese aus einer url Daten aus und möchte diese in einer GUI (Pysimplegui) darstellen, wenn diese
dargstellt wird .
Beim Drücken des Buttons "Aktualisierung" sollen die Daten aktualisiert werden.

Die GUI wir erstellt, die Daten werden aber nicht übernommen.
Beim Drücken des Buttons werden die Daten korrekt eingetragen.

Ich gehe davon aus, dass der Fehler darin liegt, dass die Funktion zum Auslesen der Daten
die zu befüllenden Felder updated und ein update beim ersten Aufruf der GUI nicht funktioniert.

Der Code sieht wie folgt aus:

Code: Alles auswählen

import datetime
import pandas as pd
import requests
from bs4 import BeautifulSoup
import PySimpleGUI as darstellung

HEADERS = {"User-Agent": "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:44.0) Gecko/20100101 Firefox/44.0"}

def wetter_fr():
    aktuelles_datum = datetime.datetime.now()
    aktuelles_datum = aktuelles_datum.strftime( "%d.%m.%Y   %H:%M" )
    print( aktuelles_datum )
    url = "https://weather.uni-freiburg.de/"
    page = requests.get( url, headers=HEADERS )
    soup = BeautifulSoup( page.content, "html.parser" )
    #print(soup.prettify())
    a = soup.find_all("div", {"class": "meteo-val"})
    #print(a)
    liste_daten =[]
    liste_werte =[]
    liste_del = []
    for b in a:
        c = b.text
        c = c.replace("\n","")
        c = c.replace("°", " ")
        c = c.replace("C", "°")
        c = " ".join(c.split())
        c = c.split()
        liste_daten.append(c[0])
        liste_werte.append(c[1])
        liste_del.append(c[2])
        #print(f"LISTE_DATEN: {liste_daten}")
        #print(f"LISTE_WERTE: {liste_werte}")
        #print(f"LISTE_DEL: {liste_del}")
    print ("Daten für Freiburg im Breisgau")

    df = pd.DataFrame(list(zip(liste_daten,liste_werte,liste_del)), columns = ['Daten',aktuelles_datum,"Einheit"])
    #print (df)
    df = df.set_index("Daten")
    df[aktuelles_datum] = df[aktuelles_datum] + " " + df["Einheit"]
    del df["Einheit"]

    fenster1["_akt_dat_"].update(f"{aktuelles_datum} Uhr")
    fenster1["_lufttemp_"].update(df.at[df.index[0],df.columns[0]])
    fenster1["_luftfeucht_"].update(df.at[df.index[1],df.columns[0]])
    fenster1["_globstr_"].update(df.at[df.index[2],df.columns[0]])
    fenster1["_wind_"].update(df.at[df.index[3],df.columns[0]])
    fenster1["_niedschl_"].update(df.at[df.index[4],df.columns[0]])
    fenster1["_luftdr_"].update(df.at[df.index[5],df.columns[0]])
    #print(df)

darstellung.theme()
layout1 = [{darstellung.Text( "Ablesezeitpunkt", font="Arial", auto_size_text=True)},
            [darstellung.Text(font="Arial", size=(30,1), key='_akt_dat_')],
            [darstellung.Text("Lufttemperatur:", font="Arial", auto_size_text=True)],
            [darstellung.Text(font="Arial", size=(30,1), key='_lufttemp_')],
            [darstellung.Text('Luftfeuchtigkeit', font="Arial", size=(30,1))],
            [darstellung.Text(font="Arial", size=(30,1), key='_luftfeucht_')],
            [darstellung.Text('Globalstrahlung:', font="Arial", auto_size_text=True)],
            [darstellung.Text(font="Arial", size=(30,1), key='_globstr_')],
            [darstellung.Text('Wind:', font="Arial", auto_size_text=True)],
            [darstellung.Text(font="Arial", size=(30,1), key='_wind_')],
            [darstellung.Text('Niederschlag:', font="Arial", auto_size_text=True)],
            [darstellung.Text(font="Arial", size=(30,1), key='_niedschl_')],
            [darstellung.Text('Luftdruck:', font="Arial", auto_size_text=True)],
            [darstellung.Text(font="Arial", size=(30,1), key='_luftdr_')],
            [darstellung.Button("Aktualisieren"), darstellung.Button("Schließen")]]

fenster1 = darstellung.Window("Wetterdaten Freiburg", layout1, auto_size_text=True)

while True:  # Event Loop

    event, values = fenster1.read()

    if event is None or event == 'Schließen':
        fenster1.close()
        break

    if event == 'Aktualisieren':
        wetter_fr()
Ich habe nach einer Lösung gesucht, konnte es aber nicht lösen.

Weiß wer Rat?
Sirius3
User
Beiträge: 14584
Registriert: Sonntag 21. Oktober 2012, 17:20

Montag 3. Mai 2021, 21:18

Warum nennst Du PySimpleGUI in darstellung um? Laut Dokumentation scheint sg üblich zu sein.

Funktionen werden nach Tätigkeiten benannt, also aktualisiere_wetter_daten.
Alles was eine Funktion braucht, muß sie über ihre Argumente bekommen, also zumindest fenster1.
Was soll das 1 bei fenster1, es gibt doch nur ein Fenster.
Warum ist HEADERS eine Konstante, url aber nicht?
a ist ein sehr schlechter Name für div-Elemente. b ist ein sehr schlechter Name für ein div-Element, und c ist ein sehr schlechter Name für Text.
Die vielen replace sind ziemlich willkürlich. Warum erst ein split, dann ein join und dann wieder ein split?
Warum spaltet Du erst die drei zusammenhängenden Daten in drei Liste auf, um sie gleich darauf per zip wieder in eine Liste zusammenzupacken?
Warum trennst Du erst die Einheit vom Wert um gleich darauf Wert und Einheit wieder zu verbinden?
Warum benutzt ein Dataframe, wenn Du doch nur die einzelnen Zeilen wieder kompliziert daraus rausliest, sonst aber nichts mit einem Dataframe machst?
An vielen Stellen machst Du also Dinge um sie nur im nächsten Schritt wieder rückgängig zu machen.
Warum nennst Du Deine Felder so kryptisch? _akt_dat_? _luftdr_?

Code: Alles auswählen

import datetime
import requests
from bs4 import BeautifulSoup
import PySimpleGUI as sq

HEADERS = {"User-Agent": "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:44.0) Gecko/20100101 Firefox/44.0"}
URL = "https://weather.uni-freiburg.de/"

def aktualisiere_wetter_daten(fenster):
    aktuelles_datum = datetime.datetime.now()
    page = requests.get(URL, headers=HEADERS)
    soup = BeautifulSoup(page.content, "html.parser")
    elements = soup.find_all("div", {"class": "meteo-val"})

    fenster["aktuelles_datum"].update(f"{aktuelles_datum:%d.%m.%Y   %H:%M} Uhr")
    for element in elements:
        key, value = element.text.split(None, 1)
        fenster[key].update(value)

def main():
    sq.theme()
    layout = [
        {sq.Text( "Ablesezeitpunkt", font="Arial", auto_size_text=True)},
        [sq.Text(font="Arial", size=(30,1), key='aktuelles_datum')],
        [sq.Text("Lufttemperatur:", font="Arial", auto_size_text=True)],
        [sq.Text(font="Arial", size=(30,1), key='Lufttemperatur')],
        [sq.Text('Luftfeuchtigkeit', font="Arial", size=(30,1))],
        [sq.Text(font="Arial", size=(30,1), key='Luftfeuchte')],
        [sq.Text('Globalstrahlung:', font="Arial", auto_size_text=True)],
        [sq.Text(font="Arial", size=(30,1), key='Globalstrahlung')],
        [sq.Text('Wind:', font="Arial", auto_size_text=True)],
        [sq.Text(font="Arial", size=(30,1), key='Wind')],
        [sq.Text('Niederschlag:', font="Arial", auto_size_text=True)],
        [sq.Text(font="Arial", size=(30,1), key='Niederschlag')],
        [sq.Text('Luftdruck:', font="Arial", auto_size_text=True)],
        [sq.Text(font="Arial", size=(30,1), key='Luftdruck')],
        [sq.Button("Aktualisieren"), sq.Button("Schließen")]
    ]
    fenster = sq.Window("Wetterdaten Freiburg", layout, auto_size_text=True)
    while True:  # Event Loop
        event, values = fenster.read()
        if event is None or event == 'Schließen':
            break
        if event == 'Aktualisieren':
            aktualisiere_wetter_daten(fenster)
    fenster.close()

if __name__ == "__main__":
    main()
Und wenn Du willst, dass die Daten gleich angezeigt werden, dann mußt Du das aktualisiere_wetter_daten vor der while-Schleife einmal aufrufen.
Antworten