matplotlib Graph erneuern

mit matplotlib, NumPy, pandas, SciPy, SymPy und weiteren mathematischen Programmbibliotheken.
Antworten
Andi83
User
Beiträge: 1
Registriert: Montag 28. Oktober 2019, 08:44

Hallo,
ich hab mir einen ARM programmiert in bestimmten Intervallen eine bestimmte Anzahl Beschleunigungsmessungen durch zuführen und die Werte dann über UART an einen Pi 4 zu übergeben.
Das Funktioniert auch wunderbar.
Das Problem ist das mit Python noch nie etwas gemacht habe aber nun ein Tool erstellen möchte um die Daten zu plotten.

Habe mich wortwörtlich durchgewurstelt zu folgendem Stand:
Mit Python 3.7.3 tkinter wird das GUI erstellt und mit der matplotlib ,... der Graph eingebettet welcher auch schön erzeugt wird.
serielle Schnitstelle und Stringverarbeitung funktionieren wunderbar.
Momentan wir ein Beispielgrap beim Start geplottet.

Eigentlich möchte ich aber das der Graph in der Funktion "GenerateGraph()" erzeugt oder neu geplottet wird bekomme es aber nicht hin.

Ich habe den Code auf das wesentliche gekürzt und es wäre schön wenn mir jemand einen Tip geben kann.
Ebenso beim Einfügen der Labels als Legende

Code: Alles auswählen

from tkinter import *  
from PIL import ImageTk,Image  
from serial import *
import time
from matplotlib.backends.backend_tkagg import (
    FigureCanvasTkAgg, NavigationToolbar2Tk)
from matplotlib.backend_bases import key_press_handler
from matplotlib.figure import Figure
import numpy as np


anzahl1 = 100
range1 = 16
intervall1 = 1
serBuffer = ""

graph_count = [1, 2, 3, 4, 5]
graph_x = [1, 2, 3, 4, 5]
graph_y = [2, 3, 4, 5, 6]
graph_z = [3, 4, 5, 6, 7]


MainWindow = Tk()

def KeyEscape(event):
    MainWindow.destroy()
    sys.exit()
MainWindow.bind("<Escape>",KeyEscape)
  

def readSerial():
    while True:
        c = ser.read().decode("ascii")     # c = ser.read() # attempt to read a character from Serial
        if len(c) == 0:                    # was anything read?
            break
        global serBuffer                   # get the buffer from outside of this function
        if c == '\r':                      # check if character is a delimeter
            c = ''                         # don't want returns. chuck it   
        if c == '\n':
            serBuffer += "\n"              # add the newline to the buffer   
            #FmT1.insert('0.0', serBuffer)  # add the line to the TOP of the log
            FmT1.insert('end', serBuffer)  # add the line to the BOTTOM of the log
            serBuffer = ""                 # empty the buffer
        else:
            serBuffer += c                 # add to the buffer
    MainWindow.after(1000, readSerial)     # check serial again soon

def Start():
    print("Start()")
    #...

def WerteGeben():
    print("\nWerteGeben()")
    #...

def GenerateGraph():
    print ("GenerateGraph()")
    #...
 
    global graph_count
    global graph_x
    global graph_y
    global graph_z

    graph_count = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
    graph_x = [5, 4, 3, 2, 1, 1, 2, 3, 4, 5]
    graph_y = [6, 5, 4, 3, 2, 2, 3, 4, 5, 6]
    graph_z = [7, 6, 5, 4, 3, 3, 4, 5, 6, 7] 
    
    
ser = Serial(
    port='/dev/serial0',
    baudrate = 115200,parity=PARITY_NONE,
    stopbits=STOPBITS_ONE,
    bytesize=EIGHTBITS,
    timeout=1
)

MainWindow.title("Test")
screenW, screenH = MainWindow.winfo_screenwidth(), MainWindow.winfo_screenheight()
MainWindow.geometry("%dx%d+0+0" % (screenW, screenH-200))

FrameOben = Frame(MainWindow, bd="5")
FrameOben.pack(fill = X,side = "top")
FoL1 = Label(FrameOben, text="TestGrapher v0.1",font=('Arial', 55))
FoL1.pack(side = "left")

FrameMitte = Frame(MainWindow, bd="5")
FrameMitte.pack(fill = "both", expand = True)
scrollbar = Scrollbar(FrameMitte)
scrollbar.pack(side=LEFT, fill=Y)
FmT1 = Text ( FrameMitte, width=30, takefocus=0)
FmT1.pack(side = "left",fill = "y", expand = False)
FmT1.config(yscrollcommand=scrollbar.set)
scrollbar.config(command=FmT1.yview)


fig = Figure(figsize=(5, 4), dpi=100)
fig.add_subplot(111).plot(graph_count,graph_x,graph_count,graph_y,graph_count,graph_z)

canvas = FigureCanvasTkAgg(fig, master=FrameMitte)
canvas.draw()
canvas.get_tk_widget().pack(side="bottom", fill="both", expand=True)

toolbar = NavigationToolbar2Tk(canvas, FrameMitte)
toolbar.update()
canvas.get_tk_widget().pack(side="top", fill="both", expand=True)


FrameUnten = Frame(MainWindow, bd="5")
FrameUnten.pack(fill = X, side ="bottom")
FuL1 = Label(FrameUnten, padx=5, text="Anzahl Werte 1-20000" )
FuL1.grid(row=0, column=0)
FuE1 = Entry(FrameUnten)
FuE1.insert(0, anzahl1)
FuE1.grid(row=0, column=1, padx=9)

FuL2 = Label(FrameUnten, padx=5, text="Messintervall 1-100 ms" )
FuL2.grid(row=1, column=0)
FuE2 = Entry(FrameUnten)
FuE2.insert(0, intervall1)
FuE2.grid(row=1, column=1, padx=9)

FuL3 = Label(FrameUnten, padx=5, text="hohe Anzahl und Intervalle dauern sehr lange!!!" )
FuL3.grid(row=3, column=0,columnspan=2)

FuL4 = Label(FrameUnten, padx=5, text="Range" )
FuL4.grid(row=0, column=2, sticky=W)
VarChoise = IntVar(MainWindow)
VarChoise.set(range1) # set the default option
popupMenu = OptionMenu(FrameUnten, VarChoise, '2','4','8','16')
popupMenu.grid(row=0, column=3, padx=9, sticky=E) 

FuB1 = Button(FrameUnten,width=13, text='Werte übergeben', command=WerteGeben)
FuB1.grid(row=0, column=4, padx=9, sticky=W )
FuB2 = Button(FrameUnten,width=13, text='manual START', command=Start)
FuB2.grid(row=1, column=4, padx=9, sticky=W )

FuB2 = Button(FrameUnten,width=13, text='Graph generieren', command=GenerateGraph)
FuB2.grid(row=0, column=5, padx=9, sticky=E )
FrameUnten.grid_columnconfigure(5, weight=1)


MainWindow.after(300, readSerial)
MainWindow.mainloop()
__deets__
User
Beiträge: 14545
Registriert: Mittwoch 14. Oktober 2015, 14:29

Es reicht nicht, einfach nur die Namen an neue Werte zu binden. Du musst auch den Plot selbst updaten. Wenn die Daten immer die gleiche Form haben, kannst du das wie hier beschrieben machen: https://stackoverflow.com/questions/409 ... matplotlib
Antworten