You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

399 lines
12 KiB

#!/usr/bin/env python3
import sys
import getopt
import glob
import serial
import struct
from tkinter import *
import matplotlib.figure as figure
from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg
from datetime import datetime
def serial_ports():
""" Lists serial port names
:raises EnvironmentError:
On unsupported or unknown platforms
:returns:
A list of the serial ports available on the system
"""
if sys.platform.startswith('win'):
ports = ['COM%s' % (i + 1) for i in range(256)]
elif sys.platform.startswith('linux') or sys.platform.startswith('cygwin'):
# this excludes your current terminal "/dev/tty"
ports = glob.glob('/dev/tty[A-Za-z]*')
elif sys.platform.startswith('darwin'):
ports = glob.glob('/dev/tty.*')
else:
raise EnvironmentError('Unsupported platform')
result = []
for port in ports:
try:
s = serial.Serial(port)
s.close()
result.append(port)
except (OSError, serial.SerialException):
pass
return result
#print(serial_ports())
availableSerialPorts = serial_ports()
print('choose a port:')
counter = 0
for port in availableSerialPorts:
print(' [' + str(counter) + '] ' + port)
counter += 1
choosenPort = input('(type a number (0)) ')
if choosenPort == '':
choosenPortNumber = 0
else:
choosenPortNumber = int(choosenPort)
counter = 0
#serialPort = '/dev/pts/19'
serialPort = '/dev/ttyACM0'
serialPort = availableSerialPorts[choosenPortNumber]
try:
ser = serial.Serial(serialPort, 19200, serial.EIGHTBITS, serial.PARITY_NONE, serial.STOPBITS_ONE, timeout=0, writeTimeout=0)
except:
serialPort = '/dev/ttyACM1'
ser = serial.Serial(serialPort, 19200, serial.EIGHTBITS, serial.PARITY_NONE, serial.STOPBITS_ONE, timeout=0, writeTimeout=0)
#ser = serial.Serial()
#ser.port = "/dev/pts/19"
#ser.baudrate = 9600
#ser.bytesize = serial.EIGHTBITS
#ser.parity = serial.PARITY_NONE
#ser.stopbits = serial.STOPBITS_ONE
#ser.timeout = None #block read
#ser.timeout = 1 #non-block read
#ser.timeout = 2 #timeout block read
#ser.xonxoff = False #disable software flow control
#ser.rtscts = False #disable hardware (RTS/CTS) flow control
#ser.dsrdtr = False #disable hardware (DSR/DTR) flow control
#ser.writeTimeout = 2 #timeout for write
#try:
# ser.open()
#except Exception as e:
# print('error open serial port: ' + str(e))
# exit()
#ser.open()
#ser.write('hello world!')
#values = bytearray([4, 9, 62, 144, 56, 30, 147, 3, 210, 89, 111, 78, 184, 151, 17, 129])
#ser.write(values)
#while True:
# print(ser.readline())
#from serial import *
#from Tkinter import *
#serialPort = "/dev/ttyACM0"
#baudRate = 9600
#ser = Serial(serialPort , baudRate, timeout=0, writeTimeout=0) #ensure non-blocking
logEnable = 0;
#~ temps = [20, 40, 60, 80, 100, 120, 140, 160, 180, 200, 220]
temps = []
tick = 0
#~ tickArray = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
tickArray = []
tActArray = []
tSetArray = []
errArray = []
errSumArray = []
outOrigArray = []
outArray = []
def functionLog():
global logEnable
if logEnable == 1:
sendSerial([0xa3])
app.after(1000, functionLog)
def sendSerial(input):
print('send ' + str(len(input)) + ' byte(s): ' + str([hex(x) for x in input]))
data = bytearray([0xff, 0xf1])
data.append(len(input))
data.extend(bytearray(input))
ser.write(data)
def processData(input):
global logEnable
global w
global temps
global tick
global tickArray
global tActArray
global tSetArray
global errArray
global errSumArray
global outOrigArray
global outArray
print(str([hex(x) for x in input]))
if input[0] == 0xa0:
if input[1] == 0x00:
log.insert(END, '> temp sensor 0 status: ' + str.join(':', ('%02x' % x for x in input[2:])) + '\n')
elif input[1] == 0x01:
log.insert(END, '> temp sensor 1 status: ' + str.join(':', ('%02x' % x for x in input[2:])) + '\n')
elif input[0] == 0x10:
if input[1] == 0x00:
log.insert(END, '> adc: wrong channel\n')
elif input[1] == 0x01:
log.insert(END, '> adc: start cartridge resistance measurement\n')
elif input[1] == 0x02:
log.insert(END, '> adc: start cartridge current measurement\n')
elif input[1] == 0x03:
log.insert(END, '> adc: start cartridge temperature measurement\n')
elif input[1] == 0x04:
log.insert(END, '> adc: start input voltage measurement\n')
elif input[1] == 0xff:
log.insert(END, '> adc: pending measurement\n')
elif input[0] == 0x11:
if input[1] == 0x01:
log.insert(END, '> raw_adc_cartridge_resistance: ' + str(((input[2] * 256) + input[3])) + '\n')
elif input[1] == 0x02:
log.insert(END, '> raw_adc_cartridge_current: ' + str(((input[2] * 256) + input[3])) + '\n')
elif input[1] == 0x03:
log.insert(END, '> raw_adc_cartridge_temperature: ' + str(((input[2] * 256) + input[3])) + '\n')
elif input[1] == 0x04:
log.insert(END, '> raw_adc_v_in: ' + str(((input[2] * 256) + input[3])) + '\n')
elif input[1] == 100:
# log.insert(END, '> raw_adc_cartridge_temperature_cycle: ' + str(((input[2] * 256) + input[3])) + '\n')
log.insert(END, '> raw_adc_cartridge_temperature_cycle: ' + str(round(((input[2] * 256) + input[3]) * 0.4833149757 + 35.1689715661)) + ' degC\n')
#~ tick = tick + 1
#~ tickArray.append(tick)
#~ temps.append(((input[2] * 256) + input[3]) * 0.4833149757 + 35.1689715661)
#~ tickArray = tickArray[-200:]
#~ temps = temps[-200:]
#~ ax1.clear()
#~ ax1.set_ylim(0, 400)
#~ ax1.plot(tickArray, temps, linewidth=2, color='black')
#~ fig.canvas.draw()
elif input[0] == 0x20:
if input[1] == 0x00:
log.insert(END, '> cartridge resistance measure disabled\n')
elif input[1] == 0x01:
log.insert(END, '> cartridge resistance measure enabled\n')
elif input[0] == 0x21:
if input[1] == 0x00:
log.insert(END, '> power-mosfet disabled\n')
elif input[1] == 0x01:
log.insert(END, '> power-mosfet enabled\n')
elif input[0] == 0x8d:
cartridge_temperature_adc_raw = ((input[1] * 256) + input[2])
tAct = struct.unpack('>f', input[3:7])
tSet = struct.unpack('>f', input[7:11])
err = struct.unpack('>f', input[11:15])
errSum = struct.unpack('>f', input[15:19])
outOrig = struct.unpack('>f', input[19:23])
out = input[23] * 256 + input[24]
if out > 32767:
out -= 65536
log.insert(END, 'tAct: ' + str(tAct) + 'tSet: ' + str(tSet) + 'err: ' + str(err) + 'errSum: ' + str(errSum) + 'outOrig: ' + str(outOrig) + 'out: ' + str(out) + '\n')
#~ tActArray.append(tAct)
#~ tActArray = tActArray[-200:]
#~ ax1.clear()
#~ ax1.plot(tickArray, tActArray, linewidth=2, color='black')
#~ fig.canvas.draw()
else:
log.insert(END, '> ' + str.join(':', ('%02x' % x for x in input)) + '\n')
log.see("end")
def btnClearAction():
log.delete(1.0,END)
log.insert(END, str(datetime.now()) + '\n')
def btnGetRawAdcCartridgeResistanceAction():
sendSerial([0x10, 0x01])
def btnGetRawAdcCartridgeCurrentAction():
sendSerial([0x10, 0x02])
def btnGetRawAdcCartridgeTemperatureAction():
sendSerial([0x10, 0x03])
def btnGetRawAdcInputVoltageAction():
sendSerial([0x10, 0x04])
def btnSetCartridgeResistanceMosfetOnAction():
sendSerial([0x20, 0x01])
def btnSetCartridgeResistanceMosfetOffAction():
sendSerial([0x20, 0x00])
def btnSetPowerMosfetOnAction():
sendSerial([0x91, 0x01, 0x18])
def btnSetPowerMosfetOffAction():
sendSerial([0x91, 0x00, 0x00])
def btnGetTempSensor0DegCAction():
sendSerial([0xa2, 0x00])
def btnGetTempSensor1DegCAction():
sendSerial([0xa2, 0x01])
def btnGetTempSensorsDegCAction():
sendSerial([0xa3])
def btnStartLogAction():
global logEnable
global w
w = open('reflow_oven_temperature_log', 'w')
logEnable = 1
w.write('time;seconds;status;temperature;tAct;tSet;err;errSum;outOrig;out\n')
sendSerial([0xa5])
#functionLog()
def btnStopLogAction():
global logEnable
global w
sendSerial([0xa4, 0x00])
logEnable = 0
w.close()
def btnDisablePwmAction():
sendSerial([0xb0, 0x00, 0x00])
def btnSetTemperature0Action():
sendSerial([0xb1, 0x00])
def btnSetTemperature80Action():
sendSerial([0xb1, 0x50])
def btnSetTemperature150Action():
sendSerial([0xb1, 0x96])
def btnSetTemperature180Action():
sendSerial([0xb1, 0xb4])
def btnSetTemperature245Action():
sendSerial([0xb1, 0xf5])
#make a TkInter Window
app = Tk()
app.wm_title("attiny817_solderstation_app")
# Create figure for plotting
fig = figure.Figure(figsize=(12, 4))
#~ fig.subplots_adjust(left=0.1, right=0.8)
ax1 = fig.add_subplot(1, 1, 1)
ax1.set_ylim(0, 400)
#~ ax1.set_xlim(0, 20)
# Create a Tk Canvas widget out of our figure
canvas = FigureCanvasTkAgg(fig, master=app)
canvas_plot = canvas.get_tk_widget()
# make a scrollbar
scrollbar = Scrollbar(app)
scrollbar.pack(side=RIGHT, fill=Y)
# make a text box to put the serial output
log = Text (app, width=250, height=20, takefocus=0)
log.pack()
# attach text box to scrollbar
log.config(yscrollcommand=scrollbar.set)
scrollbar.config(command=log.yview)
btnClear = Button(app, text='clear', command=btnClearAction)
btnGetRawAdcCartridgeResistance = Button(app, text='getRawAdcCartridgeResistance', command=btnGetRawAdcCartridgeResistanceAction)
btnGetRawAdcCartridgeCurrent = Button(app, text='getRawAdcCartridgeCurrent', command=btnGetRawAdcCartridgeCurrentAction)
btnGetRawAdcCartridgeTemperature = Button(app, text='getRawAdcCartridgeTemperature', command=btnGetRawAdcCartridgeTemperatureAction)
btnGetRawAdcInputVoltage = Button(app, text='getRawAdcInputVoltage', command=btnGetRawAdcInputVoltageAction)
btnSetCartridgeResistanceMosfetOn = Button(app, text='setCartridgeResistanceMosfetOn', command=btnSetCartridgeResistanceMosfetOnAction)
btnSetCartridgeResistanceMosfetOff = Button(app, text='setCartridgeResistanceMosfetOff', command=btnSetCartridgeResistanceMosfetOffAction)
btnSetPowerMosfetOn = Button(app, text='setPowerMosfetOn', command=btnSetPowerMosfetOnAction)
btnSetPowerMosfetOff = Button(app, text='setPowerMosfetOff', command=btnSetPowerMosfetOffAction)
btnGetTempSensor0DegC = Button(app, text='getTempSensor0DegC', command=btnGetTempSensor0DegCAction)
btnGetTempSensor1DegC = Button(app, text='getTempSensor1DegC', command=btnGetTempSensor1DegCAction)
btnGetTempSensorsDegC = Button(app, text='getTempSensorsDegC', command=btnGetTempSensorsDegCAction)
btnStartLog = Button(app, text='startLog', command=btnStartLogAction)
btnStopLog = Button(app, text='stopLog', command=btnStopLogAction)
btnDisablePwm = Button(app, text='STOP', command=btnDisablePwmAction)
btnSetTemperature0 = Button(app, text='setTemperature0', command=btnSetTemperature0Action)
btnSetTemperature80 = Button(app, text='setTemperature80', command=btnSetTemperature80Action)
btnSetTemperature150 = Button(app, text='setTemperature150', command=btnSetTemperature150Action)
btnSetTemperature180 = Button(app, text='setTemperature180', command=btnSetTemperature180Action)
btnSetTemperature245 = Button(app, text='setTemperature245', command=btnSetTemperature245Action)
btnClear.pack()
canvas_plot.pack()
btnGetRawAdcCartridgeResistance.pack()
btnGetRawAdcCartridgeCurrent.pack()
btnGetRawAdcCartridgeTemperature.pack()
btnGetRawAdcInputVoltage.pack()
btnSetCartridgeResistanceMosfetOn.pack()
btnSetCartridgeResistanceMosfetOff.pack()
btnSetPowerMosfetOn.pack()
btnSetPowerMosfetOff.pack()
#make our own buffer
#useful for parsing commands
#Serial.readline seems unreliable at times too
rxInputBuffer = bytearray()
rxStatemachine = 0
def readSerial():
while True:
c = ser.read() # attempt to read a character from Serial
#was anything read?
if len(c) == 0:
break
else:
#print('DATA')
#log.insert(END, ':' + c.hex())
global rxInputBuffer
global rxStatemachine
rxInputBuffer.append(c[0])
if rxStatemachine == 0:
if rxInputBuffer[0] == 0xff:
rxStatemachine = 1
rxInputBuffer = rxInputBuffer[1:]
elif rxStatemachine == 1:
if rxInputBuffer[0] == 0xf1:
rxStatemachine = 2
else:
rxStatemachine = 0
rxInputBuffer = rxInputBuffer[1:]
elif rxStatemachine == 2:
if len(rxInputBuffer) >= rxInputBuffer[0] + 1:
processData(rxInputBuffer[1:rxInputBuffer[0] + 1])
rxInputBuffer = bytearray()
rxStatemachine = 0
else:
if len(rxInputBuffer) > 256:
print('rxInputBuffer reset!')
rxInputBuffer = bytearray()
rxStatemachine = 0
app.after(1, readSerial) # check serial again soon
# after initializing serial, an arduino may need a bit of time to reset
app.after(100, readSerial)
app.mainloop()