Commit 9b311ce0 authored by Martin Drechsler's avatar Martin Drechsler

a general main file added, for running the total control app

parent 21a894d8
......@@ -18,6 +18,7 @@ from subclasses.cameraParameterTree import CameraParameterTree
#from drivers.andorzyla import AndorZyla
from drivers.dummyAndor import AndorZyla
from measurement import MeasurementGui, MeasurementWorker
import sys
import numpy as np
......@@ -45,24 +46,31 @@ class CameraGuiMainWindow(QMainWindow):
self.cw = QtGui.QWidget()
self.win.show()
self.d1 = dockarea.Dock("Zyla Camera View")
self.d2 = dockarea.Dock("Zyla Camera Analysis")
self.d3 = dockarea.Dock("Zyla Camera Control")
self.d4 = dockarea.Dock("Measurement and saving")
self.area.addDock(self.d1)
self.area.addDock(self.d2, "left", self.d1)
self.area.addDock(self.d3, "right", self.d1)
self.area.addDock(self.d4, "bottom", self.d3)
self.dCameraView = dockarea.Dock("Zyla Camera View")
self.dCameraTimeAnal = dockarea.Dock("Zyla Camera Time Analysis")
self.dCameraControl = dockarea.Dock("Zyla Camera Control")
self.dMeasurement = dockarea.Dock("Measurement and saving")
self.dConsole = dockarea.Dock("Console for debugging")
self.dCameraScanAnal = dockarea.Dock("Zyla Camera Scan Analysis")
self.area.addDock(self.dCameraView)
self.area.addDock(self.dCameraScanAnal, "left", self.dCameraView)
self.area.addDock(self.dCameraTimeAnal, "above", self.dCameraScanAnal)
self.area.addDock(self.dCameraControl, "right", self.dCameraView)
self.area.addDock(self.dConsole, "bottom", self.dCameraControl)
self.area.addDock(self.dMeasurement, "above", self.dConsole)
# button spinbox and label
self.cameraButton = QPushButton("Start Acquisition")
self.isCameraAcquiring = False
self.d3.addWidget(self.cameraButton)
self.dCameraControl.addWidget(self.cameraButton)
self.label = QLabel("Counter of frames")
self.d1.addWidget(self.label)
self.dCameraView.addWidget(self.label)
self.param_tree = CameraParameterTree()
self.d3.addWidget(self.param_tree.t)
self.dCameraControl.addWidget(self.param_tree.t)
# layouts and viewboxes
self.ImageLayout = pg.GraphicsLayoutWidget()
......@@ -73,10 +81,10 @@ class CameraGuiMainWindow(QMainWindow):
self.img = pg.ImageItem(border="w")
self.imv = pg.ImageView(imageItem=self.img, view=self.view)
self.imv.ui.roiBtn.setText('Useless')
self.d1.addWidget(self.imv)
self.dCameraView.addWidget(self.imv)
# analysis layout
self.d2.addWidget(self.AnalysisLayout)
self.dCameraTimeAnal.addWidget(self.AnalysisLayout)
self.p = self.AnalysisLayout.addPlot(row=0, col=0, title="Time plot")
self.p.setRange(QtCore.QRectF(0, 0, 50, 255))
self.p.setAutoPan(y=True)
......@@ -106,7 +114,7 @@ class CameraGuiMainWindow(QMainWindow):
self.console = console.ConsoleWidget(
namespace = {'np': np, 'cam': backend.cam, 'roi': self.rois[0]}
)
self.d4.addWidget(self.console)
self.dConsole.addWidget(self.console)
def camera_button_pressed(self):
......@@ -204,4 +212,8 @@ if __name__ == "__main__":
cameraThread.start()
measurementGui = MeasurementGui()
MeasurementWorker = MeasurementWorker(camera)
myGuiMainWindow.dMeasurement.addWidget(measurementGui)
sys.exit(app.exec_())
......@@ -573,6 +573,9 @@ class AndorBase(SDK3Camera):
def GetBufferOverflowEvent(self):
return self.BufferOverflowEvent.getValue()
def GetAOIBinning(self):
return self.AOIBinning.getValue()
def GetMetaData(self):
metadata = dict()
metadata["BufferOverflowEvent"] = self.GetBufferOverflowEvent()
......@@ -584,6 +587,7 @@ class AndorBase(SDK3Camera):
metadata["CCDHeight"] = self.GetCCDHeight()
metadata["PicWidth"] = self.GetPicWidth()
metadata["PicHeight"] = self.GetPicHeight()
metadata["AOIBinning"] = self.GetAOIBinning()
metadata["CCDTemp"] = self.GetCCDTemp2()
metadata["NumImsBuffered"] = self.GetNumImsBuffered()
metadata["BufferSize"] = self.GetBufferSize()
......@@ -765,6 +769,28 @@ class AndorBase(SDK3Camera):
print('stopping acq loop thread')
def live_acquisition_loop_triggered(self):
t = threading.currentThread()
while getattr(t, "do_run", True):
a_s, px_encoding, xs, ys, bufs = self._live_acq_auxs
try:
pData, lData = SDK3.WaitBuffer(self.handle, 10000)
except:
return
img = create_aligned_array(xs*ys, 'uint16')
SDK3.ConvertBuffer(bufs[self.acq_index_i%len(bufs)].ctypes.data_as(ctypes.POINTER(ctypes.c_uint8)),
img.ctypes.data_as(ctypes.POINTER(ctypes.c_uint8)),
xs, ys, a_s,
px_encoding, 'Mono16')
img.shape = (ys, xs)
self.current_image = img
self.acq_queue.put(self.current_image)
SDK3.QueueBuffer(self.handle, bufs[self.acq_index_i%len(bufs)].ctypes.data_as(SDK3.POINTER(SDK3.AT_U8)), bufs[self.acq_index_i%len(bufs)].nbytes)
self.helper.imageAquiredSignal.emit(self.acq_index_i)
self.acq_index_i = self.acq_index_i + 1
print('stopping acq loop thread')
def _convert_buffer_12(self, buf):
import itertools
......
from PyQt5 import QtGui, QtCore
from drivers.andorzyla import AndorZyla
from cameraGui import CameraGuiMainWindow
from zylaCameraWorker import CameraWorker
from measurement import MeasurementWorker, MeasurementGui
from MCDAQcontrolsignals import anal_control_signal
from MCDAQcontrolsignals import digital_control_signal
from controlGui import ControlGui
if __name__ == "__main__":
import sys
app = QtGui.QApplication([])
camera = AndorZyla(0)
piezoA397 = anal_control_signal('piezoA397', channel=0, ao_type='cavity_piezo', out_minimum = 0, out_maximum = 4)
piezoB397 = anal_control_signal('piezoB397', channel=1, ao_type='cavity_piezo')
piezoA866 = anal_control_signal('piezoA866', channel=2, ao_type='cavity_piezo', out_minimum = 0, out_maximum = 4)
piezoB866 = anal_control_signal('piezoB866', channel=3, ao_type='cavity_piezo')
piezo423 = anal_control_signal('piezo423', channel=4, ao_type='laser_piezo')
trapDCA = anal_control_signal('dcA', channel = 5, ao_type='electrode')
trapDCB = anal_control_signal('dcB', channel = 6, ao_type='electrode')
trapCOMPC = anal_control_signal('compC', channel = 7, ao_type='electrode')
trapCOMPD = anal_control_signal('compD', channel = 8, ao_type='electrode')
trapOven = anal_control_signal('compOven', channel = 9, ao_type='electrode')
trapExYb = anal_control_signal('compExYb', channel = 10, ao_type='electrode')
shutter866 = digital_control_signal('shutter866', channel = 0)
shutter397 = digital_control_signal('shutter397', channel = 1)
shutter423 = digital_control_signal('shutter423', channel = 2)
shutter866WM = digital_control_signal('shutter866WM', channel = 3)
controlGui = ControlGui()
mcDAQthread = QtCore.QThread()
for ao in anal_control_signal._registry:
controlGui.make_connections(ao)
ao.make_connections(controlGui)
ao.moveToThread(mcDAQthread)
ao.scanTimer.moveToThread(mcDAQthread)
ao.scanTimer.timeout.connect(ao.scan_event)
for do in digital_control_signal._registry:
do.make_connections(controlGui)
do.moveToThread(mcDAQthread)
myGuiMainWindow = CameraGuiMainWindow()
cameraWorker = CameraWorker(andor_camera=camera)
cameraWorker.make_connections(myGuiMainWindow)
myGuiMainWindow.make_connections(cameraWorker)
cameraThread = QtCore.QThread()
cameraWorker.moveToThread(cameraThread)
measurementGui = MeasurementGui()
MeasurementWorker = MeasurementWorker(camera)
myGuiMainWindow.dMeasurement.addWidget(measurementGui)
cameraThread.start()
mcDAQthread.start()
sys.exit(app.exec_())
......@@ -4,32 +4,83 @@
tip: pyuic5 -x ventana.ui -o ventana_ui.py
@author: martindrech
The ui skeleton is built with qtdesigner and its structur lies in the measurement_ui.py file.
"""
from PyQt5 import QtCore, QtWidgets
from PyQt5 import QtCore, QtWidgets, QtGui
from PyQt5.QtCore import QSettings
from PyQt5.QtWidgets import QAction, QFileDialog, QInputDialog, QWidget
from measurement_ui import Ui_Frame
from MCDAQcontrolsignals import anal_control_signal
class MeasurementGui(QtWidgets.QFrame, Ui_Frame):
def __init__(self):
super().__init__()
self.setupUi(self)
for ao in anal_control_signal._registry:
self.selectScanSignal.addItem(ao.name)
try:
self.configure_spinBoxes(anal_control_signal._registry[0].name)
except IndexError:
print('No analog control signals defined. ')
self.treeModel = QtGui.QStandardItemModel()
self.treeView.setAlternatingRowColors(True)
self.treeView.setSortingEnabled(True)
self.treeView.setHeaderHidden(False)
self.treeView.setSelectionBehavior(QtGui.QAbstractItemView.SelectItems)
self.treeView.setEditTriggers(QtGui.QAbstractItemView.NoEditTriggers)
self.treeModel.setHorizontalHeaderLabels(['Parameter', 'Value'])
self.treeView.setModel(self.treeModel)
self.treeModel.insertRow(0)
self.treeModel.setData(self.treeModel.index(0, 0), r'dV')
self.treeModel.setData(self.treeModel.index(0, 1), '?')
def make_connections(self, backend):
# internal
self.folderButton.clicked.connect(self.select_folder)
self.selectScanSignal.activated[str].connect(self.configure_spinBoxes)
self.startValue.valueChanged.connect(self.update_tree)
self.endValue.valueChanged.connect(self.update_tree)
self.stepsNum.valueChanged.connect(self.update_tree)
def select_folder(self):
directory = QFileDialog.getExistingDirectory(self, 'Choose directory')
self.folderBrowser.setText(directory)
@QtCore.pyqtSlot(str)
def configure_spinBoxes(self, ao_name):
ao = self.get_selected_ao()
self.startValue.setMinimum(ao.min)
self.startValue.setMaximum(ao.max)
self.endValue.setMinimum(ao.min)
self.endValue.setMaximum(ao.max)
def get_selected_ao(self):
try:
return [ao for ao in anal_control_signal._registry if ao.name == self.selectScanSignal.currentText()][0]
except IndexError:
print('No analog control signals defined. ')
def update_tree(self):
try:
self.treeModel.setData(self.treeModel.index(0, 1), (self.endValue.value()-self.startValue.value())/self.stepsNum.value() )
except:
self.treeModel.setData(self.treeModel.index(0, 1), '?')
class MeasurementWorker(QtCore.QObject):
"""
Backend for the measurement frame.
"""
def __init__(self, camera, analog_control_signals):
def __init__(self, camera):
super().__init__()
def make_connections(self, frontend):
......@@ -39,26 +90,22 @@ class MeasurementWorker(QtCore.QObject):
pass
# def open_from(self, aos, window):
# name = QFileDialog.getOpenFileName(window, 'Save File')
# if not name[0]:
# print('Opening was canceled')
# return 0
# settings = QSettings(name[0], QSettings.IniFormat)
# settings.beginGroup('Ventana')
# for ao in aos:
# spin_boxes = ao.spin_boxes
# for text, spinb in spin_boxes:
# spin = settings.value(str(ao.name) + '_' + text)
# spinb.setValue( float(spin) )
# settings.endGroup()
if __name__ == '__main__':
import sys
from PyQt5 import QtWidgets
from measurement_ui import Ui_Frame
piezoA397 = anal_control_signal('piezoA397', channel=0, ao_type='cavity_piezo', out_minimum = 0, out_maximum = 4)
piezoB397 = anal_control_signal('piezoB397', channel=1, ao_type='cavity_piezo')
piezoA866 = anal_control_signal('piezoA866', channel=2, ao_type='cavity_piezo', out_minimum = 0, out_maximum = 4)
piezoB866 = anal_control_signal('piezoB866', channel=3, ao_type='cavity_piezo')
piezo423 = anal_control_signal('piezo423', channel=4, ao_type='laser_piezo')
trapDCA = anal_control_signal('dcA', channel = 5, ao_type='electrode')
trapDCB = anal_control_signal('dcB', channel = 6, ao_type='electrode')
trapCOMPC = anal_control_signal('compC', channel = 7, ao_type='electrode')
trapCOMPD = anal_control_signal('compD', channel = 8, ao_type='electrode')
trapOven = anal_control_signal('compOven', channel = 9, ao_type='electrode')
trapExYb = anal_control_signal('compExYb', channel = 10, ao_type='electrode')
app = QtWidgets.QApplication(sys.argv)
gui = MeasurementGui()
measurementWorker = MeasurementWorker(None, None)
......
......@@ -20,15 +20,6 @@ class Ui_Frame(object):
self.gridLayout = QtWidgets.QGridLayout(self.gridLayoutWidget)
self.gridLayout.setContentsMargins(0, 0, 0, 0)
self.gridLayout.setObjectName("gridLayout")
self.stepsNum = QtWidgets.QSpinBox(self.gridLayoutWidget)
self.stepsNum.setObjectName("stepsNum")
self.gridLayout.addWidget(self.stepsNum, 3, 1, 1, 1)
self.endValue = QtWidgets.QSpinBox(self.gridLayoutWidget)
self.endValue.setObjectName("endValue")
self.gridLayout.addWidget(self.endValue, 2, 1, 1, 1)
self.startValue = QtWidgets.QSpinBox(self.gridLayoutWidget)
self.startValue.setObjectName("startValue")
self.gridLayout.addWidget(self.startValue, 1, 1, 1, 1)
self.selectScanSignal = QtWidgets.QComboBox(self.gridLayoutWidget)
self.selectScanSignal.setObjectName("selectScanSignal")
self.gridLayout.addWidget(self.selectScanSignal, 0, 1, 1, 1)
......@@ -50,6 +41,15 @@ class Ui_Frame(object):
self.label_5 = QtWidgets.QLabel(self.gridLayoutWidget)
self.label_5.setObjectName("label_5")
self.gridLayout.addWidget(self.label_5, 4, 0, 1, 1)
self.startValue = SpinBox(self.gridLayoutWidget)
self.startValue.setObjectName("startValue")
self.gridLayout.addWidget(self.startValue, 1, 1, 1, 1)
self.endValue = QtWidgets.QDoubleSpinBox(self.gridLayoutWidget)
self.endValue.setObjectName("endValue")
self.gridLayout.addWidget(self.endValue, 2, 1, 1, 1)
self.stepsNum = QtWidgets.QSpinBox(self.gridLayoutWidget)
self.stepsNum.setObjectName("stepsNum")
self.gridLayout.addWidget(self.stepsNum, 3, 1, 1, 1)
self.startMeasureButton = QtWidgets.QPushButton(Frame)
self.startMeasureButton.setGeometry(QtCore.QRect(20, 320, 171, 23))
self.startMeasureButton.setObjectName("startMeasureButton")
......@@ -57,9 +57,9 @@ class Ui_Frame(object):
self.measureProgressBar.setGeometry(QtCore.QRect(20, 350, 171, 23))
self.measureProgressBar.setProperty("value", 24)
self.measureProgressBar.setObjectName("measureProgressBar")
self.listWidget = QtWidgets.QListWidget(Frame)
self.listWidget.setGeometry(QtCore.QRect(270, 110, 281, 111))
self.listWidget.setObjectName("listWidget")
self.treeView = QtWidgets.QTreeView(Frame)
self.treeView.setGeometry(QtCore.QRect(270, 110, 281, 111))
self.treeView.setObjectName("treeView")
self.label_6 = QtWidgets.QLabel(Frame)
self.label_6.setGeometry(QtCore.QRect(340, 80, 161, 20))
self.label_6.setObjectName("label_6")
......@@ -72,9 +72,9 @@ class Ui_Frame(object):
self.saveMeasureButton = QtWidgets.QPushButton(Frame)
self.saveMeasureButton.setGeometry(QtCore.QRect(199, 320, 151, 23))
self.saveMeasureButton.setObjectName("saveMeasureButton")
self.dumpMeasureButton = QtWidgets.QPushButton(Frame)
self.dumpMeasureButton.setGeometry(QtCore.QRect(200, 350, 151, 23))
self.dumpMeasureButton.setObjectName("dumpMeasureButton")
self.abortMeasureButton = QtWidgets.QPushButton(Frame)
self.abortMeasureButton.setGeometry(QtCore.QRect(30, 380, 151, 23))
self.abortMeasureButton.setObjectName("abortMeasureButton")
self.retranslateUi(Frame)
QtCore.QMetaObject.connectSlotsByName(Frame)
......@@ -91,8 +91,9 @@ class Ui_Frame(object):
self.label_6.setText(_translate("Frame", "Info about measurement"))
self.folderButton.setText(_translate("Frame", "Folder"))
self.saveMeasureButton.setText(_translate("Frame", "Save measurement"))
self.dumpMeasureButton.setText(_translate("Frame", "Dump measurement"))
self.abortMeasureButton.setText(_translate("Frame", "Abort measurement"))
from pyqtgraph import SpinBox
if __name__ == "__main__":
import sys
......
Pseudo codigo de medicion:
inputs:
- señal de control a escanear:
- minimo
- maximo
- pasos o deltaV
- Todas las demas señales que quedan constanes: esto sale de la gui de control
- Parametros de la camara: por ahora puede salir de la gui de la camara.
- Nombre de archivo donde guardar: esto mas bien que sea automatico, pero puede permitir editar.
Los objetos que hay que dejarle controlar: señalDeControl, camara
Work flow:
- Elegir parametros
- Elegir empezar medicion
- Bloquear cambios del usuario en las guis. Dejar accesible un boton para detener medicion.
- Medicion:
- Setear señal de scan
- esperar algun tiempo o chequear que la señal se seteo correctamente
- Tomar imagen y calcular cuentas en roi
- Guardar dato y actualizar gui de la camara
- repetir por todos el rango de medicion
- finalizar medicion
- Desbloquear guis
......@@ -29,15 +29,6 @@
</rect>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="3" column="1">
<widget class="QSpinBox" name="stepsNum"/>
</item>
<item row="2" column="1">
<widget class="QSpinBox" name="endValue"/>
</item>
<item row="1" column="1">
<widget class="QSpinBox" name="startValue"/>
</item>
<item row="0" column="1">
<widget class="QComboBox" name="selectScanSignal"/>
</item>
......@@ -79,6 +70,15 @@
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="SpinBox" name="startValue"/>
</item>
<item row="2" column="1">
<widget class="QDoubleSpinBox" name="endValue"/>
</item>
<item row="3" column="1">
<widget class="QSpinBox" name="stepsNum"/>
</item>
</layout>
</widget>
<widget class="QPushButton" name="startMeasureButton">
......@@ -107,7 +107,7 @@
<number>24</number>
</property>
</widget>
<widget class="QListWidget" name="listWidget">
<widget class="QTreeView" name="treeView">
<property name="geometry">
<rect>
<x>270</x>
......@@ -166,20 +166,27 @@
<string>Save measurement</string>
</property>
</widget>
<widget class="QPushButton" name="dumpMeasureButton">
<widget class="QPushButton" name="abortMeasureButton">
<property name="geometry">
<rect>
<x>200</x>
<y>350</y>
<x>30</x>
<y>380</y>
<width>151</width>
<height>23</height>
</rect>
</property>
<property name="text">
<string>Dump measurement</string>
<string>Abort measurement</string>
</property>
</widget>
</widget>
<customwidgets>
<customwidget>
<class>SpinBox</class>
<extends>QDoubleSpinBox</extends>
<header location="global">pyqtgraph</header>
</customwidget>
</customwidgets>
<resources/>
<connections/>
</ui>
......@@ -3,7 +3,7 @@ from pyqtgraph.Qt import QtGui, QtCore
from PyQt5.QtWidgets import QPushButton, QProgressBar, QLabel
import pyqtgraph as pg
import numpy as np
import resources.scanFunctions
import resources.scanFunctions as scanFunctions
from resources.messages import show_warning
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment