diff --git a/dstatInterface/dstat_comm.py b/dstatInterface/dstat_comm.py index 72168795a0aff3ec7e281871960bb9db2386ba68..2bddee4bb7c65fc095e91f8eac4014975e12a63c 100644 --- a/dstatInterface/dstat_comm.py +++ b/dstatInterface/dstat_comm.py @@ -1,6 +1,7 @@ #!/usr/bin/env python import serial, io, time, struct +from types import * from serial.tools import list_ports import numpy as np @@ -41,41 +42,41 @@ class SerialDevices: self.ports, _, _ = zip(*list_ports.comports()) class Experiment: - def __init__(self): + def __init__(self): #will always be overriden, but self.parameters and self.viewparameters should be defined pass - def init(self, adc_buffer, adc_rate, adc_pga, gain, update, updatelimit, plot_instance): + def init(self): self.__gaintable = [1e2, 3e2, 3e3, 3e4, 3e5, 3e6, 3e7, 5e8] - self.gain = self.__gaintable[int(gain)] - self.updatelimit = updatelimit - self.update = update + self.gain = self.__gaintable[int(self.parameters['gain'])] + self.updatelimit = self.view_parameters['updatelimit'] + self.update = self.view_parameters['update'] self.commands = ["A","G"] - self.commands[0] += (adc_buffer) + self.commands[0] += (self.parameters['adc_buffer']) self.commands[0] += " " - self.commands[0] += (adc_rate) + self.commands[0] += (self.parameters['adc_rate']) self.commands[0] += " " - self.commands[0] += (adc_pga) + self.commands[0] += (self.parameters['adc_pga']) self.commands[0] += " " - self.commands[1] += (gain) + self.commands[1] += (self.parameters['gain']) self.commands[1] += " " - plot_instance.clearall() - plot_instance.changetype(self) + self.plot.clearall() + self.plot.changetype(self) - def run(self, strPort, plot_instance, databuffer_instance): + def run(self, strPort): self.ser = delayedSerial(strPort, 1024000, timeout=3) self.ser.write("ck") self.ser.flushInput() self.updatecounter = 0 - databuffer_instance.set_text("") - databuffer_instance.place_cursor(databuffer_instance.get_start_iter()) + self.databuffer.set_text("") + self.databuffer.place_cursor(self.databuffer.get_start_iter()) for i in self.commands: - databuffer_instance.insert_at_cursor(i) + self.databuffer.insert_at_cursor(i) self.ser.flush() self.ser.write("!") while True: @@ -90,16 +91,16 @@ class Experiment: self.ser.write(i) print i - self.data_handler(plot_instance, databuffer_instance) #Will be overridden by experiment classes to deal with more complicated data + self.data_handler() #Will be overridden by experiment classes to deal with more complicated data self.data_postprocessing() - plot_instance.updateline(self, 0) - plot_instance.redraw() + self.plot.updateline(self, 0) + self.plot.redraw() self.ser.close() - def data_handler(self, plot_instance, databuffer_instance): + def data_handler(self): while True: for line in self.ser: if line.startswith('B'): @@ -109,11 +110,11 @@ class Experiment: self.data[0].append((voltage-32768)*3000./65536) self.data[1].append(current*(1.5/self.gain/8388607)) - plot_instance.updateline(self, 0) + self.plot.updateline(self, 0) if self.update: if self.updatecounter == self.updatelimit: - plot_instance.redraw() + self.plot.redraw() self.updatecounter = 0 else: @@ -133,7 +134,11 @@ class Experiment: # i.pop(0) class chronoamp(Experiment): - def __init__(self, adc_buffer, adc_rate, adc_pga, gain, potential, time, update, updatelimit, plot_instance): + def __init__(self, parameters, view_parameters, plot_instance, databuffer_instance): + self.parameters = parameters + self.view_parameters = view_parameters + self.plot = plot_instance + self.databuffer = databuffer_instance self.datatype = "linearData" self.xlabel = "Time (s)" self.ylabel = "Current (A)" @@ -142,22 +147,22 @@ class chronoamp(Experiment): self.xmin = 0 self.xmax = 0 - for i in time: + for i in self.parameters['time']: self.xmax += int(i) - self.init(adc_buffer, adc_rate, adc_pga, gain, update, updatelimit, plot_instance) #need to call after xmin and xmax are set + self.init() #need to call after xmin and xmax are set self.commands += "R" - self.commands[2] += str(len(potential)) + self.commands[2] += str(len(self.parameters['potential'])) self.commands[2] += " " - for i in potential: + for i in self.parameters['potential']: self.commands[2] += str(int(i*(65536./3000)+32768)) self.commands[2] += " " - for i in time: + for i in self.parameters['time']: self.commands[2] += str(i) self.commands[2] += " " - def data_handler(self, plot_instance, databuffer_instance): #overrides inherited method to not convert x axis + def data_handler(self): #overrides inherited method to not convert x axis while True: for line in self.ser: if line.startswith('B'): @@ -167,11 +172,11 @@ class chronoamp(Experiment): self.data[0].append(seconds+milliseconds/1000.) self.data[1].append(current*(1.5/self.gain/8388607)) - plot_instance.updateline(self, 0) + self.plot.updateline(self, 0) if self.update: if self.updatecounter == self.updatelimit: - plot_instance.redraw() + self.plot.redraw() self.updatecounter = 0 else: @@ -184,55 +189,60 @@ class chronoamp(Experiment): break class lsv_exp(Experiment): - def __init__(self, adc_buffer, adc_rate, adc_pga, gain, start, stop, slope, update, updatelimit, plot_instance): + def __init__(self, parameters, view_parameters, plot_instance, databuffer_instance): + self.parameters = parameters + self.view_parameters = view_parameters + self.plot = plot_instance + self.databuffer = databuffer_instance self.datatype = "linearData" self.xlabel = "Voltage (mV)" self.ylabel = "Current (A)" self.data = [[],[]] self.datalength = 2 - self.xmin = start - self.xmax = stop + self.xmin = self.parameters['start'] + self.xmax = self.parameters['stop'] - self.init(adc_buffer, adc_rate, adc_pga, gain, update, updatelimit, plot_instance) #need to call after xmin and xmax are set + self.init() #need to call after xmin and xmax are set self.commands += "L" - self.commands[2] += str(start) + self.commands[2] += str(self.parameters['start']) self.commands[2] += " " - self.commands[2] += str(stop) + self.commands[2] += str(self.parameters['stop']) self.commands[2] += " " - self.commands[2] += str(slope) + self.commands[2] += str(self.parameters['slope']) self.commands[2] += " " class cv_exp(Experiment): - def __init__(self, adc_buffer, adc_rate, adc_pga, gain, v1, v2, start, scans, slope, update, updatelimit, plot_instance): + def __init__(self, parameters, view_parameters, plot_instance, databuffer_instance): + self.parameters = parameters + self.view_parameters = view_parameters + self.plot = plot_instance + self.databuffer = databuffer_instance self.datatype = "CVData" self.xlabel = "Voltage (DAC units)" self.ylabel = "Current (A)" self.data = [[],[]] #Will have to alter data_handler to add new lists as needed - self.datalength = 2 * scans #x and y for each scan - self.xmin = 0 - self.xmax = 0 - - self.xmin = v1 - self.xmax = v2 + self.datalength = 2 * self.parameters['scans'] #x and y for each scan + self.xmin = self.parameters['v1'] + self.xmax = self.parameters['v2'] - self.init(adc_buffer, adc_rate, adc_pga, gain, update, updatelimit, plot_instance) + self.init() self.commands += "C" - self.commands[2] += str(v1) + self.commands[2] += str(self.parameters['v1']) self.commands[2] += " " - self.commands[2] += str(v2) + self.commands[2] += str(self.parameters['v2']) self.commands[2] += " " - self.commands[2] += str(start) + self.commands[2] += str(self.parameters['start']) self.commands[2] += " " - self.commands[2] += str(scans) + self.commands[2] += str(self.parameters['scans']) self.commands[2] += " " - self.commands[2] += str(slope) + self.commands[2] += str(self.parameters['slope']) self.commands[2] += " " - def data_handler(self, plot_instance, databuffer_instance): + def data_handler(self): scan = 0 while True: @@ -244,11 +254,11 @@ class cv_exp(Experiment): self.data[2*scan].append((voltage-32768)*3000./65536) self.data[2*scan+1].append(current*(1.5/self.gain/8388607)) - plot_instance.updateline(self, scan) + self.plot.updateline(self, scan) if self.update: if self.updatecounter == self.updatelimit: - plot_instance.redraw() + self.plot.redraw() self.updatecounter = 0 else: @@ -259,8 +269,8 @@ class cv_exp(Experiment): break elif line.lstrip().startswith('S'): - plot_instance.redraw() - plot_instance.addline() + self.plot.redraw() + self.plot.addline() self.data.append([]) self.data.append([]) scan += 1 @@ -268,43 +278,42 @@ class cv_exp(Experiment): elif line.lstrip().startswith('D'): self.data.pop() self.data.pop() #instrument signals with S after each cycle, so last one will be blank, D singals end of experiment - plot_instance.clearline(scan) - plot_instance.redraw() + self.plot.clearline(scan) + self.plot.redraw() break - def data_postprocessing(self): - self.data - class swv_exp(Experiment): - def __init__(self, adc_buffer, adc_rate, adc_pga, gain, start, stop, step, pulse, freq, update, updatelimit, plot_instance): + def __init__(self, parameters, view_parameters, plot_instance, databuffer_instance): + self.parameters = parameters + self.view_parameters = view_parameters + self.plot = plot_instance + self.databuffer = databuffer_instance self.datatype = "SWVData" self.xlabel = "Voltage (DAC units)" self.ylabel = "Current (A)" self.data = [[],[],[],[]] #one extra for difference self.datalength = 4 - self.xmin = 0 - self.xmax = 0 - self.xmin = start - self.xmax = stop + self.xmin = self.parameters['start'] + self.xmax = self.parameters['stop'] - self.init(adc_buffer, adc_rate, adc_pga, gain, update, updatelimit, plot_instance) + self.init() self.commands += "S" - self.commands[2] += str(start) + self.commands[2] += str(self.parameters['start']) self.commands[2] += " " - self.commands[2] += str(stop) + self.commands[2] += str(self.parameters['stop']) self.commands[2] += " " - self.commands[2] += str(step) + self.commands[2] += str(self.parameters['step']) self.commands[2] += " " - self.commands[2] += str(pulse) + self.commands[2] += str(self.parameters['pulse']) self.commands[2] += " " - self.commands[2] += str(freq) + self.commands[2] += str(self.parameters['freq']) self.commands[2] += " " - def data_handler(self, plot_instance, databuffer_instance): + def data_handler(self): while True: for line in self.ser: if line.startswith('B'): @@ -316,11 +325,11 @@ class swv_exp(Experiment): self.data[2].append(forward*(1.5/self.gain/8388607)) self.data[3].append(reverse*(1.5/self.gain/8388607)) - plot_instance.updateline(self, 0) #displays only difference current, but forward and reverse stored + self.plot.updateline(self, 0) #displays only difference current, but forward and reverse stored if self.update: if self.updatecounter == self.updatelimit: - plot_instance.redraw() + self.plot.redraw() self.updatecounter = 0 else: diff --git a/dstatInterface/interface_test.py b/dstatInterface/interface_test.py index c1a2a7f867f2813b6c0edef5e8c4c77a3168e159..f8de9637cb13b6dc2d0eaa2c8951a9533102cfb2 100644 --- a/dstatInterface/interface_test.py +++ b/dstatInterface/interface_test.py @@ -171,100 +171,103 @@ class main: def on_pot_start_clicked(self, data=None): selection = self.expcombobox.get_active() + parameters = {} + view_parameters = {} + if self.adc_pot.buffer_toggle.get_active(): #True if box checked - adc_buffer = "2" + parameters['adc_buffer'] = "2" else: - adc_buffer = "0" - self.srate_model = self.adc_pot.srate_combobox.get_model() - self.pga_model = self.adc_pot.pga_combobox.get_model() - self.gain_model = self.adc_pot.gain_combobox.get_model() + parameters['adc_buffer'] = "0" + + srate_model = self.adc_pot.srate_combobox.get_model() + pga_model = self.adc_pot.pga_combobox.get_model() + gain_model = self.adc_pot.gain_combobox.get_model() + + parameters['adc_rate'] = srate_model.get_value(self.adc_pot.srate_combobox.get_active_iter(), 2) #third column + parameters['adc_pga'] = pga_model.get_value(self.adc_pot.pga_combobox.get_active_iter(), 2) + parameters['gain'] = gain_model.get_value(self.adc_pot.gain_combobox.get_active_iter(), 2) - adc_rate = self.srate_model.get_value(self.adc_pot.srate_combobox.get_active_iter(), 2) #third column - adc_pga = self.pga_model.get_value(self.adc_pot.pga_combobox.get_active_iter(), 2) - gain = self.gain_model.get_value(self.adc_pot.gain_combobox.get_active_iter(), 2) - update = self.plotint_checkbox.get_active() - updatelimit = int(self.updatelimit_adj.get_value()) + view_parameters['update'] = self.plotint_checkbox.get_active() + view_parameters['updatelimit'] = int(self.updatelimit_adj.get_value()) self.spinner.start() + self.statusbar.remove_all(self.error_context_id) try: if selection == 0: #CA - potential = [int(r[0]) for r in self.chronoamp.model] - time = [int(r[1]) for r in self.chronoamp.model] + parameters['potential'] = [int(r[0]) for r in self.chronoamp.model] + parameters['time'] = [int(r[1]) for r in self.chronoamp.model] - if not potential: - raise InputError(potential,"Step table is empty") + if not parameters['potential']: + raise InputError(parameters['potential'],"Step table is empty") - self.current_exp = comm.chronoamp(adc_buffer, adc_rate, adc_pga, gain, potential, time, update, updatelimit, self.plot) - self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0), self.plot, self.rawbuffer) + self.current_exp = comm.chronoamp(parameters, view_parameters, self.plot, self.rawbuffer) + self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0)) elif selection == 1: #LSV - self.statusbar.remove_all(self.error_context_id) - start = int(self.lsv.start_entry.get_text()) - stop = int(self.lsv.stop_entry.get_text()) - slope = int(self.lsv.slope_entry.get_text()) + parameters['start'] = int(self.lsv.start_entry.get_text()) + parameters['stop'] = int(self.lsv.stop_entry.get_text()) + parameters['slope'] = int(self.lsv.slope_entry.get_text()) #check parameters are within hardware limits - if (start > 1499 or start < -1500): - raise InputError(start,"Start parameter exceeds hardware limits.") - if (stop > 1499 or stop < -1500): - raise InputError(stop,"Stop parameter exceeds hardware limits.") - if (slope > 2000 or slope < 1): - raise InputError(slope,"Slope parameter exceeds hardware limits.") - if start == stop: - raise InputError(start,"Start cannot equal Stop.") + if (parameters['start'] > 1499 or parameters['start'] < -1500): + raise InputError(parameters['start'],"Start parameter exceeds hardware limits.") + if (parameters['stop'] > 1499 or parameters['stop'] < -1500): + raise InputError(parameters['stop'],"Stop parameter exceeds hardware limits.") + if (parameters['slope'] > 2000 or parameters['slope'] < 1): + raise InputError(parameters['slope'],"Slope parameter exceeds hardware limits.") + if parameters['start'] == parameters['stop']: + raise InputError(parameters['start'],"Start cannot equal Stop.") - self.current_exp = comm.lsv_exp(adc_buffer, adc_rate, adc_pga, gain, start, stop, slope, update, updatelimit, self.plot) - self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0), self.plot, self.rawbuffer) + self.current_exp = comm.lsv_exp(parameters, view_parameters, self.plot, self.rawbuffer) + self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0)) elif selection == 2: #CV - self.statusbar.remove_all(self.error_context_id) #clear statusbar - start = int(self.cv.start_entry.get_text()) - slope = int(self.cv.slope_entry.get_text()) - v1 = int(self.cv.v1_entry.get_text()) - v2 = int(self.cv.v2_entry.get_text()) - scans = int(self.cv.scans_entry.get_text()) + parameters['start'] = int(self.cv.start_entry.get_text()) + parameters['slope'] = int(self.cv.slope_entry.get_text()) + parameters['v1'] = int(self.cv.v1_entry.get_text()) + parameters['v2'] = int(self.cv.v2_entry.get_text()) + parameters['scans'] = int(self.cv.scans_entry.get_text()) #check parameters are within hardware limits - if (start > 1499 or start < -1500): - raise InputError(start,"Start parameter exceeds hardware limits.") - if (slope > 2000 or slope < 1): - raise InputError(slope,"Slope parameter exceeds hardware limits.") - if (v1 > 1499 or v1 < -1500): - raise InputError(v1,"Vertex 1 parameter exceeds hardware limits.") - if (v2 > 1499 or v2 < -1500): - raise InputError(v2,"Vertex 2 parameter exceeds hardware limits.") - if (scans < 1 or scans > 255): - raise InputError(scans, "Scans parameter outside limits.") - if v1 == v2: - raise InputError(start,"Vertex 1 cannot equal Vertex 2.") + if (parameters['start'] > 1499 or parameters['start'] < -1500): + raise InputError(parameters['start'],"Start parameter exceeds hardware limits.") + if (parameters['slope'] > 2000 or parameters['slope'] < 1): + raise InputError(parameters['slope'],"Slope parameter exceeds hardware limits.") + if (parameters['v1'] > 1499 or parameters['v1'] < -1500): + raise InputError(parameters['v1'],"Vertex 1 parameter exceeds hardware limits.") + if (parameters['v2'] > 1499 or parameters['v2'] < -1500): + raise InputError(parameters['v2'],"Vertex 2 parameter exceeds hardware limits.") + if (parameters['scans'] < 1 or parameters['scans'] > 255): + raise InputError(parameters['scans'], "Scans parameter outside limits.") + if parameters['v1'] == parameters['v2']: + raise InputError(parameters['v1'],"Vertex 1 cannot equal Vertex 2.") - self.current_exp = comm.cv_exp(adc_buffer, adc_rate, adc_pga, gain, v1, v2, start, scans, slope, update, updatelimit, self.plot) - self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0), self.plot, self.rawbuffer) + self.current_exp = comm.cv_exp(parameters, view_parameters, self.plot, self.rawbuffer) + self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0)) elif selection == 3: #SWV - self.statusbar.remove_all(self.error_context_id) #clear statusbar - start = int(self.swv.start_entry.get_text()) - stop = int(self.swv.stop_entry.get_text()) - step = int(self.swv.step_entry.get_text()) - pulse = int(self.swv.pulse_entry.get_text()) - freq = int(self.swv.freq_entry.get_text()) + parameters['start'] = int(self.swv.start_entry.get_text()) + parameters['stop'] = int(self.swv.stop_entry.get_text()) + parameters['step'] = int(self.swv.step_entry.get_text()) + parameters['pulse'] = int(self.swv.pulse_entry.get_text()) + parameters['freq'] = int(self.swv.freq_entry.get_text()) #check parameters are within hardware limits (doesn't check if pulse will go out of bounds, but instrument checks this (I think)) - if (start > 1499 or start < -1500): - raise InputError(start,"Start parameter exceeds hardware limits.") - if (step > 200 or step < 1): - raise InputError(step,"Step height parameter exceeds hardware limits.") - if (stop > 1499 or stop < -1500): - raise InputError(stop,"Stop parameter exceeds hardware limits.") - if (pulse > 150 or pulse < 1): - raise InputError(pulse,"Pulse height parameter exceeds hardware limits.") - if (freq < 1 or freq > 1000): - raise InputError(freq, "Frequency parameter outside limits.") - if start == stop: - raise InputError(start,"Start cannot equal Stop.") + if (parameters['start'] > 1499 or parameters['start'] < -1500): + raise InputError(parameters['start'],"Start parameter exceeds hardware limits.") + if (parameters['step'] > 200 or parameters['step'] < 1): + raise InputError(parameters['step'],"Step height parameter exceeds hardware limits.") + if (parameters['stop'] > 1499 or parameters['stop'] < -1500): + raise InputError(parameters['stop'],"Stop parameter exceeds hardware limits.") + if (parameters['pulse'] > 150 or parameters['pulse'] < 1): + raise InputError(parameters['pulse'],"Pulse height parameter exceeds hardware limits.") + if (parameters['freq'] < 1 or parameters['freq'] > 1000): + raise InputError(parameters['freq'], "Frequency parameter outside limits.") + if parameters['start'] == parameters['stop']: + raise InputError(parameters['start'],"Start cannot equal Stop.") - self.current_exp = comm.swv_exp(adc_buffer, adc_rate, adc_pga, gain, start, stop, step, pulse, freq, update, updatelimit, self.plot) - self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0), self.plot, self.rawbuffer) + self.current_exp = comm.swv_exp(parameters, view_parameters, self.plot, self.rawbuffer) + self.current_exp.run(self.serial_liststore.get_value(self.serial_combobox.get_active_iter(), 0)) else: self.statusbar.push(self.error_context_id, "Experiment not yet implemented.") @@ -280,6 +283,10 @@ class main: except SerialException: self.spinner.stop() self.statusbar.push(self.error_context_id, "Could not establish serial connection.") + + except AssertionError as e: + self.spinner.stop() + self.statusbar.push(self.error_context_id, str(e)) self.databuffer.set_text("") self.databuffer.place_cursor(self.databuffer.get_start_iter())