Hallo, bin Lehrer an einer Berufsschule (Maschinenbau/Prozesstechnik). Mein Interesse für Steuerungstechnik
nütze ich für Schülerprojekte. Derzeit arbeite ich an der Vorbereitung für eine Drahtbiegemaschine. Der Stop-Button funktioniert leider nicht während der Datenübertragung (zum Arduino) - friert ein. Das Programm hab ich mehr zusammengestellt als selbst programmiert und bin an dieser Stelle hoffnungslos überfordert. Freu mich über jede Hilfe.
tkinter-threads
bitte um Entschuldigung irgendwie funkt das Ganze noch nicht ...
from tkinter import *
import serial # kommunikation
import serial.tools.list_ports
import time
import tk_tools
##------------variablen------------##
arduino = ""
# Sendeprotokoll #.#M3#.# bzw #G1 X100 F100#
# Werterückgabe #1# oder #0#
##------------funktionen- Stepper------------##
def comNano(befehl, timeout): # befehl zum arduino schicken und antwort zurückgeben
global arduino
if arduino == "": return ""
bytebefehl = bytes(befehl, 'utf-8')
arduino.write(bytebefehl)
vomarduino = ""
delaymax = time.time() + timeout
while delaymax > time.time():
if arduino.inWaiting() > 0: # es ist was da
inputchar = str(arduino.read(1), 'utf-8')
if inputchar >= " ": # kein steuerzeichen
vomarduino += inputchar
else:
if vomarduino > "": # es hat geklappt
return vomarduino
return ""
def suchNano(kennung, timeout): # den mit kennung definierten arduino über xxx sekunden pro port suchen
global arduino
ports = serial.tools.list_ports.comports(include_links=False)
for port in ports :
arduinoport = port.device
try:
arduino = serial.Serial(arduinoport, baudrate = 9600, bytesize = serial.EIGHTBITS, parity = serial.PARITY_NONE, stopbits = serial.STOPBITS_ONE, timeout = 1, xonxoff = 0, rtscts = 0)
arduino.setDTR(False) # arduino reset erzwingen ...
arduino.flushInput()
arduino.setDTR(True)
delaymax = time.time() + timeout
while delaymax > time.time():
if arduino.inWaiting() > 0:
vomarduino = str(arduino.readline())
if vomarduino.find(kennung) > 0: # gefunden
v = vomarduino.find(" v") # v suchen
if v == 0: v = vomarduino.find(" V") # V suchen
if v > 0: # versionsnummer ermitteln
try:
n = int(vomarduino[v + 2: v + 5])
except:
n = 0
else:
n = 0
return ("v%03d" % n) # versionsnummer zurückgeben
except:
dummy = 1
arduino = ""
return ""
def findString(text, text2, suchbeginn): # teilstring in string suchen (0: nicht gefunden, sonst stelle)
if suchbeginn < 1: # ganzen string durchsuchen
suchbeginn = 1
return (text.find(text2, suchbeginn - 1) + 1)
##------------startroutine-----------##
print ()
print (" Code_v010 (Slave " + suchNano("Code", 3) + ")")
##------------Funktionen-GUI-----------##
def nix():
return
def schließen():
tkFenster.destroy()
return
def show_pressed(but):
but.config(activebackground='red')
def show_released(but):
but.config(activebackground='yellow')
#-------------------------------------------------------------------------------------------
import webbrowser
new = 1
url = "http://www.vatican.va/content/vatican/de.html"
def openweb():
webbrowser.open(url,new=new)
#-----------------------------------------------------------------------------
def wechsleFarbeMB():
lab3["fg"]="#FF0000"
lab3["font"]="Arial 16 italic"
lab3["height"] = 2
lab3["width"] = 20
lab3["anchor"] ="center"
#return
def wechsleFarbeMB2():
lab3["fg"]="#000000"
lab3["font"]="Arial 10"
lab3["height"] = 2
lab3["width"] = 20
lab3["anchor"] ="center"
#return
#--------------Test--------------------------------------------------------------------------
def SendText():
values = textfeld1.get('1.0', 'end')
#print("Values", values)
s = values # das feld in einem string
while findString(s, "\n", 0) > 0:
stelle = findString(s, "\n", 0)
if (stelle - 1) > 0:
befehl = "#.#" + s[: stelle - 1] + "#.#"
s = s[stelle: ]
if comNano(befehl, 100)[:3] == "#1#":
print("1")
else:
print("0")
else:
s = s[stelle: ]
print("Stelle = 0")
#------------ Erzeugung des Fensters------------#
tkFenster = Tk()
tkFenster.title('NC-Drahtbiegeautomat')
tkFenster.geometry('670x650')
# Canvas für den Hintergrund
imageHintergrund = PhotoImage(file="Ausgedinge_02.png")
canvasHintergrund = Canvas(master=tkFenster)
canvasHintergrund.place(x=0, y=0, width=670, height=600)
canvasHintergrund.create_image(0, 0, image=imageHintergrund, anchor='nw')
# Button zum Senden
buttonSenden = Button(master=canvasHintergrund, text="Senden", font= ("Arial", 13, "bold"), bg="yellow",fg="red", command=SendText)
show_released(buttonSenden)
buttonSenden.bind("<ButtonPress-1>", lambda ev: [show_pressed(buttonSenden), led.to_green(True)])
buttonSenden.bind('<ButtonRelease-1>', lambda ev:[show_released(buttonSenden), led.to_green(on=False)])
buttonSenden.place(x=90, y=500, width=200, height=50)
# LED
led = tk_tools.Led(tkFenster, size=50)
led.grid(row=0, column=0)
#-----------------------#
"""
#label = Label(tkFenster)
#label.place (x=530, y=360, width=140, height=30)
"""
#--------------manueller Befehl an Arduino--------------------------------------------------------------------------
def SendZ1():
text = "#.#M3#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M5#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendZ2():
text = "#.#M8#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M9#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendZ3():
text = "#.#M1#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M2#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendCut():
text = "#.#M6#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M7#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendStop(): #Reset
text = "#.#RESET#.#" #Reset
print(text)
if comNano(text, 3)[:3] == "#1#": #Reset
print("1")
else:
print("0")
return
time.sleep(5)
from tkinter import *
import serial # kommunikation
import serial.tools.list_ports
import time
import tk_tools
##------------variablen------------##
arduino = ""
# Sendeprotokoll #.#M3#.# bzw #G1 X100 F100#
# Werterückgabe #1# oder #0#
##------------funktionen- Stepper------------##
def comNano(befehl, timeout): # befehl zum arduino schicken und antwort zurückgeben
global arduino
if arduino == "": return ""
bytebefehl = bytes(befehl, 'utf-8')
arduino.write(bytebefehl)
vomarduino = ""
delaymax = time.time() + timeout
while delaymax > time.time():
if arduino.inWaiting() > 0: # es ist was da

