# model import serial def scan(): """ gibt eine Liste von Strings der Namen der verfuegbaren Ports zurück """ L = [] for i in range(10): try: s = serial.Serial('/dev/ttyS'+str(i)) L.append(s.portstr) s.close() except serial.SerialException: pass for i in range(10): try: s = serial.Serial('/dev/ttyUSB'+str(i)) L.append(s.portstr) s.close() except serial.SerialException: pass for i in range(10): try: s = serial.Serial('COM'+str(i)) L.append(s.portstr) s.close() except serial.SerialException: pass for i in range(10): try: s = serial.Serial(i) L.append(i) s.close() except serial.SerialException: pass return L def ByteToBin(b): """ gibt einen String der Länge 8 zurueck, der das Byte b darstellt, Beispiel: 65 --> '01000001' """ return bin(b)[2:].zfill(8) def BinToByte(s): """ gibt ein Byte zurueck, das aus dem String s ermittelt wurde """ return int(s,2) import time def receiveByte(bitzeit,getLeitung): """ im miniRS232-Protokoll wird mit der Bitzeit bitzeit in s und der Funktion getLeitung zum Abtasten der Leitung ein Byte b zurueckgegeben getLeitung hat den Typ bool """ s = '' # Anfang Startbit time.sleep(1.5*bitzeit) # mitten im ersten Datenbit # Datenbits abtasten for i in range(8): if getLeitung(): s = s + '1' else: s = s + '0' time.sleep(bitzeit) # mitten im Stoppbit return int(s,2) def warteFlanke01(getLeitung): alt = getLeitung() neu = getLeitung() while not (not alt and neu): time.sleep(0.0005) alt = neu neu = getLeitung() import threading class Model(object): def __init__(self): self.scan = scan() self.s = serial.Serial(self.scan[0]) self.s.setRTS(False) self.nachricht = bytes([]) self.enabled = False def run(self): print('Thread gestartet') while self.enabled: warteFlanke01(self.s.getCTS) b = receiveByte(self.bitzeit,self.s.getCTS) print(b) self.nachricht = bytes(list(self.nachricht)+[b]) def stop(self): self.enabled = False def start(self,bitzeit): self.enabled = True self.bitzeit = bitzeit self.empfThread = threading.Thread(target = self.run) self.empfThread.start() def __del__(self): # schließt sicher die Schnittstelle self.s.close() # view import tkinter import time class View(tkinter.Tk): def __init__(self,cbSetPort,cbStart,cbStop,cbGet,cbClear,cbHalt): tkinter.Tk.__init__(self) # Callbacks self.cbSetPort = cbSetPort # setzt Port self.cbStart = cbStart # startet Empfang self.cbStop = cbStop # stoppt Empfang self.cbGetNachricht = cbGet # gibt Nachricht als bytes zurueck self.cbClear = cbClear # loescht Nachricht self.protocol("WM_DELETE_WINDOW",cbHalt) # cbHalt wird aufgerufen, wenn das 'X' gedrueckt wird # Fenster self.title("Empfänger 0") self.geometry('325x200+600+200') # Label self.lP = tkinter.Label(master=self, text='Port:') self.lP.place(x=20, y=20) self.lB = tkinter.Label(master=self, text='Bitzeit:') self.lB.place(x=210, y=20) self.lS = tkinter.Label(master=self, text='s') self.lS.place(x=295, y=20) # Optionmenu self.vS = tkinter.StringVar(master=self) self.scan = scan() self.vS.set(self.scan[0]) self.oS = tkinter.OptionMenu(self,self.vS,*self.scan, command=self.cbOption) self.oS.place(x=55,y=14, width=100) # Entry self.eA = tkinter.Entry(master=self) self.eA.insert(0, '0.05') self.eA.place(x=255, y=20, width=40) self.eA.bind('',self.cbEntry) # Text self.tA = tkinter.Text(self,width=40,height=5) # width und height in Zeichen self.tA.delete('1.0',tkinter.END) self.tA.place(x=20,y=60) # Buttons self.bClear = tkinter.Button(master=self, text="clear", command=self.cbClear) self.bClear.place(x=20,y=150) # Empfang starten self.cbEntry(None) # Polling starten self.after(0,self.poll) def poll(self): s = str(self.cbGetNachricht(),'utf8') self.tA.delete('1.0',tkinter.END) self.tA.insert(tkinter.END,s) self.after(200,self.poll) def cbOption(self, wert): # print(wert) # DEBUG self.cbSetPort(wert) def cbEntry(self,event): self.focus_force() # print('Return im Entry-Widget, String:',self.eA.get()) # DEBUG self.cbStop() bitzeit = float(self.eA.get()) # todo: Fehler abfangen self.cbStart(bitzeit) def cbClear(self): self.cbClear() # controller class Controller(object): def __init__(self): self.model = Model() self.view = View(self.setPort,self.model.start,self.model.stop,self.Get,self.Clear,self.Halt) self.view.mainloop() def setPort(self,port): self.model.s.setPort(port) def Get(self): return self.model.nachricht def Clear(self): self.model.nachricht = bytes([]) def Halt(self): # Aufraeumarbeiten self.model.s.close() # Schnittstelle schliessen self.view.quit() # mainloop beenden self.view.destroy() # Fenster beseitigen # Hauptprogramm c = Controller()