Probleme mit Formatierter Ausgabe.
Verfasst: Samstag 11. Mai 2019, 13:52
Hallo ich bin blutiger Anfänger in der Python programmierung.
Ich habe ein Programm zum Auslesen eines Vielfachmessgerätes umgebaut zum Auslesen der Feldstärke eines Kurzwellen-Empfängers.
Das Auslesen der Messwerte und Plotten funktioniert soweit alles.
Mein Problem ist dass ich die Ausgelesenen Messwerte ( 00 bis 22 )in S-Meter werte umwandeln will.
00 = S0
02 = S1
03 = S2
04 = S3
05 = S4
06 = S5
08 = S6
09 = S7
10 = S8
11 = S9
12 = S9+10
14 = S9+20
16 = S9+30
18 = S9+40
20 = S9+50
22 = S9+60
Geht das mit Formatierter Ausgabe? Ich kriege das nicht hin.
Jeder Hinweis ist erwünscht.
## Programm zur Steuerung des Transceivers Elad FDM-Duo
## Das Programm kann:
## 1.Frequenz setzen. OK
## 2.Die Modulationsart setzen.OK
## 3.Das S-Meter auslesen.OK
## 4.Verlauf der Messwerte des S-Meters grafisch darstellen. OK.
## Ich habe dieses Programm nicht selbst geschrieben,sondern von der University Reutlingen
## Fakultät TEC:Messtechnik mit Pythen heruntergeladen und geändert.
## Es war ursprünglich ein Programm zum Auslesen von Daten eines Vielfachmessgerätes.
##
## 29.04.2019 L.Holzer DF8LHO
#!/usr/bin/python3
import matplotlib.pyplot as plt
import tkinter as TK
import serial
from time import sleep
# Objekt fuer serielle Kommunikation
portDmm = serial.Serial()
# Tkinter Hauptfenster
root=TK.Tk()
root.title("Elad FDM-Duo")
# Eingabewerte durch Benutzer
comPortNo = TK.StringVar() # StringVar()-Objekt wird erzeugt und der Variablen comPortNo zugewiesen
comPortNo.set("COM11") # Initalwerte werden dem Objekt gegeben
numMeas = TK.IntVar() # IntVar()-Objekt wird erzeugt und der Variablen numMeas zugewiesen
numMeas.set(20) # Initalwerte werden dem Objekt gegeben Messungen
sampTime = TK.IntVar()
sampTime.set(1) #Periode(S)
# GUI Texte (macht hier Sinn, wenn andere Sprache noetig
comPortTxt='COM-Port:'
numMeasPerTxt='# Messungen / Periode (h):'
valTxt='Aktueller Messwert:'
unitTxt='Einheit'
# COM-Verbindung aufbauen
def connComPort(port):
print('connComPort()')
# Serielle Schnittstelle oeffnen. Muss vor GUI geschehen, damit dort Info ueber COM-Verbindungsstatus
try:
port.baudrate = 38400
port.port = comPortNo.get()
port.parity = serial.PARITY_NONE
port.stopbit = serial.STOPBITS_ONE
port.bytesize = serial.EIGHTBITS
port.timeout = 2
port.setDTR(True) # fuer Stromversorgung RS-232 Interface.
port.setRTS(False)
port.open()
print('COM-Verbindung OK')
comStatusLabel.configure(text='COM-Verbindung OK')
port.flushInput() # Seriellen Puffer leeren
except:
print('Keine COM-Verbindung')
comStatusLabel.configure(text='Keine COM-Verbindung')
# Call Back Funktion fuer Klicken des Buttons (in tkinter kann leider kein Parameter uebergeben werden)
def comConnButton():
print('comConnButton()')
connComPort(portDmm)
# Call Back Funktion fuer Klicken des Buttons (in tkinter kann leider kein Parameter uebergeben werden)
def singleMeasButton():
print('singleMeasButton()')
singleMeas(portDmm)
# Call Back Funktion fuer Klicken des Buttons (in tkinter kann leider kein Parameter uebergeben werden)
def multiMeasPlotButton():
multiMeasPlot(portDmm)
# Einzelmessung
def singleMeas(port):
print('Parameter setzen')
try:
#port.write(b'D')
#port.write(b"FA00000016400;") # Frequenz setzen (16,4 Khz)
port.write(b"FA00000023400;") # Frequenz setzen (23,4 Khz)
port.write(b"MD3;")#Einstellung CW+
#port.write(b"MD4;")#Einstellung FM
port.write(b"SMO;")#Einstellung S-Meter auslesen
result = port.read(8) # Daten aus dem Elad FDM-Duo auslesen (8 Byte)
if len(result) == 8: # Umwandlung in String und Formatierungszeichen entfernen, falls Datensatz konsistent
print(str(result)[7:9])# Nur den Aktuellen Messwert auslesen. ( 00006 )
val = str(result)[7:9] # Nur den Messwert auslesn. ( 00006 )
comStatusLabel.configure(text='Elad FDM-Duo OK') # Labeltext aktualisieren
else:
print('Kein passender Antwortstring vom Elad FDM-DUO (Elad FDM-DUO antwortet nicht).')
val = '00000' # Muss Zahl sein, falls Messreihe (wegen Berechnung Statistikparameter)
comStatusLabel.configure(text='Daten DMM inkonsistent')
except:
print('COM-Verbindung abgebrochen')
comStatusLabel.configure(text='COM-Verbindung abgebrochen')
val = '00000'
valLabel.configure(text=val)
return val
# Messreihe
def multiMeasPlot(port):
print('Messreihe')
results = list(range(0, numMeas.get())) # Liste fuer Messwerte, muesste eigentlich nicht initialisiert werden
times = [j * sampTime.get() for j in list(range(0, numMeas.get()))] # Messzeiten als "List Comprehension"
for i in range(0,numMeas.get(),1):
results = float(singleMeas(port))
print('Messreihe Messung ',i)
sleep(sampTime.get()) # Samplingperiode lang warten
xwerte = [j * sampTime.get() for j in list(range(0, numMeas.get()))] #range(10)messung beginnt erst bei 10
# plt.plot ([0,24,],[0,24,]
plt.plot(times, results)
plt.xlabel('Stunden')
plt.ylabel('S-Meter Anzeige')#Beschriftung y-Achse fest.
plt.title('Elad FDM-DUO 23.400 Khz DHO38 Germany ') #Überschrift Messplot
plt.xticks(xwerte) # x-Achsenbeschriftung fuer jeden Messwert
# plt.grid(True)# Gitterlinien können entfernt werden.
plt.show()
# Einzelne widgets: Hier werden die Buttons, Labels und Eingabefelder erzeugt und deren Layout
# festgelegt. Bei den Eingabefeldern (TK.Entry) werden die Variablen definiert.
comConnButton=TK.Button(root,text="COM-Schnittstelle verbinden",command=comConnButton,bg='light blue') # Button COM Verbinden
comStatusLabel=TK.Label(root,text='Keine COM-Verbindung',width=20,bg='light blue') # Status COM Verbindung. width ändert Breite des 1.Fensters
comInputLabel=TK.Label(root,text=comPortTxt,width=len(comPortTxt)) # Anzahl Messungen / Abtastperiode
comPortEnter=TK.Entry(root,textvariable=comPortNo,width=len(comPortTxt)) # Eingabemaske fuer COM-Port Nummer
numSampInputLabel=TK.Label(root,text=numMeasPerTxt,width=len(numMeasPerTxt))
numMeasEnter=TK.Entry(root,textvariable=numMeas,width=8) # Eingabemaske fuer Anzahl Messungen
sampTimeEnter=TK.Entry(root,textvariable=sampTime,width=8) # Eingabemaske fuer Abtastperiode
singleMeasButton=TK.Button(root,text="Parameter setzen",command=singleMeasButton) # Button Einzelmessung
multiMeasButton=TK.Button(root,text="Messreihe+Plot",command=multiMeasPlotButton) # Button Messreihe
valTextLabel=TK.Label(root,text=valTxt,width=len(valTxt)) # Aktueller Messwert
valLabel=TK.Label(root,text='-----',width=20) # Ausgabe aktueller Messwert
#Festlegung Layout der gesamten GUI: Tabellenanordnung der Widget TK.E = Textausrichtung East
comConnButton.grid(row=40,columnspan=3,sticky=TK.E+TK.W) #row=40 COM-Schnittstelle verbinden ist jetzt am unteren Ende.
comStatusLabel.grid(row=1,columnspan=3,sticky=TK.E+TK.W)#row=10 Keine Com Verbindung ist jetz am unteren Ende.
comInputLabel.grid(row=2,column=0,sticky=TK.E)#row stelle an der Com-Port steht
comPortEnter.grid(row=2,column=1,sticky=TK.W)
numSampInputLabel.grid(row=3,column=0,sticky=TK.E) #stelle an der Messunge /Periode steht
numMeasEnter.grid(row=3,column=1,sticky=TK.W)#stelle an der das Eingabefeld für Messungen steht
sampTimeEnter.grid(row=3,column=2,sticky=TK.W)#stelle an der das Eingabefeld für Periode steht.
singleMeasButton.grid(row=4,column=0,sticky=TK.E)#stelle an der Parameter setzen steht
multiMeasButton.grid(row=4,column=1,sticky=TK.W)#stelle an der Messreihe +Plott steht.
valTextLabel.grid(row=5,column=0,sticky=TK.E)#stelle an der Aktueller Messwert steht.
valLabel.grid(row=5,column=1,sticky=TK.W)#stelle an der Aktueller Messwert angezeigt wird.
# GUI starten
TK.mainloop()
Ich habe ein Programm zum Auslesen eines Vielfachmessgerätes umgebaut zum Auslesen der Feldstärke eines Kurzwellen-Empfängers.
Das Auslesen der Messwerte und Plotten funktioniert soweit alles.
Mein Problem ist dass ich die Ausgelesenen Messwerte ( 00 bis 22 )in S-Meter werte umwandeln will.
00 = S0
02 = S1
03 = S2
04 = S3
05 = S4
06 = S5
08 = S6
09 = S7
10 = S8
11 = S9
12 = S9+10
14 = S9+20
16 = S9+30
18 = S9+40
20 = S9+50
22 = S9+60
Geht das mit Formatierter Ausgabe? Ich kriege das nicht hin.
Jeder Hinweis ist erwünscht.
## Programm zur Steuerung des Transceivers Elad FDM-Duo
## Das Programm kann:
## 1.Frequenz setzen. OK
## 2.Die Modulationsart setzen.OK
## 3.Das S-Meter auslesen.OK
## 4.Verlauf der Messwerte des S-Meters grafisch darstellen. OK.
## Ich habe dieses Programm nicht selbst geschrieben,sondern von der University Reutlingen
## Fakultät TEC:Messtechnik mit Pythen heruntergeladen und geändert.
## Es war ursprünglich ein Programm zum Auslesen von Daten eines Vielfachmessgerätes.
##
## 29.04.2019 L.Holzer DF8LHO
#!/usr/bin/python3
import matplotlib.pyplot as plt
import tkinter as TK
import serial
from time import sleep
# Objekt fuer serielle Kommunikation
portDmm = serial.Serial()
# Tkinter Hauptfenster
root=TK.Tk()
root.title("Elad FDM-Duo")
# Eingabewerte durch Benutzer
comPortNo = TK.StringVar() # StringVar()-Objekt wird erzeugt und der Variablen comPortNo zugewiesen
comPortNo.set("COM11") # Initalwerte werden dem Objekt gegeben
numMeas = TK.IntVar() # IntVar()-Objekt wird erzeugt und der Variablen numMeas zugewiesen
numMeas.set(20) # Initalwerte werden dem Objekt gegeben Messungen
sampTime = TK.IntVar()
sampTime.set(1) #Periode(S)
# GUI Texte (macht hier Sinn, wenn andere Sprache noetig
comPortTxt='COM-Port:'
numMeasPerTxt='# Messungen / Periode (h):'
valTxt='Aktueller Messwert:'
unitTxt='Einheit'
# COM-Verbindung aufbauen
def connComPort(port):
print('connComPort()')
# Serielle Schnittstelle oeffnen. Muss vor GUI geschehen, damit dort Info ueber COM-Verbindungsstatus
try:
port.baudrate = 38400
port.port = comPortNo.get()
port.parity = serial.PARITY_NONE
port.stopbit = serial.STOPBITS_ONE
port.bytesize = serial.EIGHTBITS
port.timeout = 2
port.setDTR(True) # fuer Stromversorgung RS-232 Interface.
port.setRTS(False)
port.open()
print('COM-Verbindung OK')
comStatusLabel.configure(text='COM-Verbindung OK')
port.flushInput() # Seriellen Puffer leeren
except:
print('Keine COM-Verbindung')
comStatusLabel.configure(text='Keine COM-Verbindung')
# Call Back Funktion fuer Klicken des Buttons (in tkinter kann leider kein Parameter uebergeben werden)
def comConnButton():
print('comConnButton()')
connComPort(portDmm)
# Call Back Funktion fuer Klicken des Buttons (in tkinter kann leider kein Parameter uebergeben werden)
def singleMeasButton():
print('singleMeasButton()')
singleMeas(portDmm)
# Call Back Funktion fuer Klicken des Buttons (in tkinter kann leider kein Parameter uebergeben werden)
def multiMeasPlotButton():
multiMeasPlot(portDmm)
# Einzelmessung
def singleMeas(port):
print('Parameter setzen')
try:
#port.write(b'D')
#port.write(b"FA00000016400;") # Frequenz setzen (16,4 Khz)
port.write(b"FA00000023400;") # Frequenz setzen (23,4 Khz)
port.write(b"MD3;")#Einstellung CW+
#port.write(b"MD4;")#Einstellung FM
port.write(b"SMO;")#Einstellung S-Meter auslesen
result = port.read(8) # Daten aus dem Elad FDM-Duo auslesen (8 Byte)
if len(result) == 8: # Umwandlung in String und Formatierungszeichen entfernen, falls Datensatz konsistent
print(str(result)[7:9])# Nur den Aktuellen Messwert auslesen. ( 00006 )
val = str(result)[7:9] # Nur den Messwert auslesn. ( 00006 )
comStatusLabel.configure(text='Elad FDM-Duo OK') # Labeltext aktualisieren
else:
print('Kein passender Antwortstring vom Elad FDM-DUO (Elad FDM-DUO antwortet nicht).')
val = '00000' # Muss Zahl sein, falls Messreihe (wegen Berechnung Statistikparameter)
comStatusLabel.configure(text='Daten DMM inkonsistent')
except:
print('COM-Verbindung abgebrochen')
comStatusLabel.configure(text='COM-Verbindung abgebrochen')
val = '00000'
valLabel.configure(text=val)
return val
# Messreihe
def multiMeasPlot(port):
print('Messreihe')
results = list(range(0, numMeas.get())) # Liste fuer Messwerte, muesste eigentlich nicht initialisiert werden
times = [j * sampTime.get() for j in list(range(0, numMeas.get()))] # Messzeiten als "List Comprehension"
for i in range(0,numMeas.get(),1):
results = float(singleMeas(port))
print('Messreihe Messung ',i)
sleep(sampTime.get()) # Samplingperiode lang warten
xwerte = [j * sampTime.get() for j in list(range(0, numMeas.get()))] #range(10)messung beginnt erst bei 10
# plt.plot ([0,24,],[0,24,]
plt.plot(times, results)
plt.xlabel('Stunden')
plt.ylabel('S-Meter Anzeige')#Beschriftung y-Achse fest.
plt.title('Elad FDM-DUO 23.400 Khz DHO38 Germany ') #Überschrift Messplot
plt.xticks(xwerte) # x-Achsenbeschriftung fuer jeden Messwert
# plt.grid(True)# Gitterlinien können entfernt werden.
plt.show()
# Einzelne widgets: Hier werden die Buttons, Labels und Eingabefelder erzeugt und deren Layout
# festgelegt. Bei den Eingabefeldern (TK.Entry) werden die Variablen definiert.
comConnButton=TK.Button(root,text="COM-Schnittstelle verbinden",command=comConnButton,bg='light blue') # Button COM Verbinden
comStatusLabel=TK.Label(root,text='Keine COM-Verbindung',width=20,bg='light blue') # Status COM Verbindung. width ändert Breite des 1.Fensters
comInputLabel=TK.Label(root,text=comPortTxt,width=len(comPortTxt)) # Anzahl Messungen / Abtastperiode
comPortEnter=TK.Entry(root,textvariable=comPortNo,width=len(comPortTxt)) # Eingabemaske fuer COM-Port Nummer
numSampInputLabel=TK.Label(root,text=numMeasPerTxt,width=len(numMeasPerTxt))
numMeasEnter=TK.Entry(root,textvariable=numMeas,width=8) # Eingabemaske fuer Anzahl Messungen
sampTimeEnter=TK.Entry(root,textvariable=sampTime,width=8) # Eingabemaske fuer Abtastperiode
singleMeasButton=TK.Button(root,text="Parameter setzen",command=singleMeasButton) # Button Einzelmessung
multiMeasButton=TK.Button(root,text="Messreihe+Plot",command=multiMeasPlotButton) # Button Messreihe
valTextLabel=TK.Label(root,text=valTxt,width=len(valTxt)) # Aktueller Messwert
valLabel=TK.Label(root,text='-----',width=20) # Ausgabe aktueller Messwert
#Festlegung Layout der gesamten GUI: Tabellenanordnung der Widget TK.E = Textausrichtung East
comConnButton.grid(row=40,columnspan=3,sticky=TK.E+TK.W) #row=40 COM-Schnittstelle verbinden ist jetzt am unteren Ende.
comStatusLabel.grid(row=1,columnspan=3,sticky=TK.E+TK.W)#row=10 Keine Com Verbindung ist jetz am unteren Ende.
comInputLabel.grid(row=2,column=0,sticky=TK.E)#row stelle an der Com-Port steht
comPortEnter.grid(row=2,column=1,sticky=TK.W)
numSampInputLabel.grid(row=3,column=0,sticky=TK.E) #stelle an der Messunge /Periode steht
numMeasEnter.grid(row=3,column=1,sticky=TK.W)#stelle an der das Eingabefeld für Messungen steht
sampTimeEnter.grid(row=3,column=2,sticky=TK.W)#stelle an der das Eingabefeld für Periode steht.
singleMeasButton.grid(row=4,column=0,sticky=TK.E)#stelle an der Parameter setzen steht
multiMeasButton.grid(row=4,column=1,sticky=TK.W)#stelle an der Messreihe +Plott steht.
valTextLabel.grid(row=5,column=0,sticky=TK.E)#stelle an der Aktueller Messwert steht.
valLabel.grid(row=5,column=1,sticky=TK.W)#stelle an der Aktueller Messwert angezeigt wird.
# GUI starten
TK.mainloop()