#!/usr/bin/env python3 # -*- coding: utf-8 -*- """ Created on Thu Apr 4 11:10:20 2019 @author: martindrech """ import numpy as np from PyQt5 import QtCore import threading import time from MCDAQcontrolsignals import anal_control_signal from resources.messages import show_warning from resources.scanFunctions import create_measurement_array, yield_array from resources.storage import Storage class CameraWorker(QtCore.QObject): imageReadySignal = QtCore.pyqtSignal(np.ndarray, int) measurementStartingSignal = QtCore.pyqtSignal() measurementEndingSignal = QtCore.pyqtSignal() def __init__(self, andor_camera): super().__init__() self.cam = andor_camera self.cam.Init() self.cam.SensorCooling.setValue(True) print("camera worker initialized") self.storage = Storage() self.ao_to_scan = None self.scan_array_gen = None self._lock = threading.Lock() def make_connections(self, frontend): # frontend connections live_acq_params = frontend.cameraParamFrame.paramTree.p frontend.cameraButton.clicked.connect(lambda: self.run(live_acq_params)) frontend.signalWithMeasurementParameters.connect(self.simple_scan_measurement_start) frontend.roiDataReadySignal.connect(self.save_data_from_scan_step) frontend.measurementFrame.saveMeasureButton.clicked.connect( self.storage.permanent_save_current_data) # internal connections self.cam.helper.imageAquiredSignal.connect(self.new_image_acquired) def __del__(self): print("adios camera worker") def run(self, params): if self.cam.CameraAcquiring.getValue(): self._stop_acquisition_loop() print("acquisition now stopping") else: self._configure_acq_parameters(params) self._start_acquisition_loop() self.acq_thread = threading.Thread( target=self.cam.live_acquisition_loop ) self.acq_thread.start() print("acquisiting now starting") def _start_acquisition_loop(self): self.cam.live_acquisition_configure() self.cam.AcquisitionStart() def _stop_acquisition_loop(self): self.acq_thread.do_run = False self.acq_thread.join() self.cam.AcquisitionStop() self.cam._flush() def _configure_acq_parameters(self, params): print('Acq parameters: ') for p in params.children()[0].children(): print(p.name(), p.value()) # setting info in parameter tree params.child('Basic acq parameters').child('Camera name').setValue( self.cam.CameraModel.getValue() ) params.child('Basic acq parameters').child('Sensor Temperature').setValue( self.cam.SensorTemperature.getValue() ) params.child('Basic acq parameters').child('Temperature Status').setValue( self.cam.TemperatureStatus.getString() ) params.child('Basic acq parameters').child('Readout Time').setValue( self.cam.ReadoutTime.getValue() ) # setting camera parameteres according to tree self.cam.ExposureTime.setValue( params.child('Basic acq parameters').child('Exposure Time').value() ) self.cam.FrameRate.setValue(self.cam.FrameRate.max()) params.child('Basic acq parameters').child('Frame Rate').setValue( self.cam.FrameRate.getValue() ) self.cam.AOIBinning.setString( params.child('Basic acq parameters').child('Pixel Binning').value() ) self.cam.PixelReadoutRate.setString( params.child('Basic acq parameters').child('Pixel Readout Rate').value() ) self.cam.SimplePreAmpGainControl.setString( params.child('Basic acq parameters').child('Dynamic Range').value() ) self.cam.SpuriousNoiseFilter.setValue( params.child('Basic acq parameters').child('Spurious Noise Filter').value()=='True' ) @QtCore.pyqtSlot(int) def new_image_acquired(self, acq_index): self.imageReadySignal.emit(self.cam.acq_queue.get(), acq_index) def simple_scan_measurement_start(self, measure_params): if self.cam.CameraAcquiring.getValue(): show_warning('Can not start measurement if camera is acquiring') return 0 self.measurementStartingSignal.emit() self.ao_to_scan = self.get_scan_signal(measure_params['signal_to_scan']) start = measure_params['start'] end = measure_params['end'] step_num = measure_params['steps'] self.scan_array_gen = yield_array(create_measurement_array(start, end, step_num)) self.ao_to_scan.go_softly_to_value(start) self.storage.set_directory(measure_params['directory']) self.storage.create_data_file('Time', measure_params['signal_to_scan'], 'Roi data') self.storage.append_metadata_to_current_file(measure_params['spinboxes_dict'], self.cam.GetMetaData(), measure_params) self.cam.TriggerMode.setString('Software') self._start_acquisition_loop() self.acq_thread = threading.Thread( target=self.cam.live_acquisition_loop ) self.acq_thread.start() with self._lock: self.simple_scan_measurement_step() def simple_scan_measurement_end(self): self._stop_acquisition_loop() self.cam.TriggerMode.setString('Internal') self.measurementEndingSignal.emit() print('exiting scan ending in worker') def simple_scan_measurement_step(self): try: value = next(self.scan_array_gen) self.ao_to_scan.AO.set_out(value) # aca puede esperar o chequear algo, por ahora nada self.cam.trigger() except StopIteration: self.simple_scan_measurement_end() def get_scan_signal(self, ao_name): return [ao for ao in anal_control_signal._registry if ao.name == ao_name][0] @QtCore.pyqtSlot(float) def save_data_from_scan_step(self, roiData): row = [time.time(), self.ao_to_scan.AO.current_value, roiData] self.storage.append_data_to_current_file(row) self.simple_scan_measurement_step() def abort_measurement(self): self.scan_array_gen.close() print('Measurement aborted')