inputchar = str(arduino.read(1), 'utf-8')
if inputchar >= " ": # kein steuerzeichen
vomarduino += inputchar
else:
if vomarduino > "": # es hat geklappt
return vomarduino
return ""
def suchNano(kennung, timeout): # den mit kennung definierten arduino über xxx sekunden pro port suchen
global arduino
ports = serial.tools.list_ports.comports(include_links=False)
for port in ports :
arduinoport = port.device
try:
arduino = serial.Serial(arduinoport, baudrate = 9600, bytesize = serial.EIGHTBITS, parity = serial.PARITY_NONE, stopbits = serial.STOPBITS_ONE, timeout = 1, xonxoff = 0, rtscts = 0)
arduino.setDTR(False) # arduino reset erzwingen ...
arduino.flushInput()
arduino.setDTR(True)
delaymax = time.time() + timeout
while delaymax > time.time():
if arduino.inWaiting() > 0:
vomarduino = str(arduino.readline())
if vomarduino.find(kennung) > 0: # gefunden

v = vomarduino.find(" v") # v suchen
if v == 0: v = vomarduino.find(" V") # V suchen
if v > 0: # versionsnummer ermitteln
try:
n = int(vomarduino[v + 2: v + 5])
except:
n = 0
else:
n = 0
return ("v%03d" % n) # versionsnummer zurückgeben
except:
dummy = 1
arduino = ""
return ""
def findString(text, text2, suchbeginn): # teilstring in string suchen (0: nicht gefunden, sonst stelle)
if suchbeginn < 1: # ganzen string durchsuchen
suchbeginn = 1
return (text.find(text2, suchbeginn - 1) + 1)
##------------startroutine-----------##
print ()
print (" Code_v010 (Slave " + suchNano("Code", 3) + ")")
##------------Funktionen-GUI-----------##
def nix():
return
def schließen():
tkFenster.destroy()
return
def show_pressed(but):
but.config(activebackground='red')
def show_released(but):
but.config(activebackground='yellow')
#-------------------------------------------------------------------------------------------
import webbrowser
new = 1
url = "http://www.vatican.va/content/vatican/de.html"
def openweb():
webbrowser.open(url,new=new)
#-----------------------------------------------------------------------------
def wechsleFarbeMB():
lab3["fg"]="#FF0000"
lab3["font"]="Arial 16 italic"
lab3["height"] = 2
lab3["width"] = 20
lab3["anchor"] ="center"
#return
def wechsleFarbeMB2():
lab3["fg"]="#000000"
lab3["font"]="Arial 10"
lab3["height"] = 2
lab3["width"] = 20
lab3["anchor"] ="center"
#return
#--------------Test--------------------------------------------------------------------------
def SendText():
values = textfeld1.get('1.0', 'end')
#print("Values", values)
s = values # das feld in einem string
while findString(s, "\n", 0) > 0:
stelle = findString(s, "\n", 0)
if (stelle - 1) > 0:
befehl = "#.#" + s[: stelle - 1] + "#.#"
s = s[stelle: ]
if comNano(befehl, 100)[:3] == "#1#":
print("1")
else:
print("0")
else:
s = s[stelle: ]
print("Stelle = 0")
#------------ Erzeugung des Fensters------------#
tkFenster = Tk()
tkFenster.title('NC-Drahtbiegeautomat')
tkFenster.geometry('670x650')
# Canvas für den Hintergrund
imageHintergrund = PhotoImage(file="Ausgedinge_02.png")
canvasHintergrund = Canvas(master=tkFenster)
canvasHintergrund.place(x=0, y=0, width=670, height=600)
canvasHintergrund.create_image(0, 0, image=imageHintergrund, anchor='nw')
# Button zum Senden
buttonSenden = Button(master=canvasHintergrund, text="Senden", font= ("Arial", 13, "bold"), bg="yellow",fg="red", command=SendText)
show_released(buttonSenden)
buttonSenden.bind("<ButtonPress-1>", lambda ev: [show_pressed(buttonSenden), led.to_green(True)])
buttonSenden.bind('<ButtonRelease-1>', lambda ev:[show_released(buttonSenden), led.to_green(on=False)])
buttonSenden.place(x=90, y=500, width=200, height=50)
# LED
led = tk_tools.Led(tkFenster, size=50)
led.grid(row=0, column=0)
#-----------------------#
"""
#label = Label(tkFenster)
#label.place (x=530, y=360, width=140, height=30)
"""
#--------------manueller Befehl an Arduino--------------------------------------------------------------------------
def SendZ1():
text = "#.#M3#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M5#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendZ2():
text = "#.#M8#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M9#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendZ3():
text = "#.#M1#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M2#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendCut():
text = "#.#M6#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
time.sleep(1)
text = "#.#M7#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
def SendStop(): #Reset
text = "#.#RESET#.#" #Reset
print(text)
if comNano(text, 3)[:3] == "#1#": #Reset
print("1")
else:
print("0")
return
time.sleep(5)
2.Teil
def selected():
print(i.get())
if (i.get() != 1):
print("schnell")
textSt1 = "#.#G1 X1 F30#.#"
else:
print("langsam")
textSt2 = "#.#G1 X10 F50#.#"
textSt1 = "#.#G1 X1 F30#.#"
textSt2 = "#.#G1 X10 F50#.#"
def SendStep():
if(i.get()== 1):
text = textSt1 #"#.#G1 X1 F30#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
else:
text = textSt2 #"#.#G1 X1 F30#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
#----------------------------------------------------------------
def set_txt(): #Datei lesen
with open("G-Code_01.txt") as fobj:
for line in fobj:
print(line.rstrip())
textfeld1.insert(END,line)
#---------------------------------------------------------------------------------------
#Menue definieren
leiste = Menu(tkFenster)
tkFenster.config(menu = leiste)
#Untermenue Datei
dateiMenu = Menu(leiste)
leiste.add_cascade(label = "Datei", menu = dateiMenu)
dateiMenu.add_command(label="Neu", command= nix)
dateiMenu.add_command(label="Code einlesen", command= set_txt)
dateiMenu.add_command(label="Speichern", command= nix)
dateiMenu.add_command(label="Schließen", command= schließen)
#Untermenue Hilfe
hilfeMenu = Menu(leiste)
leiste.add_cascade(label = "Hilfe", menu = hilfeMenu)
hilfeMenu.add_command(label="Hilfe", command= openweb)
# Button für Zylinder anlegen und positionieren
but1 = Button(tkFenster, text='M3/M5', font= ("Arial",12), bg= "light yellow", fg="blue", relief=RAISED ,command=SendZ1)
show_released(but1)
but1.bind("<ButtonPress-1>", lambda ev: [show_pressed(but1), wechsleFarbeMB()])
but1.bind('<ButtonRelease-1>', lambda ev:[show_released(but1), wechsleFarbeMB2()])
but1.place(x=550, y=180, width=100, height=30)
but2 = Button(tkFenster, text='M8/M9', font= ("Arial", 12), bg= "light yellow", fg="blue", relief=RAISED,command=SendZ2)
show_released(but2)
but2.bind("<ButtonPress-1>", lambda ev: [show_pressed(but2), wechsleFarbeMB()])
but2.bind('<ButtonRelease-1>', lambda ev:[show_released(but2), wechsleFarbeMB2()])
but2.place(x=550, y=300, width=100, height=30)
but3 = Button(tkFenster, text='Stepper', font= ("Arial",12), bg= "light yellow", fg="blue",relief=RAISED, command=SendStep)
show_released(but3)
but3.bind("<ButtonPress-1>", lambda ev: [show_pressed(but3), wechsleFarbeMB()])
but3.bind('<ButtonRelease-1>', lambda ev:[show_released(but3), wechsleFarbeMB2()])
but3.place(x=550, y=360, width=100, height=30)
but4 = Button(tkFenster, text='M6/M7', font= ("Arial",12), bg= "light yellow", fg="blue", relief=RAISED ,command=SendCut)
show_released(but4)
but4.bind("<ButtonPress-1>", lambda ev: [show_pressed(but4), wechsleFarbeMB()])
but4.bind('<ButtonRelease-1>', lambda ev:[show_released(but4), wechsleFarbeMB2()])
but4.place(x=550, y=240, width=100, height=30)
but5 = Button(tkFenster, text='M1/M2', font= ("Arial",12), bg= "light yellow", fg="blue", relief=RAISED ,command=SendZ3)
show_released(but5)
but5.bind("<ButtonPress-1>", lambda ev: [show_pressed(but4), wechsleFarbeMB()])
but5.bind('<ButtonRelease-1>', lambda ev:[show_released(but4), wechsleFarbeMB2()])
but5.place(x=550, y=120, width=100, height=30)
Stop = Button(tkFenster, bg="red", text ="\n".join("Stopp"), font =("Arial", 14, "bold"), fg = "black",relief=RAISED, command = SendStop)
Stop.place(x=488, y=47, width=48, height=225)
#----------------------------------------------------------------------
# Textfelder
textfeld1 = Text(master=tkFenster, width=39, height=25,wrap='word')
textfeld1.place(x=30, y=57)
scrollbar1 = Scrollbar(master=tkFenster)
scrollbar1.place(x=342, y=57, width=15, height=431)
textfeld1.config(yscrollcommand=scrollbar1.set)
scrollbar1.config(command=textfeld1.yview)
#------------Radiobutton-----------#
i = IntVar() #Basically Links Any Radiobutton With The Variable=i.
i.set(1)
r1 = Radiobutton(tkFenster, text="inc 01", value=1, variable=i, command =selected)
r2 = Radiobutton(tkFenster, text="inc 10", value=10, variable=i, command=selected)
r1.place( x= 590, y=400)
r2.place( x= 590, y=420)
#------------Label------------#
lab3 = Label(tkFenster, text="manueller Betrieb") #, font=("Arial",12), fg="blue")
lab3.place(x=490, y=15, width=180, height=30)
lab4 = Label(tkFenster, text="NC Betrieb") #, font=("Arial",12), fg="blue")
lab4.place(x=150, y=25, width=80, height=30)
#------------Bild anlegen und positionieren------------#
image1 = PhotoImage(file="Zylinder2_01.png")
panel1 = Label(tkFenster, image = image1)
panel1.place(x=537, y=45, width=120, height=70)
# Aktivierung des Fensters
tkFenster.mainloop()
def selected():
print(i.get())
if (i.get() != 1):
print("schnell")
textSt1 = "#.#G1 X1 F30#.#"
else:
print("langsam")
textSt2 = "#.#G1 X10 F50#.#"
textSt1 = "#.#G1 X1 F30#.#"
textSt2 = "#.#G1 X10 F50#.#"
def SendStep():
if(i.get()== 1):
text = textSt1 #"#.#G1 X1 F30#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
else:
text = textSt2 #"#.#G1 X1 F30#.#"
print(text)
if comNano(text, 3)[:3] == "#1#":
print("1")
else:
print("0")
return
#----------------------------------------------------------------
def set_txt(): #Datei lesen
with open("G-Code_01.txt") as fobj:
for line in fobj:
print(line.rstrip())
textfeld1.insert(END,line)
#---------------------------------------------------------------------------------------
#Menue definieren
leiste = Menu(tkFenster)
tkFenster.config(menu = leiste)
#Untermenue Datei
dateiMenu = Menu(leiste)
leiste.add_cascade(label = "Datei", menu = dateiMenu)
dateiMenu.add_command(label="Neu", command= nix)
dateiMenu.add_command(label="Code einlesen", command= set_txt)
dateiMenu.add_command(label="Speichern", command= nix)
dateiMenu.add_command(label="Schließen", command= schließen)
#Untermenue Hilfe
hilfeMenu = Menu(leiste)
leiste.add_cascade(label = "Hilfe", menu = hilfeMenu)
hilfeMenu.add_command(label="Hilfe", command= openweb)
# Button für Zylinder anlegen und positionieren
but1 = Button(tkFenster, text='M3/M5', font= ("Arial",12), bg= "light yellow", fg="blue", relief=RAISED ,command=SendZ1)
show_released(but1)
but1.bind("<ButtonPress-1>", lambda ev: [show_pressed(but1), wechsleFarbeMB()])
but1.bind('<ButtonRelease-1>', lambda ev:[show_released(but1), wechsleFarbeMB2()])
but1.place(x=550, y=180, width=100, height=30)
but2 = Button(tkFenster, text='M8/M9', font= ("Arial", 12), bg= "light yellow", fg="blue", relief=RAISED,command=SendZ2)
show_released(but2)
but2.bind("<ButtonPress-1>", lambda ev: [show_pressed(but2), wechsleFarbeMB()])
but2.bind('<ButtonRelease-1>', lambda ev:[show_released(but2), wechsleFarbeMB2()])
but2.place(x=550, y=300, width=100, height=30)
but3 = Button(tkFenster, text='Stepper', font= ("Arial",12), bg= "light yellow", fg="blue",relief=RAISED, command=SendStep)
show_released(but3)
but3.bind("<ButtonPress-1>", lambda ev: [show_pressed(but3), wechsleFarbeMB()])
but3.bind('<ButtonRelease-1>', lambda ev:[show_released(but3), wechsleFarbeMB2()])
but3.place(x=550, y=360, width=100, height=30)
but4 = Button(tkFenster, text='M6/M7', font= ("Arial",12), bg= "light yellow", fg="blue", relief=RAISED ,command=SendCut)
show_released(but4)
but4.bind("<ButtonPress-1>", lambda ev: [show_pressed(but4), wechsleFarbeMB()])
but4.bind('<ButtonRelease-1>', lambda ev:[show_released(but4), wechsleFarbeMB2()])
but4.place(x=550, y=240, width=100, height=30)
but5 = Button(tkFenster, text='M1/M2', font= ("Arial",12), bg= "light yellow", fg="blue", relief=RAISED ,command=SendZ3)
show_released(but5)
but5.bind("<ButtonPress-1>", lambda ev: [show_pressed(but4), wechsleFarbeMB()])
but5.bind('<ButtonRelease-1>', lambda ev:[show_released(but4), wechsleFarbeMB2()])
but5.place(x=550, y=120, width=100, height=30)
Stop = Button(tkFenster, bg="red", text ="\n".join("Stopp"), font =("Arial", 14, "bold"), fg = "black",relief=RAISED, command = SendStop)
Stop.place(x=488, y=47, width=48, height=225)
#----------------------------------------------------------------------
# Textfelder
textfeld1 = Text(master=tkFenster, width=39, height=25,wrap='word')
textfeld1.place(x=30, y=57)
scrollbar1 = Scrollbar(master=tkFenster)
scrollbar1.place(x=342, y=57, width=15, height=431)
textfeld1.config(yscrollcommand=scrollbar1.set)
scrollbar1.config(command=textfeld1.yview)
#------------Radiobutton-----------#
i = IntVar() #Basically Links Any Radiobutton With The Variable=i.
i.set(1)
r1 = Radiobutton(tkFenster, text="inc 01", value=1, variable=i, command =selected)
r2 = Radiobutton(tkFenster, text="inc 10", value=10, variable=i, command=selected)
r1.place( x= 590, y=400)
r2.place( x= 590, y=420)
#------------Label------------#
lab3 = Label(tkFenster, text="manueller Betrieb") #, font=("Arial",12), fg="blue")
lab3.place(x=490, y=15, width=180, height=30)
lab4 = Label(tkFenster, text="NC Betrieb") #, font=("Arial",12), fg="blue")
lab4.place(x=150, y=25, width=80, height=30)
#------------Bild anlegen und positionieren------------#
image1 = PhotoImage(file="Zylinder2_01.png")
panel1 = Label(tkFenster, image = image1)
panel1.place(x=537, y=45, width=120, height=70)
# Aktivierung des Fensters
tkFenster.mainloop()
Ich glaube kaum, dass irgendwer den Code durchschauen will.
Hier wird an `arduino`, einer globalen Variable, mal ein String und mal ein Serial-Objekt gebunden. Das alleine läßt jeden Programmierer die Haare zu Berge stehen.
Damit der Code lesbar wird, muß als erstes die Einrückungen einheitlich auf 4 Leerzeichen pro Ebene angepasst werden. Variablennamen und Funktionen werden komplett klein geschrieben. Globale Variablen darf es nicht geben. Dazu darf es auf oberster Ebene keinen ausführbaren Code geben, sondern nur Funktionsdefinitionen, Konstanten und Importe.
Benutze keine *-Importe.
Die meisten Send-Funktionen sind nur kopierter Code, das sollte als idealerweise alles in einer Funktion zusammengefasst werden.
Hier wird an `arduino`, einer globalen Variable, mal ein String und mal ein Serial-Objekt gebunden. Das alleine läßt jeden Programmierer die Haare zu Berge stehen.
Damit der Code lesbar wird, muß als erstes die Einrückungen einheitlich auf 4 Leerzeichen pro Ebene angepasst werden. Variablennamen und Funktionen werden komplett klein geschrieben. Globale Variablen darf es nicht geben. Dazu darf es auf oberster Ebene keinen ausführbaren Code geben, sondern nur Funktionsdefinitionen, Konstanten und Importe.
Benutze keine *-Importe.
Die meisten Send-Funktionen sind nur kopierter Code, das sollte als idealerweise alles in einer Funktion zusammengefasst werden.
Ich versuch mal aufzuräumen. comNano sollte wohl send_command heißen. Das mischen von Deutsch und Englisch macht das Lesen kompliziert. Der Funktion fehlt als Argument `arduino`.
Dass es kein eindeutliges Zeichen für das Ende eines Rückgabewerts gibt, macht das Lesen schwierig. Denn dann könnte man die ganze Schleife durch ein read_until ersetzen.
Beim Suchen nach dem richtigen Port hast Du einen naktes except, was wirklich jeden Fehler abfängt auch viele Programmierfehler, so dass das Fehlerfinden unmöglich wird. Mit der Stringrepräsentation eines Bytes-Objekts sollte man nicht weiterarbeiten. `find` wird auch falsch angewendet.
Dann die vielen Send-Funktionen lassen sich einfacher schreiben:
`SendText` ist dann eher irgendein BASIC-Dialekt als dass es Python-Code wäre. Warum wird values in `s` umbenannt? Statt while-Schleife mit diesem ominösen findString würde man einfach str.split verwenden.
Einige Bugs habe ich wahrscheinlich aus Versehen gleich mit behoben.
Bei der GUI will ich gar nicht so genau hinschauen. Warum muß eine LED leuchten, solange ein Knopf gedrückt ist? place solle man nicht verwenden. Verwende grid.
Dass es kein eindeutliges Zeichen für das Ende eines Rückgabewerts gibt, macht das Lesen schwierig. Denn dann könnte man die ganze Schleife durch ein read_until ersetzen.
Code: Alles auswählen
def send_command(arduino, command, timeout):
arduino.write(command.encode('utf-8'))
delaymax = time.time() + timeout
result = []
while True:
arduino.timeout = delaymax - time.time()
character = arduino.read(1)
if not character:
# timeout
return ""
if character < b" ":
# TODO: define one EOF-Character
break
result.append(character)
return b"".join(result).decode('utf-8')
Code: Alles auswählen
def search_nano(signature, timeout):
ports = serial.tools.list_ports.comports(include_links=False)
for port in ports:
try:
arduino = serial.Serial(port.device, timeout=1)
except IOError:
pass
else:
# arduino reset erzwingen ...
arduino.dtr = False
arduino.flushInput()
arduino.dtr = True
arduino.timeout = timeout
line = arduino.readline().decode('utf-8')
if signature in line:
# versionsnummer ermitteln
version = line.lower().partition(" v")[2]
version = int(version) if version.isdigit() else 0
return "v%03d" % version
raise RuntimeError("arduino not found")
Code: Alles auswählen
def send_text(arduino, text):
print(text)
ok = send_command(arduino, text, 3).startswith("#1#")
print("1" if ok else "0")
def send_z1(arduino):
send_text(arduino, "#.#M3#.#")
time.sleep(1)
send_text(arduino, "#.#M5#.#")
def send_z2(arduino):
send_text(arduino, "#.#M8#.#")
time.sleep(1)
send_text(arduino, "#.#M9#.#")
def send_z3(arduino):
send_text(arduino, "#.#M1#.#")
time.sleep(1)
send_text(arduino, "#.#M2#.#")
def send_cut(arduino):
send_text(arduino, "#.#M6#.#")
time.sleep(1)
send_text(arduino, "#.#M7#.#")
def send_stop(arduino): #Reset
send_text(arduino, "#.#RESET#.#")
time.sleep(5)
def send_step(arduino, speed=1):
text = "#.#G1 X1 F30#.#" if speed == 1 else "#.#G1 X1 F30#.#"
send_text(arduino, text)
Code: Alles auswählen
def send_text(arduino, values):
for command in values.split():
send_text(arduino, "#.#%s#.#" % command)
Bei der GUI will ich gar nicht so genau hinschauen. Warum muß eine LED leuchten, solange ein Knopf gedrückt ist? place solle man nicht verwenden. Verwende grid.
erstmal einen herzlichen Dank für die vielen Antworten ich arbeite an der Umsetzung 
das grüne LED soll den Schülern nur zeigen, das der Code (G-Code auf CNC) gesendet wird.
zu "s = values" hier hab ich versucht den Text zeilenweise einzulesen und zu senden - aber wie geschrieben,
bei diesem Sendevorgang wird alles andere blockiert.
Noch einmal Danke und Gesundheit - ich melde mich wieder ...

das grüne LED soll den Schülern nur zeigen, das der Code (G-Code auf CNC) gesendet wird.
zu "s = values" hier hab ich versucht den Text zeilenweise einzulesen und zu senden - aber wie geschrieben,
bei diesem Sendevorgang wird alles andere blockiert.
Noch einmal Danke und Gesundheit - ich melde mich wieder ...
Hallo Frau/Herr __deets__ und Sirius3
wie macht man folgendes:
- Code Tags benützen
bei
def search_nano(signature, timeout):
ports = serial.tools.list_ports.comports(include_links=False)
for port in ports:
for p in ports:
print(p.device)
print(len(ports), 'ports found') ## Ports auflisten zu Testzwecken
try:
arduino = serial.Serial(port.device, timeout=1)
except IOError:
pass
kommt:
COM8
COM4
COM1
COM3
4 ports found
G-Code Master v103 (Slave v000)
wenn ich den Code G1 X100 F300 eingebe und sende, kommt:
Exception in Tkinter callback
Traceback (most recent call last):
File "C:\Python\lib\tkinter\__init__.py", line 1883, in __call__
return self.func(*args)
TypeError: send_text() missing 2 required positional arguments: 'arduino' and 'values'
erwartet wird :
G-Code Master v103 (Slave v000)
1
Was muss ich ändern?
liebe Grüße
wie macht man folgendes:
- Code Tags benützen
bei
def search_nano(signature, timeout):
ports = serial.tools.list_ports.comports(include_links=False)
for port in ports:
for p in ports:
print(p.device)
print(len(ports), 'ports found') ## Ports auflisten zu Testzwecken
try:
arduino = serial.Serial(port.device, timeout=1)
except IOError:
pass
kommt:
COM8
COM4
COM1
COM3
4 ports found
G-Code Master v103 (Slave v000)
wenn ich den Code G1 X100 F300 eingebe und sende, kommt:
Exception in Tkinter callback
Traceback (most recent call last):
File "C:\Python\lib\tkinter\__init__.py", line 1883, in __call__
return self.func(*args)
TypeError: send_text() missing 2 required positional arguments: 'arduino' and 'values'
erwartet wird :
G-Code Master v103 (Slave v000)
1
Was muss ich ändern?
liebe Grüße
Code-Tags verbergen sich im vollständigen Editor hinter dem Knopf </>.
Die for-Schleifen in `search_nano` machen so keinen Sinn. Warum sind die verschachtelt?
Natürlich mußt Du Deine GUI komplett auf die neuen Funktionen anpassen. Da Du aber eh die GUI quasi neu schreiben solltest, mit den Anmerkungen, die ich schon gegeben habe, fängst Du am besten gleich mit einer Klasse an.
Die Steuerung des Arduino mußt Du eh innerhalb eines Threads machen. Dort erzeugst Du das arduino-Objekt und wartest in einer Schleife auf Commandos per queue. Wie soetwas prinzipiell aussieht, gibt es schon genug (hier zum Beispiel).
Die for-Schleifen in `search_nano` machen so keinen Sinn. Warum sind die verschachtelt?
Natürlich mußt Du Deine GUI komplett auf die neuen Funktionen anpassen. Da Du aber eh die GUI quasi neu schreiben solltest, mit den Anmerkungen, die ich schon gegeben habe, fängst Du am besten gleich mit einer Klasse an.
Die Steuerung des Arduino mußt Du eh innerhalb eines Threads machen. Dort erzeugst Du das arduino-Objekt und wartest in einer Schleife auf Commandos per queue. Wie soetwas prinzipiell aussieht, gibt es schon genug (hier zum Beispiel).
Ich gebe mein Bestes (erstes Python-Programm), verstehe aber vieles noch nicht ...
Die for-Schleife soll den Arduino nach der Kennung und Übertragungserfolg abfragen (hab ich von einer Grbl-Erklärung)
Das mit den Objekten verstehe ich noch nicht bin aber dran ...
Die for-Schleife soll den Arduino nach der Kennung und Übertragungserfolg abfragen (hab ich von einer Grbl-Erklärung)
Das mit den Objekten verstehe ich noch nicht bin aber dran ...
Code: Alles auswählen
from tkinter import Button
import time
import tk_tools
##------------variablen------------##
arduino = ""
# Sendeprotokoll #.#M3#.# bzw #G1 X100 F100#
# Werterückgabe #1# oder #0#
##------------funktionen- Stepper------------##
def send_command(arduino, command, timeout):
arduino.write(command.encode('utf-8'))
delaymax = time.time() + timeout
result = []
while True:
arduino.timeout = delaymax - time.time()
character = arduino.read(1)
if not character:
# timeout
return ""
if character < b" ":
# TODO: define one EOF-Character
break
result.append(character)
return b"".join(result).decode('utf-8')
"""
def comNano(befehl, timeout): # befehl zum arduino schicken und antwort zurückgeben
global arduino
if arduino == "": return ""
bytebefehl = bytes(befehl, 'utf-8')
arduino.write(bytebefehl)
vomarduino = ""
delaymax = time.time() + timeout
while delaymax > time.time():
if arduino.inWaiting() > 0: # es ist was da ;)
inputchar = str(arduino.read(1), 'utf-8')
if inputchar >= " ": # kein steuerzeichen
vomarduino += inputchar
else:
if vomarduino > "": # es hat geklappt
return vomarduino
return ""
"""
def search_nano(signature, timeout):
ports = serial.tools.list_ports.comports(include_links=False)
for port in ports:
try:
arduino = serial.Serial(port.device, timeout=1)
except IOError:
pass
else:
# arduino reset erzwingen ...
arduino.dtr = False
arduino.flushInput()
arduino.dtr = True
arduino.timeout = timeout
line = arduino.readline().decode('utf-8')
if signature in line:
# versionsnummer ermitteln
version = line.lower().partition(" v")[2]
version = int(version) if version.isdigit() else 0
return "v%03d" % version
raise RuntimeError("arduino not found")
"""
def search_nano(signature, timeout): # den mit signature definierten arduino über xxx sekunden pro port suchen
global arduino
ports = serial.tools.list_ports.comports(include_links=False)
for port in ports :
arduinoport = port.device
try:
arduino = serial.Serial(arduinoport, baudrate = 9600, bytesize = serial.EIGHTBITS, parity = serial.PARITY_NONE, stopbits = serial.STOPBITS_ONE, timeout = 1, xonxoff = 0, rtscts = 0)
arduino.setDTR(False) # arduino reset erzwingen ...
arduino.flushInput()
arduino.setDTR(True)
delaymax = time.time() + timeout
while delaymax > time.time():
if arduino.inWaiting() > 0:
vomarduino = str(arduino.readline())
if vomarduino.find(signature) > 0: # gefunden ;)
v = vomarduino.find(" v") # v suchen
if v == 0: v = vomarduino.find(" V") # V suchen
if v > 0: # versionsnummer ermitteln
try:
n = int(vomarduino[v + 2: v + 5])
except:
n = 0
else:
n = 0
return ("v%03d" % n) # versionsnummer zurückgeben
except:
dummy = 1
arduino = ""
return ""
"""
def findstring(text, text2, suchbeginn): # teilstring in string suchen (0: nicht gefunden, sonst stelle)
if suchbeginn < 1: # ganzen string durchsuchen
suchbeginn = 1
return (text.find(text2, suchbeginn - 1) + 1)
##------------startroutine-----------##
print ()
print (" G-Code Master v102 (Slave " + search_nano("gcode", 3) + ")")
"""
def send_text(arduino, text):
print(text)
ok = send_command(arduino, text, 3).startswith("#1#")
print("1" if ok else "0")
"""
def send_text(arduino, text):
for command in values.split():
send_text(arduino, "#.#%s#.#" % command)
def show_released(but):
but.config(activebackground='yellow')
#------------ Erzeugung des Fensters------------#
tkFenster = Tk()
tkFenster.title('NC-Drahtbiegeautomat')
tkFenster.geometry('670x830')
# Button zum Senden
buttonSenden = Button(master=tkFenster, text="Senden", font= ("Arial", 13, "bold"), bg="yellow",fg="red", command=send_text)
buttonSenden.place(x=90, y=620, width=200, height=50)
show_released(buttonSenden)
#--------------manueller Befehl an Arduino--------------------------------------------------------------------------
def send_z1(arduino):
send_text(arduino, "#.#M3#.#")
time.sleep(1)
send_text(arduino, "#.#M5#.#")
def send_z2(arduino):
send_text(arduino, "#.#M8#.#")
time.sleep(1)
send_text(arduino, "#.#M9#.#")
def send_z3(arduino):
send_text(arduino, "#.#M1#.#")
time.sleep(1)
send_text(arduino, "#.#M2#.#")
def send_cut(arduino):
send_text(arduino, "#.#M6#.#")
time.sleep(1)
send_text(arduino, "#.#M7#.#")
def send_stop(arduino): #Reset
send_text(arduino, "#.#RESET#.#")
time.sleep(5)
def send_step(arduino, speed=1):
text = "#.#G1 X1 F30#.#" if speed == 1 else "#.#G1 X10 F50#.#"
send_text(arduino, text)
def selected():
print(i.get())
if (i.get() != 1):
print("schnell")
textSt1 = "#.#G1 X1 F30#.#"
else:
print("langsam")
textSt1 = "#.#G1 X10 F30#.#"
#--- Button anlegen---
but1 = Button(tkFenster, text='Zylinder1', font= ("Arial",12), bg= "light yellow", fg="blue", relief=tk.RAISED ,command=send_z1)
show_released(but1)
but1.bind("<ButtonPress-1>", lambda ev: [show_pressed(but1), wechsleFarbeMB()])
but1.bind('<ButtonRelease-1>', lambda ev:[show_released(but1), wechsleFarbeMB2()])
but1.place(x=550, y=120, width=100, height=30)
but2 = Button(tkFenster, text='Zylinder2', font= ("Arial", 12), bg= "light yellow", fg="blue", relief=k.RAISED,command=send_z2)
show_released(but2)
but2.bind("<ButtonPress-1>", lambda ev: [show_pressed(but2), wechsleFarbeMB()])
but2.bind('<ButtonRelease-1>', lambda ev:[show_released(but2), wechsleFarbeMB2()])
but2.place(x=550, y=180, width=100, height=30)
but3 = Button(tkFenster, text='Stepper', font= ("Arial",12), bg= "light yellow", fg="blue",relief=tk.RAISED, command=send_step)
show_released(but3)
but3.bind("<ButtonPress-1>", lambda ev: [show_pressed(but3), wechsleFarbeMB()])
but3.bind('<ButtonRelease-1>', lambda ev:[show_released(but3), wechsleFarbeMB2()])
but3.place(x=550, y=300, width=100, height=30)
but4 = Button(tkFenster, text='CUT', font= ("Arial",12), bg= "light yellow", fg="blue", relief=tk.RAISED ,command=send_cut)
show_released(but4)
but4.bind("<ButtonPress-1>", lambda ev: [show_pressed(but4), wechsleFarbeMB()])
but4.bind('<ButtonRelease-1>', lambda ev:[show_released(but4), wechsleFarbeMB2()])
but4.place(x=550, y=240, width=100, height=30)
Stop = Button(tkFenster, bg="red", text ="\n".join("Stopp"), font =("Arial", 14, "bold"), fg = "black",relief=tk.RAISED, command = send_stop)
Stop.place(x=488, y=47, width=48, height=225)
#---Textfeld----------------------------------------------------------------------
textfeld1 = Text(master=tkFenster, width=39, height=35, wrap='word')
textfeld1.place(x=30, y=65)
scrollbar1 = Scrollbar(master=tkFenster)
scrollbar1.place(x=342, y=55, width=15, height=368)
textfeld1.config(yscrollcommand=scrollbar1.set)
scrollbar1.config(command=textfeld1.yview)
#---Radiobutton---------------------------------------------------------------------
i = IntVar() #Basically Links Any Radiobutton With The Variable=i.
i.set(1)
r1 = Radiobutton(tkFenster, text="inc 01", value=1, variable=i, command =selected)
r2 = Radiobutton(tkFenster, text="inc 10", value=10, variable=i, command=selected)
r1.place( x= 590, y=340)
r2.place( x= 590, y=360)
#---Aktivierung des Fensters
tkFenster.mainloop()
Code: Alles auswählen
import tkinter as tk
import serial # kommunikation
import serial.tools.list_ports
from tkinter import PhotoImage
from tkinter import Canvas
from tkinter import Button
import time
import tk_tools